自动循环离开主图

自动循环离开主图
\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{graphs,graphs.standard}

\usepackage{etoolbox}

\begin{document}
%\begin{tikzpicture}
%  \graph[nodes={draw, circle}] { subgraph K_n [n=6,clockwise,radius=2cm] };
%\end{tikzpicture}

%\begin{tikzpicture}
%  \graph[nodes={draw, circle}, clique, n=6, clockwise, radius=2cm]
%  {
%    $X_1$, $X_2$, $X_3$, $X_4$, $X_5$, $X_6$;
%  };
%\end{tikzpicture}

\begin{tikzpicture}[transform shape]
  \foreach \x in {1,...,6}{%
    \pgfmathparse{(\x-1)*360/6 + 90}
    \ifboolexpr{test {\ifnumcomp{\x}{=}{1}}}
    {\node[draw=cyan, circle, inner sep=0.15cm] (N-\x) at (\pgfmathresult:2cm) {$X_{\x}$};}
    {\node[draw, circle,inner sep=0.15cm] (N-\x) at (\pgfmathresult:2cm) {$X_{\x}$};}
  } 
  \foreach \x [count=\xi from 1] in {1,...,6}{%
    \foreach \y in {\x,...,6}{%
      \ifboolexpr{test {\ifnumcomp{\x}{=}{1}}}
      {
            \ifboolexpr{test {\ifnumcomp{\y}{=}{1}}}
            {\path (N-\x) edge[loop above, draw=cyan, ->] (N-\y);}
                {
            \path (N-\x) edge[draw, bend right=5, ->] (N-\y);
            \path (N-\x) edge[draw=cyan, bend left=5, <-] (N-\y);
        }
      }
      {
            \ifboolexpr{test {\ifnumcomp{\y}{=}{\x}}}
            {\path (N-\x) edge[loop above, ->] (N-\y);}
        {
            \path (N-\x) edge[bend right=5, ->] (N-\y);
            \path (N-\x) edge[bend left=5, <-] (N-\y);
        }
    }   
  }
}
\end{tikzpicture}

\end{document}

在此处输入图片描述

有没有办法可以自动设置“loop [left, right]”命令,使得 X2、X3 节点向左循环,X6、X5 节点向右循环,X4 节点向下循环?无需大量的 for 循环?

答案1

我们可以查找循环的定义tikzlibrarytopaths.code.tex。例如,

\tikzset{loop above/.style={above,out=105,in=75,loop}}

以 90 度角离开的循环。这意味着,任意角度的离开,\myangle我们需要类似的东西

(<node>) edge[out=\myangle+15,in=\myangle-15,looseness=8] (<node>)

由于您已经掌握了角度,因此您可以使用

\documentclass{article}
\usepackage{tikz}
\usepackage{etoolbox}

\begin{document}
\begin{tikzpicture}[transform shape]
  \foreach \x in {1,...,6}{%
    \pgfmathsetmacro{\myangle}{(\x-1)*360/6 + 90}
    \ifboolexpr{test {\ifnumcomp{\x}{=}{1}}}
    {\node[draw=cyan, circle, inner sep=0.15cm] (N-\x) at (\myangle:2cm) {$X_{\x}$};}
    {\node[draw, circle,inner sep=0.15cm] (N-\x) at (\myangle:2cm) {$X_{\x}$};}
  } 
  \foreach \x [count=\xi from 1] in {1,...,6}{%
    \pgfmathsetmacro{\myangle}{(\x-1)*360/6 + 90}
    \foreach \y in {\x,...,6}{%
      \ifboolexpr{test {\ifnumcomp{\x}{=}{1}}}
      {
            \ifboolexpr{test {\ifnumcomp{\y}{=}{1}}}
            {\path (N-\x) edge[draw=cyan,out=\myangle+15,in=\myangle-15,looseness=8,->] (N-\x);}
                {
            \path (N-\x) edge[draw, bend right=5, ->] (N-\y);
            \path (N-\x) edge[draw=cyan, bend left=5, <-] (N-\y);
        }
      }
      {
            \ifboolexpr{test {\ifnumcomp{\y}{=}{\x}}}
            {\path (N-\x) edge[out=\myangle+15,in=\myangle-15,looseness=8,->] (N-\x);}
        {
            \path (N-\x) edge[bend right=5, ->] (N-\y);
            \path (N-\x) edge[bend left=5, <-] (N-\y);
        }
    }   
  }
}
\end{tikzpicture}

\end{document}

在此处输入图片描述

或者我们可以为此定义一种风格。

\documentclass{article}
\usepackage{tikz}
\usepackage{etoolbox}

\begin{document}
\begin{tikzpicture}[angle loop/.style={out=#1+15,in=#1-15,looseness=8,loop}]
  \foreach \x in {1,...,6}{%
    \pgfmathsetmacro{\myangle}{(\x-1)*360/6 + 90}
    \ifboolexpr{test {\ifnumcomp{\x}{=}{1}}}
    {\node[draw=cyan, circle, inner sep=0.15cm] (N-\x) at (\myangle:2cm) {$X_{\x}$};}
    {\node[draw, circle,inner sep=0.15cm] (N-\x) at (\myangle:2cm) {$X_{\x}$};}
  } 
  \foreach \x [count=\xi from 1] in {1,...,6}{%
    \pgfmathsetmacro{\myangle}{(\x-1)*360/6 + 90}
    \foreach \y in {\x,...,6}{%
      \ifboolexpr{test {\ifnumcomp{\x}{=}{1}}}
      {
            \ifboolexpr{test {\ifnumcomp{\y}{=}{1}}}
            {\path (N-\x) edge[draw=cyan,angle loop=\myangle,->] (N-\x);}
                {
            \path (N-\x) edge[draw, bend right=5, ->] (N-\y);
            \path (N-\x) edge[draw=cyan, bend left=5, <-] (N-\y);
        }
      }
      {
            \ifboolexpr{test {\ifnumcomp{\y}{=}{\x}}}
            {\path (N-\x) edge[angle loop=\myangle,->] (N-\x);}
        {
            \path (N-\x) edge[bend right=5, ->] (N-\y);
            \path (N-\x) edge[bend left=5, <-] (N-\y);
        }
    }   
  }
}
\end{tikzpicture}

\end{document}

也可以使用\ifnum和弯曲箭头,特别是让 TiZ 找出与calc图书馆的角度。

\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{arrows.meta,bending,calc}
\begin{document}
\begin{tikzpicture}[angle loop/.style={out=#1+15,in=#1-15,looseness=8,loop},
    >={Stealth[bend]}]
  \foreach \x in {1,...,6}{%
    \pgfmathsetmacro{\myangle}{(\x-1)*360/6 + 90}
    \ifnum\x=1
     \node[draw=cyan, circle, inner sep=0.15cm] (N-\x) at (\myangle:2cm) {$X_{\x}$};
    \else
     \node[draw, circle,inner sep=0.15cm] (N-\x) at (\myangle:2cm) {$X_{\x}$};
    \fi 
  } 
  \foreach \X  in {1,...,6}{%
    \foreach \Y in {\X,...,6}{%
      \ifnum\X=1
       \ifnum\Y=1
        \path let \p1=(N-\X),\n1={atan2(\y1,\x1)} in
         (N-\X) edge[draw=cyan,angle loop=\n1,->] (N-\X);
       \else
            \path (N-\X) edge[draw, bend right=5, ->] (N-\Y);
            \path (N-\X) edge[draw=cyan, bend left=5, <-] (N-\Y);
       \fi
      \else
       \ifnum\Y=\X
        \path let \p1=(N-\X),\n1={atan2(\y1,\x1)} in 
        (N-\X) edge[angle loop=\n1,->] (N-\X);
       \else    
        \path (N-\X) edge[bend right=5, ->] (N-\Y);
        \path (N-\X) edge[bend left=5, <-] (N-\Y);
       \fi
      \fi   
  }
}
\end{tikzpicture}
\end{document}

在此处输入图片描述

或者

\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{arrows.meta,bending,calc}
\begin{document}
\begin{tikzpicture}[angle loop/.style={out=#1+15,in=#1-15,looseness=8,loop},
    >={Stealth[bend]}]
  \foreach \X in {1,...,6}{%
    \pgfmathsetmacro{\myangle}{(\X-1)*360/6 + 90}
    \ifnum\X=1
     \node[draw=cyan, circle, inner sep=0.15cm] (N-\X) at (\myangle:2cm) {$X_{\X}$};
     \path (N-\X) edge[draw=cyan,angle loop=\myangle,->] (N-\X) ;
    \else
     \node[draw, circle,inner sep=0.15cm] (N-\X) at (\myangle:2cm) {$X_{\X}$};
     \path (N-\X) edge[angle loop=\myangle,->] (N-\X) ;
    \fi 
    \ifnum\X>1
    \foreach \Y in {1,...,\the\numexpr\X-1}{%
        \path (N-\Y) edge[bend right=5, ->] (N-\X);
       \ifnum\Y=1
        \path (N-\Y) edge[cyan,bend left=5, <-] (N-\X);
       \else    
        \path (N-\Y) edge[bend left=5, <-] (N-\X);
       \fi}
    \fi   
  }
\end{tikzpicture}
\end{document}

答案2

这是我的尝试。(我认为它更整洁。)

\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{graphs, graphs.standard}

\usepackage{etoolbox}

\tikzset{
  angle loop/.style={out=#1+15, in=#1-15, loop},
  node num/.code={\ifnum#1=1 \pgfkeysalso{draw=cyan}\fi}
}

\begin{document}
\begin{tikzpicture}[transform shape, inner sep=0.15cm, bend angle=5]
  \foreach \x/\i in {1/90, 2/180, 3/180, 4/270, 5/0, 6/0} {
    % draw node "X_\x"
    \node[draw, node num=\x, circle] (N-\x) at (\x*60+30:2cm) {$X_{\x}$};

    \foreach \y in {1, ..., \x} {
      \ifnum\x=\y
        % draw loop edge
        \path (N-\x) edge[node num=\x, angle loop=\i] (N-\y);
      \else
        % draw non-loop edges
        \path (N-\x) edge[node num=\y, bend right, ->] (N-\y)
                     edge[bend left, <-] (N-\y);
      \fi
    }
  }
\end{tikzpicture}
\end{document}

在此处输入图片描述

相关内容