본문 바로가기

유물/MDX/MDL

Extrarius - A (still not) brief tutorial on creating rotations


원문: http://wc3campaigns.com/showthread.php?t=79038
함부로 긁어왔습니다.
A (still not) brief tutorial on creating rotations

A (still not) brief tutorial on creating rotations:

Ok, so you know Quaternion Rotation is how rotations are represented, but still have no idea how to use them.

기본적인 쿼터니언을 사용하기 위해 반드시 알아야할 두가지가 있다 - 기본 회전을 어떻게 하는가, 그리고 회전을 어떻게 조합하는가.

우선, 원을 도는 기본 회전을 만들기 위해, 당신은 회전 커터니언이 기본적으로 4 부분을 가진다는 것을 알아야한다:XR, YR, ZR 그리고 WR. 내가 그것들 뒤에 R을 넣은 것에 주의해라. 그것들은 벡터 요소와 같은 것이 아니다.

당신이 (0, 0, 1) 같이 쭉 가는, 벡터를 가지고 있다고 하자. 그리고 당신은 계속 둥글게 회전시키길 원한다. 좋다, 완벽하게 둥글게 회전하기 위해, 당신은 0도를 시작해, 120도, 240, 그리고 360도(0도와 같다)로 회전을 애니메이트해야 한다.

왜 내가 이 숫자들을 지정했을까?, 글쎄, 원에서 당신은 0에서 360까지를 가진다. 그러나 당신이 0과 360만들 넣는다면, 그것이 같은 회전이기 때문에 거기엔 회전이 없다.
왜 간단히 반씩 0, 180, 360 으로 하지 않았나? 여기엔 두 방법이 있다. 0에서 180으로 가는 두가지 방법이 있다. clockwise 와 counter-clockwise, 그리고 당신이 회전 할 때, 진행할 수학 방법을 말하지 않않다. 그래서 당신은 저확히 180도로 회전하려고 할 어느 때 잘못된 회전을 얻을 것이다.
0, 1, 그리고 360 같은건 어떨까? 그것은 수학이 항상 제일 짧은 회전만 선택하기 때문에 제대로 작동하지 않는다.
그래서 1도, 그 다음에 다른 방법으로 2도를 회전해야 한다.
그래서 이 모든 것들은 전체 회전을 하기 위해서는 최소한 4프레임을 가져야 한다는 것이다. 그리고 당신이 다른 숫자(180도보다 작은 각 회전)를 선택할 수 있는 동안, 당신이 지속적인 속도에 부드러운 회전을 원하면, 그것은
.....................
All this means that it takes at least 4 frames to do a full rotation, and while you can pick other numbers (as long as each rotation is less than 180 degrees), if you want a smooth rotation at constant speed it's easiest to just use equally-spaced numbers and equally-spaced frames.

자, 이제 우리가 (0, 0, 1) 축으로 각도 0 부터 120, 240, 360까지 회전하기 원한다고 하자.

축과 각도(angle)를 커터니언으로 변환하는 것은 간단하다:
XR = Sine(Angle/2) * X
YR = Sine(Angle/2) * Y
ZR = Sine(Angle/2) * Z
WR = Cosine(Angle/2)

X, Y, Z는 무엇인가? 그것들은 단지 축의 요소가 아니라, 그것들은  normalized 축 벡터의 요소이다.
SineCosine 은 표준 Trigonometric 함수이다(Trigonometric Functions).

됐다, 이제 우리는 공식을 가졌다, 이제 뭐인가? 우선 회전은 모든 시간에 모든 에니메이션을 위해 적용될 것이다.
그래서 이것은GlobalSequences 섹션안의 엔트리가 필요하다. 전체 회전을 하기위한 3초를 만들어보자:
Code:
GlobalSequences 1 {
   Duration 3000,
}

이제, 어딘가(bone, helper, particle system 또는 우리가 회전하기 원하는 것 안에) 회전을 더해야한다:

Code:
Rotation 4 {
   Linear, //Linear Interpolation works fine for rotations
  GlobalSeqId 0,//Only global sequence there is
  //Axis = X 0.00000000 / Y 0.00000000 / Z 1.00000000
     0: {  0.00000000,  0.00000000,  0.00000000,  1.00000000 },//@    0.00
  1000: {  0.00000000,  0.00000000,  0.86602540,  0.50000000 },//@  120.00
  2000: {  0.00000000,  0.00000000,  0.86602540, -0.50000000 },//@  240.00
  3000: {  0.00000000,  0.00000000,  0.00000000, 1.00000000 },//@  360.00
}

이 숫자들이 어디서 온건가? MDL안의 WC3'의 회전을 위한 포햇은 (XR, YR, ZR, WR) 이고,0부터 3000 이다. 회전이 없는 것은 길이(각 요소 제곱, 모두 더하고 제곱근)는 항상 1이다. 그래서 '회전이 없다'라는 표현은 (0, 0, 0, 1)이다.

자, 이제 실제 회전:(0, 0, 1) 축과 각도 120을 위한 공식을 적용하면 우리는 다음을 얻는다:
XR = Sine(120/2) * 0 = 0
YR = Sine(120/2) * 0 = 0
ZR = Sine(120/2) * 1 = 0.866...
WR = Cosine(120/2) = 0.5
이제 가졌고, 120도를 위한 커터니언은 Z(수직) 축으로 회전(turn)됐다.

각 240도를 가지고 공식으 적용하면, WR 만 -0.5로 다르다.

기간을 위해 3000을 지정한 것은 에니메이션이 0프레임부터 2999까지 간다는 것을 의미하고, 3000프레임은 표시되지 않는다. The reason we specify a rotation for frame 3000 is that frame 2000 needs to blend back to frame 0 to make a smooth cycle 워크래프트 3는 이것을 자동적으로 해주지 않는다. 대신, 우리는 0프레임과 같은 3000프레임을 넣었고 그래서 2000프레임부터 0 프레임 같은 프레임과 같이 2999 까지 블렌딩한다. 효과는 같다(but more work).

이것에 관해 주목해야할 한가지 마지막은 이것은 모델 회전만이 아니라는 것이다, 이것은 또한 이것의 축도 회전시킨다. 이게 무엇을 의미하는가? 이것은 당신이 수평 X(1, 0, 0) 축에 대해 90도를 회전한다면, 당신은 Y 와 Z 축이 바뀔 것이다, Y 는 위/아래이고 Z 는 수평이다!  당신이 회전을 조합할 때 기억해라, 당신이 이것을 고려 안하면 틀린 결과를 얻을 수 있다.

자, 이제 회전을 조합해보자.
Ok, now to combine rotations(quite a bit longer)

Code:

A = (FirstWR + FirstXR)*(SecondWR + SecondXR);
B = (FirstZR - FirstYR)*(SecondYR - SecondZR);
C = (FirstWR - FirstXR)*(SecondYR + SecondZR);
D = (FirstYR + FirstZR)*(SecondWR - SecondXR);
E = (FirstXR + FirstZR)*(SecondXR + SecondYR);
F = (FirstXR - FirstZR)*(SecondXR - SecondYR);
G = (FirstWR + FirstYR)*(SecondWR - SecondZR);
H = (FirstWR - FirstYR)*(SecondWR + SecondZR);

WR = B + (-E - F + G + H) / 2
XR = A - ( E + F + G + H) / 2
YR = C + ( E - F + G - H) / 2
ZY = D + ( E - F - G + H) / 2

맞다, 복잡해 보인다, 복잡하다, 하지만 괜찮은 계산기(또는 기본 프로그래밍 지식)로 당신은 자동화 할 수 있고 공식을 다시 보지 않아도 된다.

우리가 X축에 객체를 90도 회전하기 원한다고 하자(옆으로 기울이기 위해), 그리고 수평 원으로 회전하자. 당신은 우리가 Z 축으로(수평 원을 만들기 위해) 객체를 회전했던거에서 정보를 사용할 것이라고 생각할 수 있다, 하지만 X 축 여기서 회전됐기 때문에, Z 축은 더이상 수직 축이 아니다.
우선, 우리는 X축 회전을 해야만 한다, 그리고 이제 수직 축이기 때문에, Y축에 대해 원을 만들어야 한다:

Code:

Rotation 4 {
Linear, //Linear Interpolation works fine for rotations
GlobalSeqId 0,//Only global sequence there is
  0: {  0.70710678,  0.00000000,  0.00000000,  0.70710678 },
1000: {  0.35355339,  0.61237244,  0.61237244,  0.35355339 },
2000: { -0.35355339,  0.61237244,  0.61237244, -0.35355339 },
3000: { -0.70710678,  0.00000000,  0.00000000, -0.70710678 },
}

숫자가 얼마나 심상치 않은지 봐라:쿼터니언은 삼각법과 제곱근을 사용한다는(축 벡터의 노멀라이징 동안) 사실 때문에 괜찮은 숫자들을 절대 산출하지 않는다.
__________________