在 SDL 游戏中应用重力的问题 - 代码未按预期执行

问题描述 投票:0回答:1

我正在使用 SDL 开发一款游戏,目前正在致力于实现角色移动和重力。但是,我遇到了一个问题,即我的代码的特定部分未按预期运行。

我面临的问题围绕着向我的玩家角色施加重力。我已经实现了一个PhysicsEngine 类,负责管理重力和角色运动。在此类的更新方法中,我增加了 yVelocity 来模拟重力。然而,尽管观察到 yVelocity 正确增加,但限制速度的后续代码块并未按预期执行。

采取的调试措施: 我已采取以下步骤来调试该问题:

添加了调试输出语句(std::cout)来跟踪关键变量的值,包括 yVelocity。 观察到 yVelocity 在调试输出中正确增加,但更新角色位置的后续代码块(yVelocityAFTER 部分)未按预期执行。 分析了条件 if (yVelocity > MAX_FALL_SPEED) 并发现在游戏过程中的某个时刻应该满足该条件,但该块中的代码并未运行。

player_character 类:(我在其中绘制玩家)

void PlayerCharacter::draw(SDL_Renderer* renderer)
{
    // Define an array of colors corresponding to each body part
    std::vector<SDL_Color> bodyPartColors = {
        COLOR_DEEP_ORANGE, COLOR_DEEP_ORANGE,
        COLOR_ROYAL_BLUE, COLOR_ROYAL_BLUE,
        COLOR_WHITE, COLOR_DEEP_FOREST_GREEN,
        COLOR_SALMON, COLOR_CRIMSON,
        COLOR_DARK_PURPLE, COLOR_DARK_PURPLE
    };
    
    color.setRenderDrawColor(renderer, COLOR_ALPHA);
    SDL_RenderFillRect(renderer, &boundingBox);
    
    color.setRenderDrawColor(renderer, bodyPartColors[0]);
    
    for (int i = 0; i < bodyPartColors.size() && i <bodyPartColors.size(); i++)
    {
        color.setRenderDrawColor(renderer, bodyPartColors[i]);
        
        const auto& part = bodyParts[i];
        SDL_Rect partRect = {boundingBox.x + part.x, boundingBox.y + part.y, part.w, part.h};
        SDL_RenderFillRect(renderer, &partRect);
        
    }
}

physical_engine 类:(我更新游戏的地方)

void PhysicsEngine::update(const int WINDOW_WIDTH, const int WINDOW_HEIGHT)
{
    checkCollisionWithGround(WINDOW_HEIGHT);
    checkCollisionWithWalls(WINDOW_WIDTH, WINDOW_HEIGHT);
    
    playercharacter.boundingBox.x += xVelocity;
    std::cout << "BoundingBoxY BEFORE: " << playercharacter.boundingBox.y << std::endl;
    playercharacter.boundingBox.y += yVelocity;
    std::cout << "BoundingBoxY AFTER: " << playercharacter.boundingBox.y << std::endl;
    //movePlayerLeft(100, false);
    //movePlayerRight(100, false);
    //move(0, 10);
    

这就是我上面提到的问题发生的地方:

  
    // Gravity conts
    const double GRAVITY = 0.5;
    const double MAX_FALL_SPEED = 10;
    
    yVelocity += GRAVITY;
    
    std::cout << "yVelocityBEFORE: " << yVelocity << std::endl;
    
    if (yVelocity > MAX_FALL_SPEED)
    {
        yVelocity = MAX_FALL_SPEED;
        std::cout << "yVelocityAFTER: " << yVelocity << std::endl;
    }
    for (auto& part : playercharacter.bodyParts)
    {
        part.x += xVelocity;
        part.y += yVelocity;
    }
}

边界框语句的控制台输出:

BoundingBoxY BEFORE: 720
BoundingBoxY AFTER: 720
BoundingBoxY BEFORE: 720
BoundingBoxY AFTER: 720 

Velocity 语句的控制台输出:(如您所见,yVelocityAFTER 不输出)

yVelocityBEFORE: 0.5
yVelocityBEFORE: 0.5
yVelocityBEFORE: 0.5
yVelocityBEFORE: 0.5

类输入处理:


void InputHandler::eventHandling(bool& isLeftKeyPressed, bool& isRightKeyPressed)
{
    bool quit = false;
    SDL_Event e;
    // Event handling
    while (SDL_PollEvent(&e) != 0)
    {
        if (e.type == SDL_QUIT)
        {
            quit = true;
            std::cout << "Quit detected";
        }
        else if (e.type == SDL_KEYDOWN)
        {
            switch (e.key.keysym.sym)
            {
                case SDLK_UP:
                    physicsengine.playerJump();
                    break;
                case SDLK_LEFT:
                    isLeftKeyPressed = true;
                    std::cout << "LEFT KEY PRESSED";
                    break;
                case SDLK_RIGHT:
                    isRightKeyPressed = true;
                    std::cout << "RIGHT KEY PRESSED";
                    break;
                default:
                    break;
            }
        }
        else if (e.type == SDL_KEYUP)
        {
            switch (e.key.keysym.sym)
            {
                case SDLK_LEFT:
                    isLeftKeyPressed = false;
                    break;
                case SDLK_RIGHT:
                    isRightKeyPressed = false;
                    break;
                default:
                    break;
            }
        }
    }
}

run_game 类:

void Game::runGame(SDL_Renderer* renderer, int WINDOW_WIDTH, int WINDOW_HEIGHT)
{
    
    while (!quit)
    {
        inputhandler.eventHandling(isLeftKeyPressed, isRightKeyPressed);
        physicsengine->update(WINDOW_WIDTH, WINDOW_HEIGHT);
        
        if (inputhandler.isLeftKeyPressed)
        {
            playercharacter->move(-1, 0); // Adjust the amount as needed
        }

    
        color.setRenderDrawColor(renderer, COLOR_PERIWINKLE_BLUE);
        SDL_RenderClear(renderer);
        
        // Draw game objects here
        
        // Drawing
        
        playercharacter->draw(renderer);
        enemy->drawEnemy(renderer, WINDOW_HEIGHT);
        enemy->enemyMovment(renderer, WINDOW_WIDTH);
        hairline.drawHair(renderer);
        SDL_RenderPresent(renderer);
    }
}

任何帮助将不胜感激。

c++ 2d sdl game-development
1个回答
-1
投票

从代码中我可以看到,yVelocity 似乎在再次递增之前不断重置。我看不到它是在哪里声明的,但是如果它是在函数内部声明的,那么该变量将被重置,然后在每次调用该函数时重新声明。

void SomeFunction() {
   double yVelocity = 0.0;
   
   //some code

   yVelocity += 0.5;
   std::cout << yVelocity << std::endl;
  //more code
}

int main() {

   //some code

   while(true) {
      SomeFunction();
   }
   
   return 0;
}

这将继续打印 0.5,因为 yVelocity 将被声明、递增,然后超出范围、重置,然后重新声明。

© www.soinside.com 2019 - 2024. All rights reserved.