이전글에서 오일러각을 이용해 플레이어 카메라의 방향벡터를 구할 수 있었고, 그 벡터의 x, z 성분이 플레이어의 평면 상에서의 방향벡터라는 것도 알 수 있었다.
이때 플레이어의 평면 상의 방향벡터가 forward 벡터가 된다.
FPS에서 W나 S를 누르면 바라보는 방향으로 이동하는데,
즉 플레이어의 속도= forward 방향*스칼라*캐릭터 이동속도 가 된다.
(여기서 스칼라 값은 W를 눌렀는지 S를 눌렀는지에 따라 결정되며 보통 W를 1, S를 -1로 둔다. 조이스틱에선 조이스틱을 기울인 정도까지 고려해 -1~1 사이의 값을 줄 수 있다.)
마찬가지로 A나 D를 누르면 속도 = right방향*스칼라*캐릭터 이동속도 가 된다.
(이 경우엔 D가 1, A가 -1)
종합하면 플레이어의 xz평면 상에서의 wasd 이동은
V = forward * 스칼라A * 이속 + right * 스칼라B * 이속
으로 정의할 수 있다.
이때 right 벡터를 어떻게 구하는가?
forward 벡터와 right 벡터가 90도를 이룬다는 것을 이용해, forward 벡터와 up벡터 (0,1,0)을 외적하면 right 벡터를 구할 수 있다.
a x b는 a와 b 벡터 모두와 수직이며, 길이가 |a||b|sin c이다. 여기서 주의해야 할 점은 a x b일때와 b x a 일때 벡터의 방향이 다르다는 점이며, 때문에 forward x up을 하면 right가 나오지먼 up x forward를 하면 left 가 나온다.
(c는 a와 b가 이루는 각)
외적은 내적과 반대로 sin을 곱하기 때문에 각이 90도일 때 크기가 가장 크고 0도일때 크기가 가장 작다. (0이다)
The cross product - Math Insight
There are two ways to take the product of a pair of vectors. One of these methods of multiplication is the cross product, which is the subject of this page. The other multiplication is the dot product, which we discuss on another page. The cross product is
mathinsight.org
v = (vx, vy, vz)
w = (wx, wy, wz)
v X w
= (vy * wz - vz * wy, vz * wx - vx * wz, vx * wy - vy * wx)
|v X w|
= |v| |w| sin 세타
참고1)
|v X w| = |v| |w| sin 세타 식으로는 외적의 크기만을 알아낼 수 있다. 외적해서 나온 벡터를 얻고 싶다면 외적 공식을 사용할 것.
내적의 경우 axbx + ayby, 그리고 |a||b|cos세타 모두 스칼라를 반환하지만,
외적의 경우 벡터를 반환하는 식과 스칼라를 반환하는 식이 있음에 주의.
참고2)
2차원 벡터의 경우 외적은 별도로 분리해 살펴볼 만 하다. 위 공식에 z=0을 대입하면 2차원 외적의 공식을 얻을 수 있다.
v x w = (vx * wy) - (vy * wx)
잘 살펴보면 이 공식은 사실
[[vx wx] [vy wy]]행렬의 determinent 혹은 판별식임을 알 수 있다. (ad-bc)
![](https://blog.kakaocdn.net/dn/3MVbe/btrGhyPPR4Z/A80CCdGgkLDhDqAotMaENk/img.jpg)
![](https://blog.kakaocdn.net/dn/bYk2Hw/btrGgsCPWJ6/Jsl7E9k8o88MBzBO8wL5qk/img.jpg)
2차원 벡터 두 개의 외적의 기하학적 성질이 중요한데, 3차원 벡터 두 개의 외적이 두 벡터와 수직을 이루는 벡터를 구하는 행위였다면, 2차원 벡터 두개의 외적은 두 벡터가 이루는 사각형의 면적을 나타낸다. (즉 결과값이 벡터가 아닌 스칼라라고 이해하면 된다)
이때 면적은 음수가 될 수도 있는데, 이는 벡터 v에 대해 벡터 w가 시계방향으로 회전한 곳에 위치하고 있을 경우이다.
이러한 성질을 이용해 어떤 백터가 다른 벡터와 비교했을 때 시계 방향으로 회전한 곳에 위치하는지 반시계 방향으로 회전한 곳에 위치하는 지를 구할 수 있다. 외적한 값이 양수인지 음수인지를 판별하면 된다. 이는 Convex hull을 구하기 위한 Graham scan 알고리즘에서 두 벡터가 시계인지 반시계인지를 구할 때 활용된다.
만약 면적이 양수 음수인지는 중요하지 않고 면적의 크기만을 구하고 싶다면 외적의 크기 공식을 사용하면 된다.
|v X w| = |v| |w| sin 세타
그런데 잘 살펴보면 이 공식은 삼각형의 면적을 구하는 공식에 2를 곱해준 것에 불과하다는 것을 알 수 있다. 2차원 벡터들의 외적이 두 벡터가 이루는 사각형의 면적을 구하는 공식이 되는 이유도 이 때문이다.
![](https://blog.kakaocdn.net/dn/biXM9R/btrDHGcPH4P/X8jQB7IISY4EF3JrLwgGi0/img.png)
![](https://blog.kakaocdn.net/dn/G3wsT/btrqLVfWP5F/lgatfJ3uFFKudhRf6Lm1s1/img.jpg)
'mathematics > game mathematics' 카테고리의 다른 글
[Mathematics] 5. AABB Intersection (0) | 2022.01.23 |
---|---|
[Mathematics] 4. Interpolation (0) | 2022.01.20 |
[Mathematics] 2. Euler angle (0) | 2022.01.15 |
[Mathematics] 1. Delta time (0) | 2022.01.15 |
오일러 각도 (Euler Angle) (0) | 2021.05.13 |