본문 바로가기
-----ETC-----/C++ 게임 개발 시리즈

[C++ 게임 개발 시리즈] Day 12: 2D 물리 엔진 기초 (Box2D)

by cogito21_cpp 2024. 8. 1.
반응형

2D 물리 엔진 기초 (Box2D)

물리 엔진은 게임에서 현실적인 움직임과 상호작용을 구현하는 데 사용됩니다. 오늘은 2D 물리 엔진인 Box2D를 사용하여 간단한 물리 효과를 구현하는 방법을 학습하겠습니다.

Box2D 설치 및 설정

Box2D는 2D 물리 엔진으로, 다양한 게임에서 물리 시뮬레이션을 제공하는데 사용됩니다.

Box2D 설치

  1. Box2D 다운로드:
  2. Box2D 빌드:
    • CMake를 사용하여 Box2D를 빌드합니다. 터미널이나 명령 프롬프트에서 다음 명령어를 실행합니다. 
    • cmake -Bbuild -H. cmake --build build
  3. Box2D 라이브러리 포함:
    • 빌드된 Box2D 라이브러리를 프로젝트에 포함합니다.

Box2D 기본 사용법

Box2D는 물리 세계(world), 물리 객체(body), 형상(shape) 등으로 구성됩니다. 다음은 Box2D를 사용하여 간단한 물리 시뮬레이션을 구현하는 예제입니다.

기본 설정

  1. Box2D 헤더 파일 포함
  2. 물리 세계 생성
  3. 물리 객체 생성
  4. 물리 시뮬레이션 실행
#include <SFML/Graphics.hpp>
#include <Box2D/Box2D.h>
#include <iostream>

// 픽셀을 미터로 변환하는 비율
const float SCALE = 30.0f;

// Box2D 세계와 객체를 설정하는 함수
void setupBox2DWorld(b2World& world) {
    // 바닥 생성
    b2BodyDef groundBodyDef;
    groundBodyDef.position = b2Vec2(400.0f / SCALE, 550.0f / SCALE);
    b2Body* groundBody = world.CreateBody(&groundBodyDef);

    b2PolygonShape groundBox;
    groundBox.SetAsBox(400.0f / SCALE, 10.0f / SCALE);
    groundBody->CreateFixture(&groundBox, 0.0f);

    // 상자 생성
    b2BodyDef boxBodyDef;
    boxBodyDef.type = b2_dynamicBody;
    boxBodyDef.position = b2Vec2(400.0f / SCALE, 100.0f / SCALE);
    b2Body* boxBody = world.CreateBody(&boxBodyDef);

    b2PolygonShape dynamicBox;
    dynamicBox.SetAsBox(25.0f / SCALE, 25.0f / SCALE);

    b2FixtureDef fixtureDef;
    fixtureDef.shape = &dynamicBox;
    fixtureDef.density = 1.0f;
    fixtureDef.friction = 0.3f;
    boxBody->CreateFixture(&fixtureDef);
}

int main() {
    // SFML 창 생성
    sf::RenderWindow window(sf::VideoMode(800, 600), "Box2D Example");

    // Box2D 세계 생성
    b2Vec2 gravity(0.0f, 9.8f);
    b2World world(gravity);

    setupBox2DWorld(world);

    // 상자 그래픽 생성
    sf::RectangleShape box(sf::Vector2f(50.0f, 50.0f));
    box.setFillColor(sf::Color::Green);
    box.setOrigin(25.0f, 25.0f);

    // 게임 루프
    sf::Clock clock;
    while (window.isOpen()) {
        sf::Event event;
        while (window.pollEvent(event)) {
            if (event.type == sf::Event::Closed)
                window.close();
        }

        // deltaTime 계산
        float deltaTime = clock.restart().asSeconds();

        // Box2D 물리 시뮬레이션 업데이트
        world.Step(deltaTime, 8, 3);

        // 상자의 위치와 회전 업데이트
        b2Body* boxBody = world.GetBodyList()->GetNext(); // 첫 번째 객체는 바닥이므로 다음 객체를 가져옴
        b2Vec2 position = boxBody->GetPosition();
        float32 angle = boxBody->GetAngle();
        box.setPosition(position.x * SCALE, position.y * SCALE);
        box.setRotation(angle * 180.0f / b2_pi);

        // 화면 지우기
        window.clear();

        // 상자 그리기
        window.draw(box);

        // 화면에 그리기
        window.display();
    }

    return 0;
}

 

결론

오늘은 2D 물리 엔진인 Box2D를 사용하여 간단한 물리 시뮬레이션을 구현하는 방법을 학습했습니다. Box2D의 기본 설정과 물리 객체를 생성하고, 이를 SFML을 사용하여 화면에 렌더링하는 방법을 알아보았습니다. 질문이나 추가적인 피드백이 있으면 언제든지 댓글로 남겨 주세요. 내일은 "Day 13: 충돌 처리와 반응"에 대해 학습하겠습니다.

반응형