繁体   English   中英

以 2D 形式拍摄移动物体

[英]Shoot moving objects in 2D

我有一个包含多个对象的二维空间(我们称它们为 B)。 假设对象 A 是我们的自动演员,他在特定路径上移动,他只需要射击它可以破坏的对象。 其他对象可能会或可能不会移动。

我需要找到我应该发射与对象 B 碰撞的子弹的方向。子弹以与对象 A 不同的速度移动,并且它具有特定的寿命。

图表

我试图用二次方来解决它,但我总是得到无穷大,这是一种错误的方法吗?

                Vector3 vectorFromVictim = bullet.Position - victim.Position;
                float distanceToVictim = vectorFromVictim.Length();
                double victimSpeed = victim.Position.Length();               

                double a = bulletSpeed * bulletSpeed - victimSpeed * victimSpeed;
                double b = 2 * vectorFromVictim.Dot(victim.LinearVelocity);
                double c = -distanceToVictim * distanceToVictim;

                float t = (QuadraticSolver(a, b, c));
                if (float.IsInfinity(t))
                {
                    return;
                }

                interceptionPosition = victim.Position + victim.LinearVelocity * t;

                if (t <= bulletLifetime)
                {
                    ShootAtDirection(interceptionPosition);
                }

编辑:我的 QuadraticSolver 是这个

            double d = Math.Pow(b, 2) - (4 * a * c);
            
            if (d < 0)
            {
                return float.PositiveInfinity;
            }

            float t;
            if (d == 0)
            {
                t = (float) (-b / (2 * a));
                if (float.IsNaN(t))
                {
                    return float.PositiveInfinity;
                }
                return t;
            }

            t = (float) ((-b - Math.Sqrt(d)) / (2 * a));
            float t2 = (float) ((-b + Math.Sqrt(d)) / (2 * a));
            if (t < t2)
            {
                return t < 0 ? float.PositiveInfinity : t;
            }
            
            return t2 < 0 ? float.PositiveInfinity : t2;

B(目标)坐标是

bx + ux * t, by + uy * t

其中 ux, uy 是 B 速度矢量的分量

子弹坐标是

ax + v * cos(f) * t, ay + v * sin(f) * t

其中v是子弹速度, f是方向角(未知)

ax + v * cos(f) * t = bx + ux * t
ay + v * sin(f) * t = y + uy * t

t * (v * cos(f) - ux) = bx - ax = dx 
t * (v * sin(f) - uy) = bx - ax = dy
    dx, dy is position difference, negated your vectorFromVictim

排除 t

dy *  (v * cos(f) - ux) = dx * (v * sin(f) - uy) 
dy * v * cos(f) - dy * ux = dx * v * sin(f) - dx * uy 
v * (dy*cos(f) - dx*sin(f)) = dy * ux - dx * uy 

g = atan2(dy, dx)   
L = vectorFromVictim.Length

所以

v * sin(g - f) = L * (dy * ux - dx * uy)
sin(g - f) = L/v * (dy * ux - dx * uy) 
g - f = arcsin(L/v * (dy * ux - dx * uy) ) 

最后

f = g - arcsin(L/v * (dy * ux - dx * uy) ) 

快速 Python 测试

import math
def aiming(ax, ay, bx, by, ux, uy, v):
    dx = bx - ax
    dy = by - ay
    g = math.atan2(dy, dx)
    L = math.hypot(dy, dx)
    if (v * math.cos(ang) - ux):
        t = dx / (v * math.cos(ang) - ux)
    elif (v * math.sin(ang) - uy):
        t = dy / (v * math.sin(ang) - uy)
    else:
        return None 
    coll_x = bx + ux * t
    coll_y = by + uy * t
    return ang, coll_x, coll_y

print(aiming(0, 0, 0, 1, 1, 0, 1.4142))

给出正确的值0.7854 = Pi/4 radians = 45 degrees ,点 (1,1)

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM