# Triangle with $3$ unknowns

I have a situation where I am trying to calculate a leading shot for a character in a 2D top down game. The enemy character moves with a certain speed $s$, which is applied to its normalized direction vector each game tick--so the game ticks are discrete units of "time" as opposed to actual time.

I have my character, which shoots a bullet with speed $z$. During my leading shot calculation, I can aim my character towards the enemy character, and calculate $\phi$ between the line drawn directly between the enemy and my character.

I need to somehow calculate $\theta$, the angle I need to shoot the bullet in order to hit the enemy character...the unknowns are: $t$, $\theta$, and the third angle.

Can't remember how to do this.

Here is a picture of the situation: • $${\sin (\theta)\over s*t} = {\sin (\phi)\over z*t}$$
– user312097
Jul 7, 2016 at 13:33
• thought it was something simple like that...but I refused to believe. lol Jul 7, 2016 at 13:34
• same with me :)
– user312097
Jul 7, 2016 at 13:35

After seeing the answer above, I was able to mostly solve the problem. There was an issue, however, in that the sign of $\theta$ is always positive when you actually go through the whole solution--calculating the vectors, then $\phi$, then $\theta$ using the law of sines.

So the issue is: which side of the character face vector is the enemy direction vector (assuming the character is facing the enemy). There doesn't seem to be a trivial way to figure this out, given two arbitrary vectors, using the tools a computer has.

The simplest, most straight forward way that I found to accomplish this--without any kind of logic or pattern recognition--was to just use the sign of the determinant of the two vectors--so $\operatorname{sign}(x_1*y_2 - y_1*x_2)$. The asymmetry gives you a left and right with only 2 multiplies and a subtraction (important when you are in a game loop that is doing 120 fps).

Anyhow, here is how it worked out:

In order to calculate $\phi$ in the drawing above, I used the dot product:

$$\mathbf{A}\bullet\mathbf{B} = ||A||\operatorname{cos}\phi$$

Where $\mathbf{A}$ is the unit vector pointing from the enemy to my character (in the drawing), and $\mathbf{B}$ is the unit vector pointing in the enemy's direction of travel.

Having solved for $\phi$ by taking the $\operatorname{arccos}$ of the dot product result, I calculated $\theta$ in the drawing above with the law of sines,

$$z*t*\operatorname{sin}\theta = s*t*\operatorname{sin}\phi\\ \theta = \operatorname{arcsin}(\frac{s}{z}\operatorname{sin}\phi)$$

But there was a problem: $\theta$ was always positive. The issue was the range of the $\operatorname{arccos}$ function: $[0,\pi]$. As a result of the $\operatorname{arccos}$ range, $\phi$ was always positive, and the character would only lead the enemy when the angular velocity of the enemy relative to the character was positive.

So, in order to recapture the "sign" of the angle, I think that what you need is the sign of the determinant of the two vectors (did not find an authority or proof...just thought about it and tested).

So,

$$\theta' = \operatorname{sign}(\operatorname{det} \begin{bmatrix} A_x & A_y \\ B_x & B_y \end{bmatrix} ) * \theta$$

Will give you back the "sign" of the angle.

• I did not read your answer full but here is my idea to deal with it. You can get the direction the enemy is travelling, that is either left or right of the player and so if it is right then positive and if left then negative.
– user312097
Jul 8, 2016 at 13:47
• @ritwiksinha yeah, the determinant was the easiest way to figure out right and left sides...because when it is just two arbitrary vectors in any random direction, it is kind of hard to say for sure what left and right is--rotate back to 0, then see what quadrant the vector is in was the only way I could think of that was robust...but it is a gui screen, so X and Y are pixels counting from the top left, so rotation is problematic... The determinant is going to capture L/R in two multiplies and one subtraction, while an abstract "left" and "right" is going to take a lot of work in code. Jul 8, 2016 at 20:20
• It wont take too much but yes the determinant is easier. Anyway thanks, i don't do much programming but once i encountered a similar problem and i calculated left and right instead of using determinants.
– user312097
Jul 8, 2016 at 20:55
• @A---B no, you are right -- it won't take too much...but it will lack the elegance of the determinant :) May 17, 2020 at 20:52

By the Law of sines, we have $$\frac{\sin \theta}{s\cdot t} = \frac{\sin \phi}{z\cdot t}$$ We can cancel the common factors of $t$ and isolate $$\sin\theta = \frac{s}{z} \sin\phi$$ This should help you find $\theta$.

• @MatthewLeingang i think you should have wrote your own answer, instead of doing complete revamp of mine. Anyway i don't have a problem with it.
– user312097
Jul 7, 2016 at 16:59
• my only additional contribution was to cite the Law of sines and cancel a t. Your answer was CW so it seemed greedy to post the same thing under my own name. In any case, the question has an answer. Jul 7, 2016 at 23:05
• @MatthewLeingang wound up uncovering an issue when you try to solve the whole problem. Jul 8, 2016 at 13:21