C++ Game Development

Creating interactive games and entertainment software

🎮 What is Game Development?

Game development with C++ involves creating interactive entertainment software using powerful graphics libraries, game engines, and real-time programming techniques for optimal performance.


// Simple game loop structure
#include <iostream>
#include <chrono>

class Game {
public:
    void run() {
        while (running) {
            update();
            render();
        }
    }
private:
    bool running = true;
    void update() { /* Game logic */ }
    void render() { /* Draw graphics */ }
};
                                    

Output:

Game loop running...

(Continuous update and render cycle)

Key Game Development Areas

đŸŽ¯

Game Loop

Core update-render cycle

while (running) {
    update();
    render();
}
🎨

Graphics

2D/3D rendering and sprites

// SDL2 example
SDL_RenderCopy(renderer, 
    texture, NULL, ▭);
đŸŽĩ

Audio

Sound effects and music

// SFML example
sf::Sound sound;
sound.setBuffer(buffer);
sound.play();
đŸ•šī¸

Input

Keyboard, mouse, and controller

if (sf::Keyboard::isKeyPressed(
    sf::Keyboard::Space)) {
    jump();
}

🔹 Simple Player Class

Basic game entity with position and movement:

#include <iostream>
#include <cmath>

struct Vector2 {
    float x, y;
    
    Vector2(float x = 0, float y = 0) : x(x), y(y) {}
    
    Vector2 operator+(const Vector2& other) const {
        return Vector2(x + other.x, y + other.y);
    }
    
    float magnitude() const {
        return std::sqrt(x * x + y * y);
    }
};

class Player {
private:
    Vector2 position;
    Vector2 velocity;
    float speed;
    int health;
    
public:
    Player(float x, float y) : position(x, y), speed(5.0f), health(100) {}
    
    void move(float deltaX, float deltaY) {
        velocity = Vector2(deltaX * speed, deltaY * speed);
        position = position + velocity;
    }
    
    void takeDamage(int damage) {
        health -= damage;
        if (health < 0) health = 0;
    }
    
    bool isAlive() const {
        return health > 0;
    }
    
    void printStatus() const {
        std::cout << "Player at (" << position.x << ", " << position.y 
                  << ") Health: " << health << std::endl;
    }
};

int main() {
    Player player(0, 0);
    
    player.printStatus();
    player.move(1, 0);  // Move right
    player.move(0, 1);  // Move up
    player.printStatus();
    
    player.takeDamage(25);
    player.printStatus();
    
    return 0;
}

Output:

Player at (0, 0) Health: 100

Player at (5, 5) Health: 100

Player at (5, 5) Health: 75

🔹 Simple Game State Manager

Managing different game states (menu, playing, paused):

#include <iostream>
#include <memory>
#include <stack>

enum class GameState {
    MENU,
    PLAYING,
    PAUSED,
    GAME_OVER
};

class StateManager {
private:
    std::stack<GameState> states;
    
public:
    void pushState(GameState state) {
        states.push(state);
        std::cout << "Entered state: " << stateToString(state) << std::endl;
    }
    
    void popState() {
        if (!states.empty()) {
            std::cout << "Exiting state: " << stateToString(states.top()) << std::endl;
            states.pop();
        }
    }
    
    GameState getCurrentState() const {
        return states.empty() ? GameState::MENU : states.top();
    }
    
    void update() {
        GameState current = getCurrentState();
        
        switch (current) {
            case GameState::MENU:
                updateMenu();
                break;
            case GameState::PLAYING:
                updateGame();
                break;
            case GameState::PAUSED:
                updatePause();
                break;
            case GameState::GAME_OVER:
                updateGameOver();
                break;
        }
    }
    
private:
    std::string stateToString(GameState state) const {
        switch (state) {
            case GameState::MENU: return "Menu";
            case GameState::PLAYING: return "Playing";
            case GameState::PAUSED: return "Paused";
            case GameState::GAME_OVER: return "Game Over";
            default: return "Unknown";
        }
    }
    
    void updateMenu() { std::cout << "Updating menu..." << std::endl; }
    void updateGame() { std::cout << "Updating game..." << std::endl; }
    void updatePause() { std::cout << "Game paused..." << std::endl; }
    void updateGameOver() { std::cout << "Game over screen..." << std::endl; }
};

int main() {
    StateManager stateManager;
    
    stateManager.pushState(GameState::MENU);
    stateManager.update();
    
    stateManager.pushState(GameState::PLAYING);
    stateManager.update();
    
    stateManager.pushState(GameState::PAUSED);
    stateManager.update();
    
    stateManager.popState(); // Back to playing
    stateManager.update();
    
    return 0;
}

Output:

Entered state: Menu

Updating menu...

Entered state: Playing

Updating game...

Entered state: Paused

Game paused...

Exiting state: Paused

Updating game...

🔹 Simple Collision Detection

Basic rectangle collision detection for 2D games:

#include <iostream>

struct Rectangle {
    float x, y, width, height;
    
    Rectangle(float x, float y, float w, float h) 
        : x(x), y(y), width(w), height(h) {}
    
    bool intersects(const Rectangle& other) const {
        return (x < other.x + other.width &&
                x + width > other.x &&
                y < other.y + other.height &&
                y + height > other.y);
    }
    
    void print() const {
        std::cout << "Rect(" << x << ", " << y << ", " 
                  << width << ", " << height << ")" << std::endl;
    }
};

class GameObject {
protected:
    Rectangle bounds;
    
public:
    GameObject(float x, float y, float w, float h) : bounds(x, y, w, h) {}
    
    virtual ~GameObject() = default;
    
    bool collidesWith(const GameObject& other) const {
        return bounds.intersects(other.bounds);
    }
    
    Rectangle getBounds() const { return bounds; }
    
    virtual void onCollision(const GameObject& other) {
        std::cout << "Collision detected!" << std::endl;
    }
};

class Player : public GameObject {
public:
    Player(float x, float y) : GameObject(x, y, 32, 32) {}
    
    void onCollision(const GameObject& other) override {
        std::cout << "Player hit something!" << std::endl;
    }
};

class Enemy : public GameObject {
public:
    Enemy(float x, float y) : GameObject(x, y, 24, 24) {}
    
    void onCollision(const GameObject& other) override {
        std::cout << "Enemy collision!" << std::endl;
    }
};

int main() {
    Player player(10, 10);
    Enemy enemy1(50, 50);  // No collision
    Enemy enemy2(15, 15);  // Collision
    
    std::cout << "Checking collisions:" << std::endl;
    
    if (player.collidesWith(enemy1)) {
        player.onCollision(enemy1);
    } else {
        std::cout << "No collision with enemy1" << std::endl;
    }
    
    if (player.collidesWith(enemy2)) {
        player.onCollision(enemy2);
    } else {
        std::cout << "No collision with enemy2" << std::endl;
    }
    
    return 0;
}

Output:

Checking collisions:

No collision with enemy1

Player hit something!

🧠 Test Your Knowledge

What is the core pattern in most game engines?