Tikz:: 3D에서 이동 및 회전?

Tikz:: 3D에서 이동 및 회전?

아래와 같이 2D 공간에서 수행할 수 있는 것과 유사한 방식 으로 정의된 객체를 3D 공간에서 변환 (Tx,Ty,Tz)하고 회전 하고 싶습니다 .(roll,pitch,yaw)scope

\begin{scope}[shift={(7,9)},rotate=30]
% draw some object
\end{scope}

3D 회전 및 변환을 위한 간단한 방법이 있습니까?

답변1

여기에 해결책이 있지만 (지금까지는) 번역에만 해당됩니다. 내부적으로 TikZ3D 포인트를 2D 포인트로 처리한다는 사실을 사용합니다 . 따라서 3D 이동 벡터는 mytranslation2D 점인 좌표에 저장되어 에 전달될 수 있습니다 shift. 두꺼운 선은 번역이 올바르게 완료되었음을 보여주기 위한 것입니다.

\documentclass{standalone}
\usepackage{tikz}

\newcommand{\translatepoint}[1]%
{   \coordinate (mytranslation) at (#1);
}

\newcommand{\somedrawing}%
{   \coordinate (a) at (0,0,0);
    \coordinate (b) at (5,1,0);
    \coordinate (c) at (2,4,0);
    \coordinate (d) at (1,-1,-4);
    \draw (a) -- (b) (a) -- (c) (a) -- (d) (b) -- (c) (b) -- (d) (c) -- (d);
}

\begin{document}

\begin{tikzpicture}[x={(0.866cm,0.5cm)},y={(-0.866cm,0.5cm)},z={(0cm,1cm)}]
    \somedrawing    

    \translatepoint{5,0,0}
    \draw[very thick,red] (0,0,0) -- (5,0,0);
    \begin{scope}[shift=(mytranslation),draw=red]
        \somedrawing
    \end{scope}

    \translatepoint{0,6,0}
    \draw[very thick,blue] (0,0,0) -- (0,6,0);
    \begin{scope}[shift=(mytranslation),draw=blue]
        \somedrawing
    \end{scope}

    \translatepoint{0,0,8}
    \draw[very thick,green!50!gray] (0,0,0) -- (0,0,8);
    \begin{scope}[shift=(mytranslation),draw=green!50!gray]
        \somedrawing
    \end{scope}

    \translatepoint{-5,0,-2}
    \draw[very thick,orange] (0,0,0) -- (-5,0,-2);
    \begin{scope}[shift=(mytranslation),draw=orange]
        \somedrawing
    \end{scope}
\end{tikzpicture}

\end{document}

여기에 이미지 설명을 입력하세요


편집 1:드디어 로테이션에 성공했는데, 그건 개소리였어. 나는 먼저 RPY 회전에 대한 수학적 기초를 마련했습니다.정말 좋아행렬. 그러다가 아이디어를 빌렸어요앤드류 스테이시~에서이 질문: (데카르트) 단위 벡터가 를 통해 가리키는 위치를 알아냅니다 \pgfgetlastxy. 그런 다음 Tikz표기법 으로 행렬을 작성하고 \pgfgetlastxy다시 한 번 사용하면 됩니다!

\documentclass[parskip]{scrartcl}
\usepackage[margin=15mm]{geometry}
\usepackage{tikz}
\usetikzlibrary{arrows}
\usepackage{amsmath}

\newcommand{\rotateRPY}[3]% roll, pitch, yaw
{   \pgfmathsetmacro{\rollangle}{#1}
    \pgfmathsetmacro{\pitchangle}{#2}
    \pgfmathsetmacro{\yawangle}{#3}

    % to what vector is the x unit vector transformed, and which 2D vector is this?
    \pgfmathsetmacro{\newxx}{cos(\yawangle)*cos(\pitchangle)}
    \pgfmathsetmacro{\newxy}{sin(\yawangle)*cos(\pitchangle)}
    \pgfmathsetmacro{\newxz}{-sin(\pitchangle)}
    \path (\newxx,\newxy,\newxz);
    \pgfgetlastxy{\nxx}{\nxy};

    % to what vector is the y unit vector transformed, and which 2D vector is this?
    \pgfmathsetmacro{\newyx}{cos(\yawangle)*sin(\pitchangle)*sin(\rollangle)-sin(\yawangle)*cos(\rollangle)}
    \pgfmathsetmacro{\newyy}{sin(\yawangle)*sin(\pitchangle)*sin(\rollangle)+ cos(\yawangle)*cos(\rollangle)}
    \pgfmathsetmacro{\newyz}{cos(\pitchangle)*sin(\rollangle)}
    \path (\newyx,\newyy,\newyz);
    \pgfgetlastxy{\nyx}{\nyy};

    % to what vector is the z unit vector transformed, and which 2D vector is this?
    \pgfmathsetmacro{\newzx}{cos(\yawangle)*sin(\pitchangle)*cos(\rollangle)+ sin(\yawangle)*sin(\rollangle)}
    \pgfmathsetmacro{\newzy}{sin(\yawangle)*sin(\pitchangle)*cos(\rollangle)-cos(\yawangle)*sin(\rollangle)}
    \pgfmathsetmacro{\newzz}{cos(\pitchangle)*cos(\rollangle)}
    \path (\newzx,\newzy,\newzz);
    \pgfgetlastxy{\nzx}{\nzy};
}

\tikzset{RPY/.style={x={(\nxx,\nxy)},y={(\nyx,\nyy)},z={(\nzx,\nzy)}}}

\begin{document}

$R=\begin{pmatrix}
    \cos \alpha \cos \beta
&   \textcolor{red}{\cos \alpha \sin \beta \sin \gamma - \sin \alpha \cos \gamma}
&   \cos \alpha \sin \beta \cos \gamma + \sin \alpha \sin \gamma \\
    \textcolor{red}{\sin \alpha \cos \beta}
&   \sin \alpha \sin \beta \sin \gamma + \cos \alpha \cos \gamma
&   \textcolor{red}{\sin \alpha \sin \beta \cos \gamma - \cos \alpha \sin \gamma} \\
    - \sin \beta
&   \textcolor{red}{\cos \beta \sin \gamma}
&   \cos \beta \cos \gamma
\end{pmatrix}\\p'=R\cdot p$

\begin{tikzpicture}
    \draw[-latex] node at (3.5,0,0) {x} (0,0,0) -- (3,0,0);
    \draw[-latex] node at (0,3.5,0) {y} (0,0,0) -- (0,3,0);
    \draw[-latex] node at (0,0,3.5) {z} (0,0,0) -- (0,0,3);

    \rotateRPY{0}{0}{45}
    \begin{scope}[draw=red, text=red,fill=red,densely dashed,RPY]
        \draw[-latex] node at (3.5,0,0) {x} (0,0,0) -- (3,0,0);
        \draw[-latex] node at (0,3.5,0) {y} (0,0,0) -- (0,3,0);
        \draw[-latex] node at (0,0,3.5) {z} (0,0,0) -- (0,0,3);
    \end{scope}
    \node[fill=white,fill opacity=0.7,text opacity=1] {RPY: 0,0,45};
\end{tikzpicture}
\begin{tikzpicture}
    \draw[-latex] node at (3.5,0,0) {x} (0,0,0) -- (3,0,0);
    \draw[-latex] node at (0,3.5,0) {y} (0,0,0) -- (0,3,0);
    \draw[-latex] node at (0,0,3.5) {z} (0,0,0) -- (0,0,3);

    \rotateRPY{0}{30}{0}
    \begin{scope}[draw=red, text=red,fill=red,densely dashed,RPY]
        \draw[-latex] node at (3.5,0,0) {x} (0,0,0) -- (3,0,0);
        \draw[-latex] node at (0,3.5,0) {y} (0,0,0) -- (0,3,0);
        \draw[-latex] node at (0,0,3.5) {z} (0,0,0) -- (0,0,3);
    \end{scope}
    \node[fill=white,fill opacity=0.7,text opacity=1] {RPY: 0,30,0};
\end{tikzpicture}

\begin{tikzpicture}
\draw[-latex] node at (3.5,0,0) {x} (0,0,0) -- (3,0,0);
    \draw[-latex] node at (0,3.5,0) {y} (0,0,0) -- (0,3,0);
    \draw[-latex] node at (0,0,3.5) {z} (0,0,0) -- (0,0,3);

    \rotateRPY{80}{0}{0}
    \begin{scope}[draw=red, text=red,fill=red,densely dashed,RPY]
        \draw[-latex] node at (3.5,0,0) {x} (0,0,0) -- (3,0,0);
        \draw[-latex] node at (0,3.5,0) {y} (0,0,0) -- (0,3,0);
        \draw[-latex] node at (0,0,3.5) {z} (0,0,0) -- (0,0,3);
    \end{scope}
    \node[fill=white,fill opacity=0.7,text opacity=1] {RPY: 80,0,0};
\end{tikzpicture}
\begin{tikzpicture}[x={(0.866cm,-0.5cm)},y={(-0.866cm,-0.5cm)},z={(0cm,1cm)}]
\draw[-latex] node at (3.5,0,0) {x} (0,0,0) -- (3,0,0);
    \draw[-latex] node at (0,3.5,0) {y} (0,0,0) -- (0,3,0);
    \draw[-latex] node at (0,0,3.5) {z} (0,0,0) -- (0,0,3);

    \rotateRPY{13}{171}{55}
    \begin{scope}[draw=red, text=red,fill=red,densely dashed,RPY]
        \draw[-latex] node at (3.5,0,0) {x} (0,0,0) -- (3,0,0);
        \draw[-latex] node at (0,3.5,0) {y} (0,0,0) -- (0,3,0);
        \draw[-latex] node at (0,0,3.5) {z} (0,0,0) -- (0,0,3);
    \end{scope}
    \node[fill=white,fill opacity=0.7,text opacity=1] {RPY: 13,171,55};
\end{tikzpicture}

\end{document}

여기에 이미지 설명을 입력하세요


편집 2:이제 명령에 점을 전달하고 매핑되는 새로운 xyz 좌표를 결정할 수 있습니다. 또한, 다음에서 영감을 받아허버트의 솔루션을 사용하면 이제 큐브와 화살표를 특징으로 하는 더 나은 예가 있습니다.

\documentclass[parskip]{scrartcl}
\usepackage[margin=15mm]{geometry}
\usepackage{tikz}
\usetikzlibrary{arrows,3D}

\newcommand{\savedx}{0}
\newcommand{\savedy}{0}
\newcommand{\savedz}{0}

\newcommand{\somedrawing}%
{   \coordinate (a) at (-2,-2,-2);
    \coordinate (b) at (-2,-2,2);
    \coordinate (c) at (-2,2,-2);
    \coordinate (d) at (-2,2,2);
    \coordinate (e) at (2,-2,-2);
    \coordinate (f) at (2,-2,2);
    \coordinate (g) at (2,2,-2);
    \coordinate (h) at (2,2,2);
    \draw (a)--(b) (a)--(c) (a)--(e) (b)--(d) (b)--(f) (c)--(d) (c)--(g) (d)--(h) (e)--(f) (e)--(g) (f)--(h) (g)--(h);
    \fill (a) circle (0.1cm);
    \fill (d) ++(0.1cm,0.1cm) rectangle ++(-0.2cm,-0.2cm);
}

\newcommand{\rotateRPY}[4][0/0/0]% point to be saved to \savedxyz, roll, pitch, yaw
{   \pgfmathsetmacro{\rollangle}{#2}
    \pgfmathsetmacro{\pitchangle}{#3}
    \pgfmathsetmacro{\yawangle}{#4}

    % to what vector is the x unit vector transformed, and which 2D vector is this?
    \pgfmathsetmacro{\newxx}{cos(\yawangle)*cos(\pitchangle)}% a
    \pgfmathsetmacro{\newxy}{sin(\yawangle)*cos(\pitchangle)}% d
    \pgfmathsetmacro{\newxz}{-sin(\pitchangle)}% g
    \path (\newxx,\newxy,\newxz);
    \pgfgetlastxy{\nxx}{\nxy};

    % to what vector is the y unit vector transformed, and which 2D vector is this?
    \pgfmathsetmacro{\newyx}{cos(\yawangle)*sin(\pitchangle)*sin(\rollangle)-sin(\yawangle)*cos(\rollangle)}% b
    \pgfmathsetmacro{\newyy}{sin(\yawangle)*sin(\pitchangle)*sin(\rollangle)+ cos(\yawangle)*cos(\rollangle)}% e
    \pgfmathsetmacro{\newyz}{cos(\pitchangle)*sin(\rollangle)}% h
    \path (\newyx,\newyy,\newyz);
    \pgfgetlastxy{\nyx}{\nyy};

    % to what vector is the z unit vector transformed, and which 2D vector is this?
    \pgfmathsetmacro{\newzx}{cos(\yawangle)*sin(\pitchangle)*cos(\rollangle)+ sin(\yawangle)*sin(\rollangle)}
    \pgfmathsetmacro{\newzy}{sin(\yawangle)*sin(\pitchangle)*cos(\rollangle)-cos(\yawangle)*sin(\rollangle)}
    \pgfmathsetmacro{\newzz}{cos(\pitchangle)*cos(\rollangle)}
    \path (\newzx,\newzy,\newzz);
    \pgfgetlastxy{\nzx}{\nzy};

    % transform the point given by #1
    \foreach \x/\y/\z in {#1}
    {   \pgfmathsetmacro{\transformedx}{\x*\newxx+\y*\newyx+\z*\newzx}
        \pgfmathsetmacro{\transformedy}{\x*\newxy+\y*\newyy+\z*\newzy}
        \pgfmathsetmacro{\transformedz}{\x*\newxz+\y*\newyz+\z*\newzz}
        \xdef\savedx{\transformedx}
        \xdef\savedy{\transformedy}
        \xdef\savedz{\transformedz}     
    }
}

\tikzset{RPY/.style={x={(\nxx,\nxy)},y={(\nyx,\nyy)},z={(\nzx,\nzy)}}}

\begin{document}

\begin{tikzpicture}
    \somedrawing
    \rotateRPY{0}{0}{101}
    \begin{scope}[draw=red, text=red,fill=red,densely dashed,RPY]
        \somedrawing
    \end{scope}
    \draw[canvas is xy plane at z=2,-latex,thick, blue] (-2,2) arc (135:236:2.828);
    \node[fill=white,fill opacity=0.7,text opacity=1] {RPY: 0,0,101};
\end{tikzpicture}
\begin{tikzpicture}
    \somedrawing    
    \rotateRPY{0}{55}{0}
    \begin{scope}[draw=red, text=red,fill=red,densely dashed,RPY]
        \somedrawing
    \end{scope}
    \draw[canvas is xz plane at y=2,-latex,thick, blue] (-2,2) arc (135:80:2.828);
    \node[fill=white,fill opacity=0.7,text opacity=1] {RPY: 0,55,0};
\end{tikzpicture}

\begin{tikzpicture}
    \somedrawing    
    \rotateRPY{61}{0}{0}
    \begin{scope}[draw=red, text=red,fill=red,densely dashed,RPY]
        \somedrawing
    \end{scope}
    \draw[canvas is yz plane at x=-2,-latex,thick, blue] (2,2) arc (45:106:2.828);
    \node[fill=white,fill opacity=0.7,text opacity=1] {RPY: 71,0,0};
\end{tikzpicture}
\begin{tikzpicture}%[x={(1cm,1cm)},y={(-1cm,1cm)},z={(-2cm,-1cm)}]
    \somedrawing    
    \rotateRPY[-2/2/2]{13}{171}{55}
    \node[fill=white,fill opacity=0.7,text opacity=1,align=left,text=blue] at (5,2)  {-2 $\longrightarrow$ \savedx \\ 2 $\longrightarrow$ \savedy \\ 2 $\longrightarrow$ \savedz};  
    \begin{scope}[draw=red, text=red,fill=red,densely dashed,RPY]
        \somedrawing
    \end{scope}
    \draw[blue,ultra thick] (-2,2,2) -- (\savedx,2,2) -- (\savedx,\savedy,2) -- (\savedx,\savedy,\savedz) circle (0.25);
    \rotateRPY[-2/-2/-2]{13}{171}{55}
    \node[fill=white,fill opacity=0.7,text opacity=1,align=left,text=green!50!gray] at (5,0)  {-2 $\longrightarrow$ \savedx \\ -2 $\longrightarrow$ \savedy \\ -2 $\longrightarrow$ \savedz};
    \draw[green!50!gray,ultra thick] (-2,-2,-2) -- (\savedx,-2,-2) -- (\savedx,\savedy,-2) -- (\savedx,\savedy,\savedz) circle (0.25);
    \node[fill=white,fill opacity=0.7,text opacity=1] {RPY: 13,171,55};
\end{tikzpicture}

\end{document}

여기에 이미지 설명을 입력하세요

답변2

PStricks의 예. 다음으로 실행하세요.xelatex

\documentclass{article}
\pagestyle{empty}
\setlength\parindent{0pt}
\usepackage{pst-solides3d}
\begin{document}
\psset{viewpoint=20 60 20 rtp2xyz,lightsrc=10 15 7,Decran=20}
\begin{pspicture}(-5,-5)(6,5)
\psSolid[object=grille,base=-3 3 -3 3,fillcolor=red!50]
\axesIIID(4,4,3)
\psSolid[object=cube,a=2,ngrid=3,RotX=45,RotY=30,fillcolor=yellow!50](-2,0,0)
\psSolid[object=cube,a=2,ngrid=3,transform={.75 3 .5 scaleOpoint3d}](2,0,1)
\psSolid[object=cube,a=2,ngrid=3,RotZ=30,transform={ 3 -2 0 addv3d },action=draw](-2,0,0)
\end{pspicture}
\end{document}
  • 첫 번째 큐브: x 및 y 축에서 회전합니다((-2,0,0) 에서 상자 중심)
  • 두 번째: x=0.75, y=3, z=0.5로 크기 조정((2,0,1)의 중심)
  • 세 번째: z축으로 회전하고 (3,-2,0)만큼 이동합니다((-2,0,0)의 중심)

여기에 이미지 설명을 입력하세요

관련 정보