임의의 축 <A>는 $X , Y ,Z$ 에 대한 요소를 가지고 있습니다.
$<A>$ 의 $X,Y,Z$ 요소 중 나머지 두 요소를 제거하여 하나만 남긴다면 위에서 알아본 회전 변환에 대한 행렬식을 그대로 쓸 수가 있습니다.
그럼 문제는 어떻게 나머지 두 요소를 제거하느냐의 문제가 됩니다.
우리는 $Z$ 요소만을 남기고 나머지 두 개의 요소를 제거하도록 하겠습니다.
$<A>$ 에서 $X , Y$ 요소를 제거하려면 $<A>$ 을 회전을 시켜 $Z$ 축에 일치시키면 $X ,Y$ 두 요소가 사라질 것입니다.
일단 $<A>$ 을 $Y-Z$ 평면상에 내린 후에 $Z$축과의 각을 $\alpha$ 라고 하고,
$X$축을 $\alpha$ 만큼 회전을 시키면 축 <A>는 $X-Z$평면상에 놓이게 되고, 다시 여기에서 $Z$축과의 각을 $\beta$ 라고 하자. 그리고 $Y$축을 $\beta$만큼 회전을 시키면 축 <A>는 $Z$축과 동일하게 됩니다.
이제 $Z$축을 원하는 각도만큼 회전을 시킨 후에 앞의 순서를 거꾸로 하면 원래의 위치에 원하는 각도만큼 회전되어 놓이게 됩니다.
여기에서 우리가 구해야 할 변수는 $\alpha,\beta$ 입니다.
먼저 $\alpha$을 구하기 위해 <A>축을 $Y-Z$평면 상에 내린 후에, $$ d=\sqrt{(c^2_y + c^2_z)}\\ cos(\alpha)=\frac{c_z}{d},sin(\alpha)=\frac{c_y}{d} $$ 을 사용해서 $\alpha$을 구할 수가 있습니다.
여기서 $C_x,C_y,C_z$는 축 <A>의 방향 코사인입니다.
$beta$는,
$$ cos(\beta)=d,sin(\beta)=c_x $$ 을 사용해서 구할 수가 있습니다.
이렇게 해서 $\alpha,\beta$을 구해서 축 <A>을 $X$축에 대하여 $\alpha$만큼, $Y$축에 대하여 $beta$만큼 회전을 시키면 $Z$축과 일치하게 됩니다.
<A>을 $Z$축에 일치시킨 후에 $Z$축을 원하는 각도만큼(여기서는 $\theta$라고 하자.)회전을 하면 됩니다.
$<A>$ 의 $X,Y,Z$ 요소 중 나머지 두 요소를 제거하여 하나만 남긴다면 위에서 알아본 회전 변환에 대한 행렬식을 그대로 쓸 수가 있습니다.
그럼 문제는 어떻게 나머지 두 요소를 제거하느냐의 문제가 됩니다.
우리는 $Z$ 요소만을 남기고 나머지 두 개의 요소를 제거하도록 하겠습니다.
$<A>$ 에서 $X , Y$ 요소를 제거하려면 $<A>$ 을 회전을 시켜 $Z$ 축에 일치시키면 $X ,Y$ 두 요소가 사라질 것입니다.
일단 $<A>$ 을 $Y-Z$ 평면상에 내린 후에 $Z$축과의 각을 $\alpha$ 라고 하고,
$X$축을 $\alpha$ 만큼 회전을 시키면 축 <A>는 $X-Z$평면상에 놓이게 되고, 다시 여기에서 $Z$축과의 각을 $\beta$ 라고 하자. 그리고 $Y$축을 $\beta$만큼 회전을 시키면 축 <A>는 $Z$축과 동일하게 됩니다.
이제 $Z$축을 원하는 각도만큼 회전을 시킨 후에 앞의 순서를 거꾸로 하면 원래의 위치에 원하는 각도만큼 회전되어 놓이게 됩니다.
여기에서 우리가 구해야 할 변수는 $\alpha,\beta$ 입니다.
먼저 $\alpha$을 구하기 위해 <A>축을 $Y-Z$평면 상에 내린 후에, $$ d=\sqrt{(c^2_y + c^2_z)}\\ cos(\alpha)=\frac{c_z}{d},sin(\alpha)=\frac{c_y}{d} $$ 을 사용해서 $\alpha$을 구할 수가 있습니다.
여기서 $C_x,C_y,C_z$는 축 <A>의 방향 코사인입니다.
$beta$는,
$$ cos(\beta)=d,sin(\beta)=c_x $$ 을 사용해서 구할 수가 있습니다.
이렇게 해서 $\alpha,\beta$을 구해서 축 <A>을 $X$축에 대하여 $\alpha$만큼, $Y$축에 대하여 $beta$만큼 회전을 시키면 $Z$축과 일치하게 됩니다.
<A>을 $Z$축에 일치시킨 후에 $Z$축을 원하는 각도만큼(여기서는 $\theta$라고 하자.)회전을 하면 됩니다.
CIsVect3d::GetAngleToZAxis(double &alpha, double &beta) const
{
CIsVect2d vec1(m_dy , m_dz);
CIsVect2d vec2(0 , 1);
try
{
alpha = 0;
vec1.Normalize();
alpha = acos(vec1.DotProduct(vec2));
double cross = vec1 * vec2;
if(cross < 0) alpha = -alpha;
}
catch(...)
{
}
const double d = sqrt(m_dy * m_dy + m_dz * m_dz);
vec1.Set(m_dx , d);
try
{
beta = 0;
vec1.Normalize();
beta = acos(vec1.DotProduct(vec2));
double cross = vec2 * vec1; // reverse cross product
if(cross < 0) beta = -beta;
}
catch(...)
{
}
}
댓글
댓글 쓰기