如何让节点形成一个完美的圆圈?

如何让节点形成一个完美的圆圈?

这是代码,我可以创建一个菱形或粗略的曲线形状,但我希望节点对齐为圆形。

% Author: Paul Henckel, 2015
% Inspired by: Rasmus Pank Roulund via http://www.texample.net/tikz/examples/borrowers-and-lenders/

\documentclass{minimal}
\usepackage{tikz}
\usetikzlibrary{arrows,positioning} 
\tikzset{
   %Define standard arrow tip
   >=stealth',
   %Define style for boxes
   punkt/.style={
         rectangle,
         rounded corners,
         draw=black, very thick,
         text width=8em,
         minimum height=2em,
         text centered},
   % Define arrow style
   pil/.style={
         ->,
         thick,
         shorten <=2pt,
         shorten >=2pt,}
}

\begin{document}
    \begin{tikzpicture}[node distance=2.5cm, auto]
     %nodes
     \node[punkt] (1food) {1. Food and Waste Identification};
     \node[punkt, above right of=1food] (8disintegration) {8. Disintegration};
        % edge[pil, bend left] (1food.north east);
     \node[punkt, above right of=8disintegration] (7distribution) {7. Distribution of waste};
        % edge[pil, bend left] (8disintegration.north east);
     \node[punkt, above left of=7distribution] (6preservation) {6. Preservation};
        % edge[pil, bend left] (7distribution.north);
     \node[punkt, above left of=6preservation] (5consumption) {5. Consumption};
        % edge[pil, bend left] (6preservation.north);
     \node[punkt, below left of=5consumption] (4preparation) {4. Preparation};
        % edge[pil, bend left] (5consumption.west);
     \node[punkt, below left of=4preparation] (3distribution) {3. Distribution of food};
        % edge[pil, bend left] (4preparation.west);
     \node[punkt, below right of=3distribution] (2production) {2. Production};
        % edge[pil, bend left] (3distribution.south);

    \draw[->] (1food) edge (2production); % Or use edge[bend left] to create curved lines
    \draw[->] (2production) edge (3distribution);
    \draw[->] (3distribution) edge (4preparation);
    \draw[->] (4preparation) edge (5consumption);
    \draw[->] (5consumption) edge (6preservation);
    \draw[->] (6preservation) edge (7distribution);
    \draw[->] (7distribution) edge (8disintegration);
    \draw[->] (8disintegration) edge (1food);

   \end{tikzpicture}
\end{document}

答案1

另一种解决方案是使用基本树,按顺时针方向放置节点。我建议改用圆形节点:它们具有相同的形状和大小,因此除了实用之外,该方案也有点令人愉悦。

我稍微减小了字体大小,但仍然足够大,可以轻松阅读。箭头已使用 来\foreach减少代码行数。

最后,更喜欢使用standalone类而不是minimal。有关更多详细信息,请参阅此问题:为什么要避免使用最小类?

输出

示例图片

代码

\documentclass[margin=10pt]{standalone}
\usepackage{tikz}
\usetikzlibrary{arrows,positioning,trees} 

\tikzset{
    >=stealth',
    punkt/.style={
        circle,
        font=\scriptsize,
        draw, very thick,
        text width=5em,
        inner sep=3pt,
        text centered},
    pil/.style={
        ->,
        thick,
        shorten <=2pt,
        shorten >=2pt,},
    level 1/.style={sibling angle=45, level distance=3.5cm},
    edge from parent/.style= {draw=none},
}

\begin{document}
\begin{tikzpicture}

\coordinate (main) at (0,0) [clockwise from=270]
    child { node[punkt] (1) {1.\\Food and Waste Identification}}
    child { node[punkt] (2) {2.\\Production}}
    child { node[punkt] (3) {3.\\Distribution of food}}
    child { node[punkt] (4) {4.\\Preparation}}
    child { node[punkt] (5) {5.\\Consumption}}
    child { node[punkt] (6) {6.\\Preservation}}
    child { node[punkt] (7) {7.\\Distribution of waste}}
    child { node[punkt] (8) {8.\\Disintegration}}
;

\foreach \x [evaluate=\x as \y using int(\x+1)] in {1,...,8}{
    \ifnum\x<8
        \draw[->] (\x) edge[bend left=10] (\y);
    \else
        \draw[->] (8) edge[bend left=10] (1);
    \fi
}

\end{tikzpicture}
\end{document}

答案2

该方案可以用smartdiagram包轻松绘制。

\documentclass[border=2mm]{standalone}
\usepackage{smartdiagram}
\usetikzlibrary{arrows.meta,bending}

\begin{document}
\smartdiagramset{module shape=circle, text width=1.5cm, font=\scriptsize, circular distance=3.7cm, arrow tip={}}
\smartdiagram[circular diagram:clockwise]{1.\\ Food and Waste Identification, 2.\\ Production, 3.\\ Distribution of food, 4.\\ Preparation, 5.\\ Consumption, 6.\\ Preservation, 7.\\ Distribution of waste, 8.\\ Dis\-integration}
\end{document}

在此处输入图片描述

更新:如何将节点 1 放置到底部。

文档中的第 35 页smartdiagram显示了代码,据circular clockwise diagram我所知,不可能轻易强制某个节点处于特殊位置。代码将节点放置i在列表中的角度位置180+360*i/elements_in_list,因此第一个节点始终是西边节点之后的顺时针第一个节点。

我不知道如何改变这种行为,除非在序言中包含并修改整个代码。但是,了解了图表的构建方式,您可以重新排列元素,使其Food and Waste Identification出现在图表的底部位置。

\documentclass[border=2mm]{standalone}
\usepackage{smartdiagram}
\usetikzlibrary{arrows.meta,bending}

\begin{document}
\smartdiagramset{module shape=circle, text width=1.5cm, font=\scriptsize, circular distance=3.7cm, arrow tip={}}
\smartdiagram[circular diagram:clockwise]{4.\\ Preparation, 5.\\ Consumption, 6.\\ Preservation, 7.\\ Distribution of waste, 8.\\ Dis\-integration, 1.\\ Food and Waste Identification, 2.\\ Production, 3.\\ Distribution of food}
\end{document}

在此处输入图片描述

答案3

与 PSTricks 和 相同pst-node。运行xelatex

\documentclass[margin=10pt,pstricks]{standalone}
\usepackage{multido,pst-node,ragged2e}
\def\PB#1{\parbox[b][]{2cm}{\Centering\sffamily#1}}
\begin{document}
\begin{pspicture}(-6,-6)(6,6)
    \psset{radius=1.25}\degrees[8]% A circle with 8 units
    \pgfforeach \iA/\iB in {
      1/Food and Waste Identification,2/Production,3/Distribution of food,
      4/Preparation,5/Consumption,6/Preservation,7/Distribution of waste,
      8/Disintegration}{\Cnodeput[fillcolor=blue!20,fillstyle=solid]{0}(5;\iA){\iA}{\PB{\iA.\\\iB}}}
    \nccurve[arrowscale=1.5,ncurv=.5,angleA=2,angleB=7]{<-}{8}{1}
    \multido{\iA=1+1,\iB=2+1,\iC=3+1,\iD=0+1}{7}{%
        \nccurve[arrowscale=1.5,ncurv=.5,angleA=\iC,angleB=\iD]{<-}{\iA}{\iB}}
\end{pspicture}
\end{document}

在此处输入图片描述

相关内容