将重力应用于物体

时间:2017-01-18 02:16:16

标签: c++ opengl glut

我在对象上实施重力方面遇到了麻烦。

我有一堆使用OpenGL绘制的圆形对象。我使用delta-xdelta-y移动圈子(球)。我试图在每帧的y坐标处添加一个引力常数,以便模拟向下拉,但我不确定该怎么做。

以下是相关代码:

class Ball
{
    public:
        double x;
        double y;
        double radius;
        double deltaX;
        double deltaY;
};


std::vector<Ball> gAllBalls;  // a vector of balls with random positions and delta-values
double gGravity = ?;  // gravitational constant - I know it's 92 m/s^s, but I don't know how to apply that to deltaX and deltaY


void display(void)
{
    glClear(GL_COLOR_BUFFER_BIT);

    for (auto &thisBall : gAllBalls)
    {
        // draw
        glColor3d(thisBall.red, thisBall.green, thisBall.blue);
        DrawCircle(thisBall.x, thisBall.y, thisBall.radius);

        // gravity - not working
        if (thisBall.y + thisBall.radius < gScreenHeight - gGravity)
        {
            thisBall.y += gGravity;
        }

        // wall bouncing
        if (thisBall.y + thisBall.radius + thisBall.deltaY >= gScreenHeight)  // up
        {
            thisBall.deltaY = -thisBall.deltaY;
        }

        if (thisBall.y + thisBall.deltaY - thisBall.radius < 0)  // down
        {
            thisBall.deltaY = -thisBall.deltaY;
        }

        if (thisBall.x + thisBall.deltaX - thisBall.radius < 0) // left
        {
            thisBall.deltaX = -thisBall.deltaX;
        }

        if (thisBall.x + thisBall.radius + thisBall.deltaX >= gScreenWidth)  // right
        {
            thisBall.deltaX = -thisBall.deltaX;
        }

        // move
        thisBall.x += thisBall.deltaX;
        thisBall.y += thisBall.deltaY;
    }
    glutSwapBuffers();
    glutPostRedisplay();
}

我遇到的一个大问题是,我不知道如何计算重力,因为我使用deltaXdeltaY而不是单独的速度和距离变量计算为92 m / s ^ 2。然而,无论我将引力设置为什么,球都不会像他们应该的那样 - 无论重力如何,所以必须有其他错误,但我不知道是什么。

1 个答案:

答案 0 :(得分:4)

我认为这里的问题是物理学,而不是编程技术。 在你的情况下,我会改变“delta”#39;你的Ball类的成员要加速,因为它们是每个周期(时间)改变物体位置的距离单位,但这只是一个建议,使其更容易可视化......

class Ball
{
    public:
        double x;
        double y;
        double radius;
        double speedX;
        double speedY;
};

排在第二位,我在你的代码中,你正在改变&#39; y&#39;成员,而不是速度,因为重力改变速度,因此问题。 尝试这样做,为了调试目的,我会尝试使用准时对象(没有半径,只有普通(x,y)坐标)。

因此,总而言之,我只需将您的重力代码更改为以下内容:

  // gravity - 'fixed'
  if (thisBall.y + thisBall.radius < gScreenHeight - gGravity)
  {
      thisBall.speedY -= gGravity; //notice the '-'
  }

引力的价值应该是绝对的和积极的,以便保持事物的简单性。如果你试试这个,你应该有一个理想的简单物理模拟器,有一个恒定速度的球X(只改变它的方向,而不是幅度)。 请试试这个,让我知道它是怎么回事,祝你好运,坚持下去=)