我遇到的问题是,我不想让这两个弯曲箭头穿过其他节点,我该怎么做?
代码:
\begin{tikzpicture}
%nodes
\node [ellipse,draw=black, fill=green!20, minimum size = 2cm] (ctld) at (0,0) {slurmctld};
\node [rectangle,draw=black,rounded corners, fill=green!20, minimum size = 2cm, dashed] (dbd) at (3,0) {slurmdbd};
\node [rectangle,draw=black,rounded corners, fill=blue!20, minimum size = 2cm] (db) at (6,0) {database};
\node [rectangle,draw=black,rounded corners, fill=blue!20, minimum size = 2cm] (pmix) at (-3,0) {PMIx3};
\node [rectangle,draw=black,rounded corners, fill=blue!20, minimum size = 2cm] (mpi) at (-6,0) {OpenMPI};
\node [rectangle,draw=black,rounded corners, fill=red!20, minimum size = 2cm] (cuda) at (-6,-6) {CUDA};
\node [rectangle,draw=black,rounded corners, fill=red!20, minimum size = 2cm] (ib) at (-6,-10) {infiniband};
\node [ellipse,draw=black, fill=green!20, minimum size = 2cm] (sl1) at (-3,-6) {slurmd};
\node [ellipse,draw=black, fill=green!20, minimum size = 2cm] (sl2) at (0,-6) {slurmd};
\node [ellipse,draw=black, fill=green!20, minimum size = 2cm] (sl3) at (4,-6) {slurmd};
\node [rectangle,draw=black,rounded corners, fill=blue!20, minimum size = 2cm] (si1) at (-3,-10) {singularity};
\node [rectangle,draw=black,rounded corners, fill=blue!20, minimum size = 2cm] (si2) at (0,-10) {singularity};
\node [rectangle,draw=black,rounded corners, fill=blue!20, minimum size = 2cm] (si3) at (4,-10) {singularity};
% boxes
\node[draw, thick, dotted, rounded corners, inner xsep=1em, inner ysep=1em, fit=(sl1) (sl2) (sl3)] (slbox) {};
\node[draw, thick, dotted, rounded corners, inner xsep=1em, inner ysep=1em, fit=(si1) (si2) (si3)] (sibox) {};
%arrows
\path[every node] (mpi) edge[<->, thick] node [auto] {} (pmix);
\path[every node] (pmix) edge[<->, thick] node [auto] {} (ctld);
\path[every node] (ctld) edge[<->, thick] node [auto] {} (dbd);
\path[every node] (dbd) edge[<->, thick] node [auto] {} (db);
\path[every node] (mpi) edge[<->, thick, dashed, bend right=70] node [auto] {} (sibox);
\path[every node] (pmix) edge[<->, thick, dashed, bend right=70] node [auto] {} (sibox);
\end{tikzpicture}
答案1
对于此类重复任务,创建专用的 是有意义的to path
。
您可以将 视为to path
接受两个参数的路径的包装器。第一个参数是起点,第二个参数是目标点。在包装器中,您可以使用 和 引用\tikztostart
点\tikztotarget
。
以下是一个典型的例子:
请记住,我选择了最简单的弯曲形式,即仅将路径的拐角弄圆。但是,应该很容易根据您的需要调整示例。
如果您还有疑问,请告知我们。
\documentclass{article}
\usepackage{tikz}
\usepackage[hmargin=2cm]{geometry}
\usetikzlibrary{shapes, fit}
\begin{document}
\begin{tikzpicture}[
scale=0.82,
dedicated to path/.style = {
rounded corners=1em,
to path = {
(\tikztostart.north) -- ++(0,#1) -- ++(-4*#1,0) \tikztonodes coordinate(aux) --
(aux |- \tikztotarget.south) -- ++(0,-#1) coordinate(aux) -- (aux-|\tikztotarget.south) -- (\tikztotarget.south)
}
}
]
%nodes
\node [ellipse,draw=black, fill=green!20, minimum size = 2cm] (ctld) at (0,0) {slurmctld};
\node [rectangle,draw=black,rounded corners, fill=green!20, minimum size = 2cm, dashed] (dbd) at (3,0) {slurmdbd};
\node [rectangle,draw=black,rounded corners, fill=blue!20, minimum size = 2cm] (db) at (6,0) {database};
\node [rectangle,draw=black,rounded corners, fill=blue!20, minimum size = 2cm] (pmix) at (-3,0) {PMIx3};
\node [rectangle,draw=black,rounded corners, fill=blue!20, minimum size = 2cm] (mpi) at (-6,0) {OpenMPI};
\node [rectangle,draw=black,rounded corners, fill=red!20, minimum size = 2cm] (cuda) at (-6,-6) {CUDA};
\node [rectangle,draw=black,rounded corners, fill=red!20, minimum size = 2cm] (ib) at (-6,-10) {infiniband};
\node [ellipse,draw=black, fill=green!20, minimum size = 2cm] (sl1) at (-3,-6) {slurmd};
\node [ellipse,draw=black, fill=green!20, minimum size = 2cm] (sl2) at (0,-6) {slurmd};
\node [ellipse,draw=black, fill=green!20, minimum size = 2cm] (sl3) at (4,-6) {slurmd};
\node [rectangle,draw=black,rounded corners, fill=blue!20, minimum size = 2cm] (si1) at (-3,-10) {singularity};
\node [rectangle,draw=black,rounded corners, fill=blue!20, minimum size = 2cm] (si2) at (0,-10) {singularity};
\node [rectangle,draw=black,rounded corners, fill=blue!20, minimum size = 2cm] (si3) at (4,-10) {singularity};
% boxes
\node[draw, thick, dotted, rounded corners, inner xsep=1em, inner ysep=1em, fit=(sl1) (sl2) (sl3)] (slbox) {};
\node[draw, thick, dotted, rounded corners, inner xsep=1em, inner ysep=1em, fit=(si1) (si2) (si3)] (sibox) {};
\foreach[count=\i] \j/\k in {mpi/ib,pmix/si1,ctld/si2} {
\draw[->, >=stealth] (\j) to[dedicated to path=\i] node[above]{Annotation \i} (\k);
}
\end{tikzpicture}
\end{document}
答案2
关于在哪里绘制弯曲箭头的想法与 @user1146332 的回答类似,但整个代码要短得多。它使用chains
TikZ 库和节点形状的预定义样式。箭头直接绘制:
\documentclass[tikz, margin=3mm]{standalone}
\usetikzlibrary{arrows.meta,
chains,
fit,
shapes.geometric}
\begin{document}
\begin{tikzpicture}[scale=0.82,
node distance = 8mm and 4mm,
start chain = going right,
base/.style = {draw, minimum size = 2cm, on chain},
E/.style = {base, ellipse, fill=green!20, inner xsep=-1ex]},
F/.style = {draw, thick, dotted, rounded corners, inner sep=2mm, fit=#1},
R/.style = {base, rounded corners, fill=#1},
R/.default = blue!20,
]
%nodes
\node [R] (mpi) {OpenMPI};
\node [R] (pmix) {PMIx3};
\node [E] (ctld) {slurmctld};
\node [R=green!30, dashed] (dbd) {slurmdbd};
\node [R] (db) {database};
%
\node [R=red!20, below=16mm of mpi] (cuda) {CUDA};
\node [E] (sl1) {slurmd};
\node [E] (sl2) {slurmd};
\node [R] (sl3) {slurmd};
%
\node [R=red!20, below=of cuda] (ib) {infiniband};
\node [R] (si1) {singularity};
\node [R] (si2) {singularity};
\node [R] (si3) {singularity};
% fit boxes
\node[F=(sl1) (sl2) (sl3)] (slbox) {};
\node[F=(si1) (si2) (si3)] (sibox) {};
% connections
\foreach[count=\i] \j/\k in {mpi/ib,pmix/si1}
{
\draw[thick, densely dashed, rounded corners=3mm, -stealth]
(\j.north) -- ++ (0,\i*4mm)
-| ([xshift=-\i*5mm] mpi.west)
|- ([yshift=-\i*5mm] ib.south)
-| (\k);
}
\end{tikzpicture}
\end{document}