我有一个相当简单的鸟瞰2D游戏,其中塔精灵通过向他们射击子弹来防御传入的移动精灵。我的问题:如果子弹总是具有相同的定义速度,我如何计算子弹到达其移动目标所需的子弹速度?
我正在使用JavaScript并拥有这些精灵变量(以及其他): sprite.x,sprite.y,sprite.width,sprite.height,sprite.speedX(即velocity),sprite.speedY ...所以我有对象originSprite,targetSprite和bulletSprite,都有这些类型的值,而我需要设置正确的bulletSprite速度值。
可能它看起来不错,子弹将从originSprite的外部开始(或者一些定义的半径,虽然我想从originSprite中心开始也可以工作),但它的子弹中心会尝试击中它的中心targetSprite左右。请注意,这个世界上没有引力或任何东西。 (也许我应该使用角度和速度来获得我的精灵变量,但现在我正在使用speedX和speedY ......)
非常感谢!
答案 0 :(得分:6)
将目标精灵视为二维房间中的直线,其中:
A(time) = (sprite.positionX + sprite.speedX * time, sprite.positionX + sprite.speedX * time)
由于你的子弹速度恒定,你也知道:
bullet.speedX^2 + bullet.speedY^2 = bullet.definedSpeed^2
然后你也可以计算子弹的直线:
B(time) = (bullet.positionX + bullet.speedX * time, bullet.positionX + bullet.speedX * time)
你知道这两条线都在某处:
A(time) = B(time)
然后由您决定使用您给定的值来解决这些方程式,并寻求time
的最小值。
答案 1 :(得分:5)
答案 2 :(得分:3)
使用vectors可以使围绕这个的数学看起来更简单一些。 Sylvester似乎是JavaScript中有希望的向量实现,但出于我的例子的目的,我将编写自己的向量函数。我还假设.x
/ .y
是在左上角测量的。
// this is a "constant" - representing 10px motion per "time unit"
var bulletSpeed = 10;
// calculate the vector from our center to their center
var enemyVec = vec_sub(targetSprite.getCenter(), originSprite.getCenter());
// measure the "distance" the bullet will travel
var dist = vec_mag(enemyVec);
// adjust for target position based on the amount of "time units" to travel "dist"
// and the targets speed vector
enemyVec = vec_add(enemyVec, vec_mul(targetSprite.getSpeed(), dist/bulletSpeed));
// calculate trajectory of bullet
var bulletTrajectory = vec_mul(vec_normal(enemyVec), bulletSpeed);
// assign values
bulletSprite.speedX = bulletTrajectory.x;
bulletSprite.speedY = bulletTrajectory.y;
// functions used in the above example:
// getCenter and getSpeed return "vectors"
sprite.prototype.getCenter = function() {
return {
x: this.x+(this.width/2),
y: this.y+(this.height/2)
};
};
sprite.prototype.getSpeed = function() {
return {
x: this.speedX,
y: this.speedY
};
};
function vec_mag(vec) { // get the magnitude of the vector
return Math.sqrt( vec.x * vec.x + vec.y * vec.y);
}
function vec_sub(a,b) { // subtract two vectors
return { x: a.x-b.x, y: a.y-b.y };
}
function vec_add(a,b) { // add two vectors
return { x: a.x + b.x, y: a.y + b.y };
}
function vec_mul(a,c) { // multiply a vector by a scalar
return { x: a.x * c, y: a.y * c };
}
function vec_div(a,c) { // divide == multiply by 1/c
return vec_mul(a, 1.0/c);
}
function vec_normal(a) { // normalize vector
return vec_div(a, vec_mag(a));
}
答案 3 :(得分:1)
计算射手和目标之间的距离:dist = sqrt((xt - xs)^2 + (yt - ys)^2)
将x和y距离除以上述距离:nx = (xt - xs)/dist; ny = (yt - ys)/dist;
(向量的归一化)
将结果乘以一个因子,得到每个时间单位n个像素,即。每个方向的速度。它应该在想要的方向上保持恒定的速度。
答案 4 :(得分:0)
我假设目标将以恒定速度在直线上移动。
如果方向和方向的子弹速度都是可变的(即您尝试计算子弹的speedX
和speedY
),则会有无数的解决方案。
如果设置固定方向,则只需将子弹和目标的两条线相交。从目标的当前点和交叉点(以及目标的速度)之间的距离,您可以计算目标到达此交叉点所需的时间。
从子弹的原点和交叉点(以及之前计算的时间)之间的距离,您可以计算子弹的速度。