Куб в TikZ нарисован неправильно — возможно, это ошибка в TikZ?

Куб в TikZ нарисован неправильно — возможно, это ошибка в TikZ?

У меня есть простой куб в трехмерном пространстве, четыре грани которого нарисованы красным цветом, а верх и низ — зеленым.

 \documentclass[border=5,tikz]{standalone}

 \usepackage{tikz-3dplot}

 \begin{document}
 \foreach\s in{2,4,...,360}{
     \tdplotsetmaincoords{2.71828+\s}{2.71828+\s*2}
     \tikz[tdplot_main_coords,scale=.1]{
         \path(-15cm,-15cm)(15cm,15cm);
         \draw[ultra thick, color=black, fill=green!80!black]
             (0,0,0)--(20,0,0)--(20,20,0)--(0,20,0)--cycle        % bottom
             (0,0,20)--(20,0,20)--(20,20,20)--(0,20,20)--cycle;   % top
         \draw[ultra thick, color=black, fill=red!80!black]
             (0,0,0)--(20,0,0)--(20,0,20)--(0,0,20)--cycle
             (0,20,0)--(20,20,0)--(20,20,20)--(0,20,20)--cycle
             (0,0,0)--(0,20,0)--(0,20,20)--(0,0,20)--cycle
             (20,0,0)--(20,20,0)--(20,20,20)--(20,0,20)--cycle;
     }
 }

 \end{document}

которые, если смотреть с определенных углов в TikZ, показывают неожиданную проекцию. Кажется, что когда определенные лица накладываются друг на друга — они становятся прозрачными!

введите описание изображения здесь

Это ошибка или что-то не так с конструкцией куба?

решение1

Поскольку каждый прямоугольник заполняется независимо, ни один из них не рассматривается как отверстие. Для твердого тела нужно рисовать грани от дальнего к ближнему или назначить нормальный вектор и рисовать только грани, указывающие в этом направлении.

математика здесь

\documentclass[border=5,tikz]{standalone}

% Uses \nearx, \neary and \nearz
% #1=x, #2=y, #3=z, #4={code to be executed}
\def\ifnear(#1,#2,#3)#4 
  {\pgfmathparse{#1*\nearx+#2*\neary+#3*\nearz}%
  \ifdim\pgfmathresult pt>0pt\relax #4\fi}

 \usepackage{tikz-3dplot}

 \begin{document}
 \foreach\s in{2,4,...,360}{
   \pgfmathsetmacro{\aTheta}{2.71828+\s}
   \pgfmathsetmacro{\aPhi}{2.71828+\s*2}
   \pgfmathsetmacro{\nearx}{sin(\aPhi)*sin(\aTheta)}
   \pgfmathsetmacro{\neary}{-cos(\aPhi)*sin(\aTheta)}
   \pgfmathsetmacro{\nearz}{cos(\aTheta)}
   \begin{tikzpicture}[scale=.1]
     \path(-15cm,-15cm)(15cm,15cm);
     \tdplotsetmaincoords{\aTheta}{\aPhi}
     \begin{scope}[tdplot_main_coords]
       \ifnear(0,0,-1){\draw[fill=green!80!black]
             (0,0,0)--(20,0,0)--(20,20,0)--(0,20,0)--cycle;}       % bottom
       \ifnear(0,0,1){\draw[fill=green!80!black]
             (0,0,20)--(20,0,20)--(20,20,20)--(0,20,20)--cycle;}   % top
       \ifnear(0,-1,0){\draw[fill=red!80!black]
             (0,0,0)--(20,0,0)--(20,0,20)--(0,0,20)--cycle;}
       \ifnear(0,1,0){\draw[fill=red!80!black]
             (0,20,0)--(20,20,0)--(20,20,20)--(0,20,20)--cycle;}
       \ifnear(-1,0,0){\draw[fill=red!80!black]
             (0,0,0)--(0,20,0)--(0,20,20)--(0,0,20)--cycle;}
       \ifnear(1,0,0){\draw[fill=red!80!black]
             (20,0,0)--(20,20,0)--(20,20,20)--(20,0,20)--cycle;}
     \end{scope}
   \end{tikzpicture}
 }

 \end{document}

Если поменять знаки местами \nearx, \nearyто \nearzполучится другая сторона куба.

Нормальный вектор — это линия, перпендикулярная грани и (для наших целей) направленная от центра. Для правильных многогранников можно использовать вектор из центра объекта к центру грани.

Центр куба находится в точке (10,10,10). Поскольку центр нижней грани находится в точке (10,10,0), (нормализованный) вектор нормали для этой грани равен (0,0,-1).

Связанный контент