我正在用C++写一点物理模拟,基本上是在屏幕上移动圆圈,当两个圆圈发生碰撞时,它们应该像弹子球一样弹跳。当这些圈子相互碰撞时,大多数时候它们实际上会无限地减速/它们看起来相互粘在一起并变得静止。有时候只有一个球会在碰撞中反弹,另一个会保持它的运动轨迹。这只是一个简单的2D模拟。圆形碰撞回弹不能正常工作
所以这里就是我对检测/跳弹逻辑:
bool Ball::BallCollision(Ball &b2)
{
if (sqrt(pow(b2.x - x, 2) + pow(b2.y - y, 2)) <= b2.radius + radius) // Test for collision
{
normal[0] = (x - (x + b2.x)/2)/radius; // Finds normal vector from point of collision to radius
normal[1] = (y - (y + b2.y)/2)/radius;
xvel = xvel - 2 * (xvel * normal[0]) * normal[0]; // Sets the velocity vector to the reflection vector
yvel = yvel - 2 * (yvel * normal[1]) * normal[1];
////x = xprev; // These just move the circle back a 'frame' so the collision
////y = yprev; // detection doesn't detect collision more than once.
// Not sure if working?
}
}
我想不出有什么不对我的功能。感谢您提前提供任何帮助!
编辑: 每个变量声明为float
功能:
void Ball::Move()
{
xprev = x;
yprev = y;
x += xvel;
y += yvel;
}
void Ball::DrawCircle()
{
glColor3ub(100, 230, 150);
glBegin(GL_POLYGON);
for (int i = 0; i < 10; i++)
{
angle = i * (2*3.1415/10);
newx = x + r*cos(angle);
newy = y + r*sin(angle);
glVertex2f(newx, newy);
}
glEnd();
}
循环:
run_prev.clear(); // A vector, cleared every loop, that holds the Ball objects that collided
for (int i = 0; i < num_balls; i++)
{
b[i].Move();
}
for (int i = 0; i < num_balls; i++)
{
b[i].WallCollision(); // Just wall collision detecting, that is working just fine
}
//The loop that checks for collisions... Am I executing this properly?
for (int i = 0; i < num_balls; i++)
{
for (int j = 0; j < num_balls; j++)
{
if (i == j) continue;
if (b[i].BallCollision(b[j]) == true)
{
run_prev.push_back(b[i]);
}
}
}
for (int i = 0; i < num_balls; i++)
{
b[i].DrawCircle();
}
//xprev and yprev are the x and y values of the frame before for each circle
for (int i = 0; i < run_prev.size(); i++)
{
run_prev[i].x = run_prev[i].xprev;
run_prev[i].y = run_prev[i].yprev;
}
你应该发布你的变量是什么类型,只是为了知道我们是否可以排除舍入或其他铸造错误。 – vsz 2012-03-31 07:48:14
我不明白你为什么要这样计算正常值。他们应该有单位长度吗? – 2012-03-31 08:06:41
我以为他们是。无论我可能滑倒,请纠正我。 – Christian 2012-03-31 08:08:48