让敌方车辆跟随玩家车辆C++

Getting enemy vehicle to follow player vehicle C++

本文关键字:C++ 玩家 跟随 方车辆      更新时间:2023-10-16

我目前正在制作一款游戏,玩家驾驶一辆半卡车,被敌方汽车尾随并试图猛烈撞击。我从我的一位老师那里得到了一些帮助,告诉我如何让敌人选择前进的方向,以便跟随并攻击玩家。在实施她给我的东西时,我有了奇怪的行为,感觉自己错过了什么。

当我在游戏中把一辆敌方汽车放在玩家附近,并把玩家的位置传给功能时,敌方汽车只是绕着圆圈旋转。如果加上速度,我会绕大圈行驶。一般来说,它从不选择直接驶入的方向。

调试后,我的if语句似乎永远无法解析,每次更新时,它都会尝试返回0,但由于某种原因,它无法解析。我不确定是玩家的坐标造成了问题,还是我的数学计算不稳定。

void EnemySpeedy::playerTracking(float posX, float posY)
{
    //Direction choosing
    dir.x = posX - pos.x;
    dir.y = posY - pos.y;
    //plus maybe this?
    goalAngle = atan2f(dir.y, dir.x);
    //I think this is the problem code?//
    if (angle < goalAngle) angle -= sfw::getDeltaTime() * angularSpeed;
    else                   angle += sfw::getDeltaTime() * angularSpeed;

    //AI Movement alla adding velocity
    acc = speed;
    vel = vel + (acc - dragVel) * sfw::getDeltaTime();
    vel = std::fmaxf(0, vel);
    vel = std::fminf(vel, maxVel);
    pos = { pos.x + vel * cosf(angle * PI / 180) * sfw::getDeltaTime(),
            pos.y + vel * sinf(angle * PI / 180) * sfw::getDeltaTime() };
}

atan2f返回弧度,因此您的goalAngle在[-Pi,Pi]范围内。

我不知道你的angleangularSpeed是否使用相同的度量,但当你计算sinfcosf时,你正在将angle从度转换为弧度。

我建议你把所有的角度都用弧度表示,并检查一下:

#include <cmath>
inline float normAngle ( float ang ) {
    return ang < -M_PI ? ang + 2.0*M_PI : ( ang > M_PI ? ang - 2.0*M_PI : ang);
}
inline float limitValue ( float x, float min, float max ) {
    return x < min ? min : ( x > max ? max : x );
}

然后,你可以试试这个逻辑:

void EnemySpeedy::playerTracking(float posX, float posY)
{
    //Direction choosing, pos is a member of EnemySpeedy
    float dirX = posX - pos.x;
    float dirY = posY - pos.y;
    //Angle choosing; angle, angularSpeed and angularSpeedMax are members of EnemySpeedy
    float goalAngle = atan2(dirY, dirX);
    float difAngle = normAngle(angle - goalAngle);
    angularSpeed = limitValue(-difAngle,-angularSpeedMax,angularSpeedMax);
    float dt = sfw::getDeltaTime();
    angle = normAngle(angle + dt * angularSpeed);
    // Update speed; acc, vel, etc. are members of EnemySpeedy class
    // acc = speed;         // it seems odd to me...
    // vel = limitValue(vel + (acc - dragVel) * dt, 0.0, maxVel);
                         // what about:
    acc = (difAngle > 1.5 || difAngle < -1.5) ? -maxAcc/2.0 : maxAcc*(maxVel - vel)/maxVel;
    //          brake if direction is wrong, go to limit velocity otherwise
    acc = limitValue(acc, -maxAcc, maxAcc);
    vel = limitValue(vel + acc * dt, 0.0, maxVel);
    // Update position
    pos.x += vel * cos(angle) * dt;
    pos.y += vel * sin(angle) * dt;
}