在 TikZ 3D 中正确绘制单位法线(方向和长度)

在 TikZ 3D 中正确绘制单位法线(方向和长度)

我想将 3D 中的某些点与连接三角形和这些三角形的单位法线(点之间的差异向量的交叉积)以及法线的平均单位法线(n_i)一起可视化。

我到目前为止所做的工作可以在这个 MWE 中看到。它有点黑客,看起来“不正确”。后者似乎是由以下原因造成的:

  1. 我不确定法线是否朝向正确的方向。
  2. 我很确定法线的长度不正确(它们在 2D 中长度相同,但在 3D 中长度不同)。

此外,直角和指示的差异向量之间存在差距。任何帮助都非常感谢!顺便说一句。我试过了答案在这篇文章中但没有看到改善。

\documentclass{article}
\usepackage[utf8]{inputenc}
\usepackage{graphicx}
\usepackage{amsmath}
\usepackage{tikz}
\usepackage{tikz-3dplot}
\usetikzlibrary{intersections}
\usepackage{tkz-euclide}
\usetkzobj{all}
\usetikzlibrary{angles}

\begin{document}

\newcommand{\RightAngle}[4][blue]{%
  \draw[#1] ($#3!0.15cm!#2$)
  --($ #3!2!($($#3!0.15cm!#2$)!.5!($#3!0.15cm!#4$)$) $)
  --($#3!0.15cm!#4$) ;
}

\begin{center}
  \definecolor{vis_pab}{RGB}{0,0,255}
  \definecolor{vis_pbc}{RGB}{0,150,0}
  \definecolor{vis_pda}{RGB}{255,0,0}
  \definecolor{vis_pcd}{RGB}{255,165,0}
  \definecolor{vis_highlight}{RGB}{0,0,0}

  \tdplotsetmaincoords{70}{130}
  \begin{tikzpicture}[>=stealth,shorten >=1pt,tdplot_main_coords, scale=1.2]

    \pgfmathsetmacro{\Px}{ 0.0}; \pgfmathsetmacro{\Py}{-0.1}; \pgfmathsetmacro{\Pz}{ 0.25};
    \pgfmathsetmacro{\Ax}{ 2.0}; \pgfmathsetmacro{\Ay}{ 2.3}; \pgfmathsetmacro{\Az}{ 0.0};
    \pgfmathsetmacro{\Bx}{-1.5}; \pgfmathsetmacro{\By}{ 1.35}; \pgfmathsetmacro{\Bz}{-0.95};
    \pgfmathsetmacro{\Cx}{-2.0}; \pgfmathsetmacro{\Cy}{-2.5}; \pgfmathsetmacro{\Cz}{ 0.0};
    \pgfmathsetmacro{\Dx}{ 2.0}; \pgfmathsetmacro{\Dy}{-1.0}; \pgfmathsetmacro{\Dz}{ -0.25};
    \coordinate (p) at (\Px, \Py, \Pz);
    \coordinate (a) at (\Ax, \Ay, \Az);
    \coordinate (b) at (\Bx, \By, \Bz);
    \coordinate (c) at (\Cx, \Cy, \Cz);
    \coordinate (d) at (\Dx, \Dy, \Dz);


    \draw[dashed,->] (0,0,0) -- (3,0,0) node[left] {$x$};
    \draw[dashed,->] (0,0,0) -- (0,3,0) node[right] {$y$};
    \draw[dashed,->] (0,0,0) -- (0,0,2) node[above] {$z$};

    \draw[fill=black] (a) circle (2pt) node [below] {$\boldsymbol{a}$};
    \draw[fill=black] (b) circle (2pt) node [right] {$\boldsymbol{b}$};
    \draw[fill=black] (c) circle (2pt) node [above] {$\boldsymbol{c}$};
    \draw[fill=black] (d) circle (2pt) node [left] {$\boldsymbol{d}$};

    \fill[fill=vis_pab,opacity=0.1] (p) -- (a) -- (b) -- cycle;
    \fill[fill=vis_pbc,opacity=0.1] (p) -- (b) -- (c) -- cycle;
    \fill[fill=vis_pcd,opacity=0.1] (p) -- (c) -- (d) -- cycle;
    \fill[fill=vis_pda,opacity=0.1] (p) -- (d) -- (a) -- cycle;

    \draw (a) -- (b) -- (c) -- (d) -- (a) -- cycle;
    \draw (p) -- (a);
    \draw (p) -- (b);
    \draw (p) -- (c);
    \draw (p) -- (d);

    \draw[vis_highlight,fill=vis_highlight] (p) circle (2pt) node [below right] {$\boldsymbol{p}_i$};

    \coordinate (N1) at (barycentric cs:a=1,b=1,p=1);
    \coordinate (N2) at (barycentric cs:b=1,c=1,p=1);
    \coordinate (N3) at (barycentric cs:c=1,d=1,p=1);
    \coordinate (N4) at (barycentric cs:d=1,a=1,p=1);

    \fill[fill=vis_pab] (N1) circle (1pt);
    \fill[fill=vis_pbc] (N2) circle (1pt);
    \fill[fill=vis_pcd] (N3) circle (1pt);
    \fill[fill=vis_pda] (N4) circle (1pt);

    \pgfmathsetmacro{\PAx}{\Ax-\Px};
    \pgfmathsetmacro{\PAy}{\Ay-\Py};
    \pgfmathsetmacro{\PAz}{\Az-\Pz};
    \pgfmathsetmacro{\PBx}{\Bx-\Px};
    \pgfmathsetmacro{\PBy}{\By-\Py};
    \pgfmathsetmacro{\PBz}{\Bz-\Pz};
    \pgfmathsetmacro{\PCx}{\Cx-\Px};
    \pgfmathsetmacro{\PCy}{\Cy-\Py};
    \pgfmathsetmacro{\PCz}{\Cz-\Pz};
    \pgfmathsetmacro{\PDx}{\Dx-\Px};
    \pgfmathsetmacro{\PDy}{\Dy-\Py};
    \pgfmathsetmacro{\PDz}{\Dz-\Pz};
    \tdplotcrossprod(\PAx,\PAy,\PAz)(\PBx,\PBy,\PBz);
    \coordinate (NE1) at (\tdplotresx, \tdplotresy, \tdplotresz);
    \draw[dashed,draw=vis_pab] (N1) -- ($(N1)!1.75cm!(NE1)$);
    \draw[thick,draw=vis_pab,->] (N1) -- ($(N1)!1cm!(NE1)$);
    \coordinate (N1_support_a) at ($(N1) - (p) + (a)$);
    \draw[draw=vis_pab] (N1) -- ($(N1)!0.3cm!(N1_support_a)$);
    \coordinate (N1_support_b) at ($(N1) - (p) + (b)$);
    \draw[draw=vis_pab] (N1) -- ($(N1)!0.3cm!(N1_support_b)$);
    \RightAngle[draw=vis_pab]{(NE1)}{(N1)}{(N1_support_a)};
    \RightAngle[draw=vis_pab]{(NE1)}{(N1)}{(N1_support_b)};

    \tdplotcrossprod(\PBx,\PBy,\PBz)(\PCx,\PCy,\PCz);
    \coordinate (NE2) at (\tdplotresx, \tdplotresy, \tdplotresz);
    \draw[dashed,draw=vis_pbc>] (N2) -- ($(N2)!1.75cm!(NE2)$);
    \draw[thick,draw=vis_pbc,->] (N2) -- ($(N2)!1cm!(NE2)$);
    \coordinate (N2_support_b) at ($(N2) - (p) + (b)$);
    \draw[draw=vis_pbc] (N2) -- ($(N2)!0.3cm!(N2_support_b)$);
    \coordinate (N2_support_c) at ($(N2) - (p) + (c)$);
    \draw[draw=vis_pbc] (N2) -- ($(N2)!0.3cm!(N2_support_c)$);
    \RightAngle[draw=vis_pbc]{(NE2)}{(N2)}{(N2_support_b)};
    \RightAngle[draw=vis_pbc]{(NE2)}{(N2)}{(N2_support_c)};

    \tdplotcrossprod(\PCx,\PCy,\PCz)(\PDx,\PDy,\PDz);
    \coordinate (NE3) at (\tdplotresx, \tdplotresy, \tdplotresz);
    \draw[dashed,draw=vis_pcd] (N3) -- ($(N3)!1.75cm!(NE3)$);
    \draw[thick,draw=vis_pcd,->] (N3) -- ($(N3)!1cm!(NE3)$);
    \coordinate (N3_support_c) at ($(N3) - (p) + (c)$);
    \draw[draw=vis_pcd] (N3) -- ($(N3)!0.3cm!(N3_support_c)$);
    \coordinate (N3_support_d) at ($(N3) - (p) + (d)$);
    \draw[draw=vis_pcd] (N3) -- ($(N3)!0.3cm!(N3_support_d)$);
    \RightAngle[draw=vis_pcd]{(NE3)}{(N3)}{(N3_support_c)};
    \RightAngle[draw=vis_pcd]{(NE3)}{(N3)}{(N3_support_d)};

    \tdplotcrossprod(\PDx,\PDy,\PDz)(\PAx,\PAy,\PAz);
    \coordinate (NE4) at (\tdplotresx, \tdplotresy, \tdplotresz);
    \draw[dashed,draw=vis_pda] (N4) -- ($(N4)!1.75cm!(NE4)$);
    \draw[thick,draw=vis_pda,->] (N4) -- ($(N4)!1cm!(NE4)$);
    \coordinate (N4_support_d) at ($(N4) - (p) + (d)$);
    \draw[draw=vis_pda] (N4) -- ($(N4)!0.3cm!(N4_support_d)$);
    \coordinate (N4_support_a) at ($(N4) - (p) + (a)$);
    \draw[draw=vis_pda] (N4) -- ($(N4)!0.3cm!(N4_support_a)$);
    \RightAngle[draw=vis_pda]{(NE4)}{(N4)}{(N4_support_d)};
    \RightAngle[draw=vis_pda]{(NE4)}{(N4)}{(N4_support_a)};

    \coordinate (NP) at (barycentric cs:NE1=1,NE2=1,NE3=1,NE4=1);
    \draw[ultra thick,vis_highlight,->,>=stealth] (p) -- ($(p)!1cm!(NP)$) node [vis_highlight,near end,right] {$\boldsymbol{n}_i$};

  \end{tikzpicture}
\end{center}

\end{document}

现在的结果

答案1

叉积的结果以相对于原点的向量形式给出,但您希望它相对于(N1)原点绘制。计算单位向量很简单。

\pgfmathsetmacro{\s}{1/sqrt(\tdplotresx*\tdplotresx + \tdplotresy*\tdplotresy + \tdplotresz*\tdplotresz)}
\coordinate (NE1) at ($(N1)+(\s*\tdplotresx, \s*\tdplotresy, \s*\tdplotresz)$);
\draw[thick,draw=vis_pab,->] (N1) -- (NE1);

当你处理其他法线向量时你可以重复使用 \s。

\newcommand{\RightAngle}[4][blue]{%
  \draw[#1] #3 -- ($#3!0.15cm!#2$)
  --($($#3!0.3cm!#2$)!.5!($#3!0.3cm!#4$)$)
  --($#3!0.15cm!#4$) -- cycle;
}

将消除差距。

法向量

相关内容