使用森林包,我使用以下代码
\begin{forest}
for tree={
grow'=east,
anchor=west,
node options={font=\itshape, align=center, },
forked edges,
l sep=4mm,
s sep=2mm,
fork sep = 2mm,
where level=0{anchor=center,draw=none}{},
where level=1{s sep=1mm,draw=none}{},
where level=2{s sep=1mm,draw=none}{},
where level=3{s sep=1mm,draw=none}{},
where level=4{s sep=1mm,draw=none}{},
where level=5{s sep=1mm,draw=none}{},
where level=6{s sep=1mm,draw=none}{},
where level=7{s sep=1mm,draw=none}{},
},
[Papilionoidea,
[Papilionidae]
[
[
[Hedylidae]
[Hesperiidae]
] % b
[
[
[Pieridae]
[
[
[Riodinidae]
[Lycaenidae]
] % f
[
[
[Nymphalidae]
] % h
] % g
] % e
] % d
] % c
] % a
] % Papilionoidea
\end{forest}
但是,这会产生空节点空间。如何消除这些空间,使线条连接起来?
答案1
即使是空的“正常”节点也会有一定的宽度和高度。Forest 和 TikZ 都是如此,Forest 就是建立在 TikZ 之上的。如果你编译这个,你就会看到这一点:
\documentclass{article}
\usepackage{tikz}
\begin{document}
\begin{tikzpicture}
\node[draw]{};
\end{tikzpicture}
\end{document}
创建宽度和高度为零的节点的最简单(也是最合适的)方法是将其形状设置为coordinate
,这就是我下面所做的。
现在,由于我们希望所有没有内容的节点都是坐标,因此我们将其放入coordinate
森林的循环中where
。我们将此循环放入森林的时间中delay
,因为如果我们不这样做,循环将在节点收到任何内容之前执行,因此它会将所有节点更改为坐标。
\documentclass{article}
\usepackage[edges]{forest}
\begin{document}
\begin{forest}
for tree={
grow'=east,
anchor=west,
font=\itshape,
forked edge,
fork sep = 2mm,
l sep=4mm,
s sep=1mm,
},
s sep=2mm,
% delay={
% where content={}{coordinate}{},
% },
[Papilionoidea,
[Papilionidae]
[
[
[Hedylidae]
[Hesperiidae]
] % b
[
[
[Pieridae]
[
[
[Riodinidae]
[Lycaenidae]
] % f
[
[
[Nymphalidae]
] % h
] % g
] % e
] % d
] % c
] % a
] % Papilionoidea
\end{forest}
\end{document}
我还擅自修复了代码中的其他几个问题。
永远不要把 a 放在
where
里面for tree
(除非你真的知道自己在做什么)。这样会形成一个双重循环。因此,它非常低效,有时甚至会导致微妙的问题。事实上,所有的
where level
s 几乎什么都没做,所以我删除了它们。它们唯一的作用是根是唯一具有 的节点s sep=2mm
。看看下面是如何实现的:s sep=1mm
在 内for tree
,以及s sep=2mm
树的外部。forked edges
是一个for tree
循环forked edge
(注意没有最后的s
)。因此,在内for tree
,您应该使用后者(如上文第 1 点所述)。align=center
设置多线节点的内部对齐,因此这里不需要。