0% found this document useful (0 votes)
25 views12 pages

FPS Game

This document contains a C++ OpenGL program that implements a simple first-person shooter game using GLUT. The game features a camera that can move and shoot bullets at randomly placed targets, with a scoring system based on hits. Key functionalities include target initialization, bullet firing, movement controls, and rendering of the game scene with a crosshair and score display.

Uploaded by

mersha abdisa
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
25 views12 pages

FPS Game

This document contains a C++ OpenGL program that implements a simple first-person shooter game using GLUT. The game features a camera that can move and shoot bullets at randomly placed targets, with a scoring system based on hits. Key functionalities include target initialization, bullet firing, movement controls, and rendering of the game scene with a crosshair and score display.

Uploaded by

mersha abdisa
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as DOCX, PDF, TXT or read online on Scribd
You are on page 1/ 12

#include <GL/glut.

h>

#include <cmath>

#include <vector>

#include <cstdlib>

#include <ctime>

// Camera position and orientation

float cameraX = 0.0f, cameraY = 1.0f, cameraZ = 5.0f;

float lookX = 0.0f, lookY = 0.0f, lookZ = -1.0f;

float angleX = 0.0f, angleY = 0.0f;

// Movement variables

bool keyStates[256] = {false};

float moveSpeed = 0.1f;

float mouseSensitivity = 0.2f;

// Target structure

struct Target {

float x, y, z;

bool active;

};

std::vector<Target> targets;

// Bullet structure

struct Bullet {

float x, y, z;

float dx, dy, dz;

bool active;

};
std::vector<Bullet> bullets;

// Score

int score = 0;

void initTargets() {

srand(time(0));

for (int i = 0; i < 10; ++i) {

Target t;

t.x = (rand() % 20) - 10;

t.y = (rand() % 4) + 0.5f;

t.z = (rand() % 20) - 20;

t.active = true;

targets.push_back(t);

void drawTarget(float x, float y, float z) {

glPushMatrix();

glTranslatef(x, y, z);

glColor3f(1.0f, 0.0f, 0.0f); // Red target

// Draw a simple cube as target

glutSolidCube(0.5f);

glPopMatrix();

void drawBullet(float x, float y, float z) {


glPushMatrix();

glTranslatef(x, y, z);

glColor3f(1.0f, 1.0f, 0.0f); // Yellow bullet

// Draw a small sphere as bullet

glutSolidSphere(0.1f, 10, 10);

glPopMatrix();

void drawCrosshair() {

glDisable(GL_DEPTH_TEST);

glMatrixMode(GL_PROJECTION);

glPushMatrix();

glLoadIdentity();

gluOrtho2D(0, 100, 0, 100);

glMatrixMode(GL_MODELVIEW);

glPushMatrix();

glLoadIdentity();

glColor3f(1.0f, 1.0f, 1.0f);

glBegin(GL_LINES);

// Horizontal line

glVertex2f(48, 50);

glVertex2f(52, 50);

// Vertical line

glVertex2f(50, 48);

glVertex2f(50, 52);
glEnd();

glPopMatrix();

glMatrixMode(GL_PROJECTION);

glPopMatrix();

glMatrixMode(GL_MODELVIEW);

glEnable(GL_DEPTH_TEST);

void fireBullet() {

Bullet b;

b.x = cameraX;

b.y = cameraY;

b.z = cameraZ;

// Direction vector is the camera's look direction

b.dx = lookX * 0.5f;

b.dy = lookY * 0.5f;

b.dz = lookZ * 0.5f;

b.active = true;

bullets.push_back(b);

void updateBullets() {

for (size_t i = 0; i < bullets.size(); ) {

if (!bullets[i].active) {

bullets.erase(bullets.begin() + i);

continue;
}

bullets[i].x += bullets[i].dx;

bullets[i].y += bullets[i].dy;

bullets[i].z += bullets[i].dz;

// Check if bullet hits any target

for (size_t j = 0; j < targets.size(); ++j) {

if (targets[j].active &&

abs(bullets[i].x - targets[j].x) < 0.5f &&

abs(bullets[i].y - targets[j].y) < 0.5f &&

abs(bullets[i].z - targets[j].z) < 0.5f) {

targets[j].active = false;

bullets[i].active = false;

score++;

break;

// Deactivate bullet if it goes too far

if (abs(bullets[i].x) > 50 || abs(bullets[i].y) > 50 || bullets[i].z < -50) {

bullets[i].active = false;

i++;

void display() {
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

glLoadIdentity();

// Set camera position and orientation

gluLookAt(cameraX, cameraY, cameraZ,

cameraX + lookX, cameraY + lookY, cameraZ + lookZ,

0.0f, 1.0f, 0.0f);

// Draw ground

glColor3f(0.5f, 0.5f, 0.5f);

glBegin(GL_QUADS);

glVertex3f(-50.0f, 0.0f, -50.0f);

glVertex3f(-50.0f, 0.0f, 50.0f);

glVertex3f( 50.0f, 0.0f, 50.0f);

glVertex3f( 50.0f, 0.0f, -50.0f);

glEnd();

// Draw targets

for (const Target& t : targets) {

if (t.active) {

drawTarget(t.x, t.y, t.z);

// Draw bullets

for (const Bullet& b : bullets) {

if (b.active) {

drawBullet(b.x, b.y, b.z);

}
}

// Draw crosshair

drawCrosshair();

// Display score

glDisable(GL_DEPTH_TEST);

glMatrixMode(GL_PROJECTION);

glPushMatrix();

glLoadIdentity();

gluOrtho2D(0, 100, 0, 100);

glMatrixMode(GL_MODELVIEW);

glPushMatrix();

glLoadIdentity();

glColor3f(1.0f, 1.0f, 1.0f);

glRasterPos2f(10, 90);

std::string scoreStr = "Score: " + std::to_string(score);

for (char c : scoreStr) {

glutBitmapCharacter(GLUT_BITMAP_HELVETICA_18, c);

glPopMatrix();

glMatrixMode(GL_PROJECTION);

glPopMatrix();

glMatrixMode(GL_MODELVIEW);

glEnable(GL_DEPTH_TEST);
glutSwapBuffers();

void reshape(int w, int h) {

if (h == 0) h = 1;

glViewport(0, 0, w, h);

glMatrixMode(GL_PROJECTION);

glLoadIdentity();

gluPerspective(60.0f, (float)w / (float)h, 0.1f, 100.0f);

glMatrixMode(GL_MODELVIEW);

void keyboard(unsigned char key, int x, int y) {

keyStates[key] = true;

if (key == 27) { // ESC key

exit(0);

void keyboardUp(unsigned char key, int x, int y) {

keyStates[key] = false;

void mouse(int x, int y) {

static int centerX = 400, centerY = 300;


int deltaX = x - centerX;

int deltaY = y - centerY;

angleY += deltaX * mouseSensitivity;

angleX += deltaY * mouseSensitivity;

// Clamp vertical rotation

if (angleX > 89.0f) angleX = 89.0f;

if (angleX < -89.0f) angleX = -89.0f;

// Calculate new look direction

lookX = sin(angleY * M_PI / 180.0f);

lookY = -sin(angleX * M_PI / 180.0f);

lookZ = -cos(angleY * M_PI / 180.0f) * cos(angleX * M_PI / 180.0f);

// Normalize look vector

float length = sqrt(lookX*lookX + lookY*lookY + lookZ*lookZ);

lookX /= length;

lookY /= length;

lookZ /= length;

// Reset mouse to center of screen

glutWarpPointer(centerX, centerY);

void mouseClick(int button, int state, int x, int y) {

if (button == GLUT_LEFT_BUTTON && state == GLUT_DOWN) {

fireBullet();

}
}

void update(int value) {

// Handle movement based on key states

if (keyStates['w']) {

cameraX += lookX * moveSpeed;

cameraZ += lookZ * moveSpeed;

if (keyStates['s']) {

cameraX -= lookX * moveSpeed;

cameraZ -= lookZ * moveSpeed;

if (keyStates['a']) {

// Strafe left

cameraX -= cos(angleY * M_PI / 180.0f) * moveSpeed;

cameraZ += sin(angleY * M_PI / 180.0f) * moveSpeed;

if (keyStates['d']) {

// Strafe right

cameraX += cos(angleY * M_PI / 180.0f) * moveSpeed;

cameraZ -= sin(angleY * M_PI / 180.0f) * moveSpeed;

if (keyStates[' ']) { // Space bar

cameraY += moveSpeed;

if (keyStates['c']) {

cameraY -= moveSpeed;

}
// Keep camera above ground

if (cameraY < 0.5f) cameraY = 0.5f;

updateBullets();

glutPostRedisplay();

glutTimerFunc(16, update, 0); // ~60 FPS

int main(int argc, char** argv) {

glutInit(&argc, argv);

glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH);

glutInitWindowSize(800, 600);

glutCreateWindow("Simple FPS Game");

glutDisplayFunc(display);

glutReshapeFunc(reshape);

glutKeyboardFunc(keyboard);

glutKeyboardUpFunc(keyboardUp);

glutPassiveMotionFunc(mouse);

glutMouseFunc(mouseClick);

glutTimerFunc(0, update, 0);

// Hide cursor and capture mouse

glutSetCursor(GLUT_CURSOR_NONE);

glutWarpPointer(400, 300);

// Initialize game elements

initTargets();
// Enable depth testing

glEnable(GL_DEPTH_TEST);

glutMainLoop();

return 0;

You might also like