我正在用C ++制作游戏,这是一个可以在舞台上移动的坦克。坦克有一个角度(漂浮,以度为单位,我假设坦克在他的大炮指向右边时为0º),速度(浮动),并且有一个称为“deltaT”(浮动)的时间常数。
当玩家向前移动坦克时,为了计算新坦克,我使用三角学和时间函数的位置物理方程(我的意思是X(t),我不知道它用英语怎么说)阶段中的坐标。
这是我的问题:由于从float到int的通道,不考虑最接近零的值。因此,在某些角度,坦克看起来是旋转的,但是朝不同的方向移动。
这就是我的代码所做的:
1 - 首先,我通过使用坦克移动的角度来分离其组件X和Y的速度:
float speedX = this->speed * cos(this->angle);
float speedY = this->speed * sin(this->angle);
2 - 然后使用我上面提到的等式来获得新坐标:
this->x = (int) ceil(this->x + (speedX * deltaT));
this->y = (int) ceil(this->y - (speedY * deltaT));
问题从第一步开始:在某些角度,cos或sin的值非常接近于零。 因此,当我将它乘以速度来获得速度X时,我仍然得到一个非常低的数字,然后当我将它乘以deltaT它仍然太低时,最后当应用ceil时,这个数量完全丢失了。
例如,在94º,deltaT = 1.5,速度= 2,假设X的初始值为400,我们有:
speedX = -0.1395...
this->x = 400 //it must be 399.86..., but stays in 400 due to the ceiling
因此,在我的游戏中,坦克显示为旋转,但直接向前移动。此外,有时候它向后移动但向前移动错误,反之亦然。
¿我怎样才能让坦克的方向更准确?提高deltaT的速度或值不是选项,因为它是关于坦克,而不是公式1:P
答案 0 :(得分:9)
如何使水箱的方向更准确?提高deltaT的速度或值不是选项,因为它是关于坦克,而不是公式1:P
您应该将您的位置值存储为float
s,即使它们最终用作int
用于屏幕定位。这样,你就不会失去你职位的非整数部分。当您进行绘图时,只需在最后投射到int
。
答案 1 :(得分:5)
始终将坦克的位置保持在float
。或者,只让油箱以45度的增量旋转。决定你的游戏是否会使用大致的位置和标题或精确的位置,并一直坚持这个决定。
答案 2 :(得分:0)
你的问题不准确!浮点数学具有24位精度,即正/负1 / 16,777,216。没问题。
这是你的rounding mode。
ceil
四舍五入。
尝试:
int x = this->x + (speedX * deltaT) +.5f;
ceil
创建的0℃的舍入误差(E); E&。1,如上面所铸造给出-.5&LT,E 1 + 5,其具有一半的绝对误差
另外,避免使用双数学。 ceil
是双重版本,您的意思是ceilf
。从技术上讲,您的代码会抛出float-> double-> int。你从中得不到任何东西,但需要时间。
最后......真正的问题:
你的准确性问题真的是因为你在积累它!
所以0< E< 1 ... PER FRAME! 无论你怎么回事,这总是一个问题。
而是在舍入之前存储浮点结果。因此,绝对误差总是0 你现在应该顺利移动。 PS:英文单词是"参数",https://en.wikipedia.org/wiki/Parametric_equation
在60Hz => 0℃; E< 60 *秒。因此,在一分钟0 this->XPos += speedX * deltaT;
this->YPos += speedY * deltaT;
this->x = static_cast<int>(this->XPos+.5f);
this->y = static_cast<int>(this->YPos+.5f);