Odpowiedzi:
Paraboliczna funkcja trayectory jest zdefiniowana jako:
Fx = Vox*t + Ox;
Fy = -0.5 * g * t * t + Voy*t + Oy;
Znane wartości:
P: the target point.
O: the origin point.
g: gravity.
t: time needed to impact.
Nieznane wartości:
Vo: Initial Velocity
Aby obliczyć „Vo”, możemy nadać wartości funkcji F:
't' = flight time 'duration'
'F' = target point 'P'
(Px-Ox)
Vox = --------
duration
Py + 0.5* g * duration * duration - Oy
Voy = ---------------------------------------
duration
Możesz teraz uzyskać wszystkie wartości, aby osiągnąć cel od początku, podając wartości t do równania F:
When t = 0 => F == O (Origin)
When t = duration => F == P (Target)
Niedawno musiałem rozwiązać podobny problem, wymyśliłem dwa rozwiązania oparte na formule, którą znalazłem na stronie wikipedii „Dan the Man”, o której już wspominałem: trajektoria pocisku
W tym rozwiązaniu faktycznie potrzebujesz stałego kąta startu lub prędkości x. Prędkość Y nie jest potrzebna, ponieważ wystrzeliwujemy pocisk pod określonym kątem.
Rozwiązanie 1, kąt startu jest stały, obliczyć prędkość:
g = 9.81; // gravity
x = 49; // target x
y = 0; // target y
o = 45; // launch angle
v = (sqrt(g) * sqrt(x) * sqrt((tan(o)*tan(o))+1)) / sqrt(2 * tan(o) - (2 * g * y) / x); // velocity
Rozwiązanie 2, prędkość jest stała, oblicz kąt startu:
g = 9.81; // gravity
v = 40; // velocity
x = 42; // target x
y = 0; // target y
s = (v * v * v * v) - g * (g * (x * x) + 2 * y * (v * v)); //substitution
o = atan(((v * v) + sqrt(s)) / (g * x)); // launch angle
W moim przypadku te rozwiązania działały całkiem dobrze.
Jeśli nie obchodzi cię, czy jest to poprawne matematycznie, wystarczy, że wygląda wystarczająco poprawnie, oblicz prostą ścieżkę i spraw, aby pocisk podążał tą ścieżką, ale „popchnij ją w górę” wzdłuż normalnej linii w zależności od jej odległości w dół segment linii, więc unosi się, gdy zbliża się do środka segmentu i spada, gdy odchodzi od środka segmentu linii.
Możesz użyć do tego fali sinusoidalnej, używając zakresu stopni od -90 do +90 (gdzie -90 to lewy punkt na segmencie linii, 90 to prawy punkt, a ty lerp na środku) i pomnóż wynik przez stałą, aby zwiększyć skalę.
Jeśli potrzebujesz czysto poprawnej odpowiedzi matematycznej / fizycznej, to nie pomoże. Jeśli tego nie zrobisz, prawdopodobnie będzie to dla ciebie całkiem dobre!
Nie zapominaj, że w programowaniu gier chodzi o stosowanie złudzeń, które wyglądają poprawnie (i są tańsze w obliczeniach), zamiast realizmu.
Jeśli potrzebujesz czegoś, co jest w porządku i masz stałą prędkość, możesz użyć tej bardzo uproszczonej metody.
distance = to.x - from.x;
angleToPoint = atan2(to.y - from.y, to.x - from.x);
distanceFactor = 1/1000;
angleCorrection = (PI*0.18) * (distance * distanceFactor);
velocity.X = cos(angleToPoint+angleCorrection) * power;
velocity.Y = sin(angleToPoint+angleCorrection) * power;
Odległość może być ujemna, ale nadal będzie działać, ponieważ kąt zależy również od odległości. Jeśli odległość jest ujemna, kąt, który należy dodać, jest również ujemny.
Będziesz musiał bawić się z DistanceFactor, aby znaleźć właściwą wartość. Zależy to od grawitacji i mocy pocisku. Powinien być blisko 1 podzielony przez maksymalną odległość, jaką pocisk może pokonać.