森林 v.2

森林 v.2

今天是个好日子 -

是否有一种快速有效的方法来绘制目录树结构(又名深度缩进列表),就像unix的tree命令一样,也就是说,是否有办法使用TikZ绘制以下内容?

root
  |
  |--- dir1
  |     |
  |     |-- a1
  |     |-- a2
  |--- dir2
  |--- dir3

我已经检查了 tikz-tree 和 tikz-qtree,但是这些包总是希望树平衡地生长,而不是向下然后向右生长。

任何建议都将不胜感激。

谢谢。

答案1

我刚刚在使用 TikZ 的垂直树。下面的代码似乎有效,尽管我承认我没有对其进行全面测试,并且编造了一些数字,因此刚刚起作用

让我们从一些输出开始:

TikZ 版本的 dirtree

代码如下:

\documentclass[border=10]{standalone}
\usepackage{tikz}

\makeatletter
\newcount\dirtree@lvl
\newcount\dirtree@plvl
\newcount\dirtree@clvl
\def\dirtree@growth{%
  \ifnum\tikznumberofcurrentchild=1\relax
  \global\advance\dirtree@plvl by 1
  \expandafter\xdef\csname dirtree@p@\the\dirtree@plvl\endcsname{\the\dirtree@lvl}
  \fi
  \global\advance\dirtree@lvl by 1\relax
  \dirtree@clvl=\dirtree@lvl
  \advance\dirtree@clvl by -\csname dirtree@p@\the\dirtree@plvl\endcsname
  \pgf@xa=1cm\relax
  \pgf@ya=-1cm\relax
  \pgf@ya=\dirtree@clvl\pgf@ya
  \pgftransformshift{\pgfqpoint{\the\pgf@xa}{\the\pgf@ya}}%
  \ifnum\tikznumberofcurrentchild=\tikznumberofchildren
  \global\advance\dirtree@plvl by -1
  \fi
}

\tikzset{
  dirtree/.style={
    growth function=\dirtree@growth,
    every node/.style={anchor=north},
    every child node/.style={anchor=west},
    edge from parent path={(\tikzparentnode\tikzparentanchor) |- (\tikzchildnode\tikzchildanchor)}
  }
}
\makeatother
\begin{document}
\begin{tikzpicture}[dirtree]
\node {toplevel} 
    child { node {Foo}
            child { node {foo} }
            child { node {bar} }
            child { node {baz} }
    }
    child { node {Bar}
        child { node {foo} }
        child { node {foo} }
        child { node {foo} }
        child { node {foo} }
        child { node {bar} }
        child { node {baz} }
    }
    child { node {Baz}
        child { node {foo} }
        child { node {bar} }
        child { node {baz} }
    };
\end{tikzpicture}
\end{document}

我们定义了一个新的增长函数。我们的想法是,我们有一个全局计数器,用于跟踪到目前为止我们已处理的节点数,并根据此来定位子节点。主要问题是树的构建方式:每个分支的原点是父节点。因此,我们想要应用绝对变换(从根节点开始的总高度),但必须首先考虑相对变换。这需要一点簿记,但一旦弄清楚了,剩下的就……一帆风顺了。

边缘比较简单 - 我们只需将它们定义为|-,即垂直的,然后是水平的。

答案2

这里有两个概念使用 来实现这一点TikZ。第一个概念画的线不够多,第二个概念画的线太多了。我想每个级别都需要计数器。如果再次出现相同的级别并为其画一条线,这些计数器就会增加,而当遇到更高的级别时,它们会重置,例如,就像人们主要用 来实现的那样

\usepackage{chngcntr}
\counterwithin{leveltwo}{levelone}

可能我这周就能完成,但别指望了。以下是我目前所做的事情:

\documentclass[parskip,14pt]{scrartcl}
\usepackage[margin=15mm]{geometry}
\usepackage{tikz}

\newcounter{treeline}

\newcommand{\treeroot}[1]{% Title
\node[above] at (0,0) {#1};%
\setcounter{treeline}{0}
}

\newcommand{\treeentry}[2]{% Title, Level
\draw[->] (#2-1,-\value{treeline}/2) -- (#2-1,-\value{treeline}/2-0.5) -- (#2+0.5,-\value{treeline}/2-0.5) node[right] {#1};
\stepcounter{treeline}
}

\newcommand{\altentry}[2]{% Title, Level
\draw[->] (#2-1,-\value{treeline}/2) -- (#2-1,-\value{treeline}/2-0.5) -- (#2+0.5,-\value{treeline}/2-0.5) node[right] {#1};
\foreach \x in {1,...,#2}
{   \draw (\x-1,-\value{treeline}/2) -- (\x-1,-\value{treeline}/2-0.5);
}
\stepcounter{treeline}
}

\begin{document}

\begin{tikzpicture}
\treeroot{$\sqrt{of\ all\ evil}$}
\treeentry{Bla}{1}
\treeentry{Bla}{2}
\treeentry{Bla}{3}
\treeentry{Bla}{2}
\treeentry{Bla}{2}
\treeentry{Bla}{3}
\treeentry{Bla}{3}
\treeentry{Bla}{3}
\treeentry{Bla}{3}
\treeentry{Bla}{3}
\treeentry{Bla}{4}
\treeentry{Bla}{4}
\treeentry{Bla}{4}
\treeentry{Bla}{4}
\treeentry{Bla}{4}
\treeentry{Bla}{4}
\treeentry{Bla}{1}
\treeentry{Bla}{1}
\treeentry{Bla}{2}
\treeentry{Bla}{3}
\treeentry{Bla}{2}
\treeentry{Bla}{2}
\treeentry{Bla}{3}
\treeentry{Bla}{1}
\end{tikzpicture}
\hspace{2cm}
\begin{tikzpicture}
\treeroot{$\sqrt{of\ all\ evil}$}
\altentry{Bla}{1}
\altentry{Bla}{2}
\altentry{Bla}{3}
\altentry{Bla}{2}
\altentry{Bla}{2}
\altentry{Bla}{3}
\altentry{Bla}{3}
\altentry{Bla}{3}
\altentry{Bla}{3}
\altentry{Bla}{3}
\altentry{Bla}{4}
\altentry{Bla}{4}
\altentry{Bla}{4}
\altentry{Bla}{4}
\altentry{Bla}{4}
\altentry{Bla}{4}
\altentry{Bla}{1}
\altentry{Bla}{1}
\altentry{Bla}{2}
\altentry{Bla}{3}
\altentry{Bla}{2}
\altentry{Bla}{2}
\altentry{Bla}{3}
\altentry{Bla}{1}
\end{tikzpicture}

\end{document}

结果如下:

在此处输入图片描述

答案3

更新:Forest 现在或多或少提供了这种开箱即用的样式。如果您需要针对旧版本 Forest 的解决方案(无论出于何种原因),请参阅下面我原来的回答,了解合适样式的定义。


森林 v.2

这是一个forest使用库folder提供的样式的解决方案edges。这需要 Forest 版本 2。

\documentclass[tikz, border=5pt, multi]{standalone}
\usepackage[edges]{forest}
\begin{document}
\begin{forest}
  for tree={%
    folder,
    grow'=0,
    fit=band,
  }
  [root
    [bin
    ]
    [etc
      [X11]
      [cron.d]
      [default]
    ]
    [local
      [bin]
      [etc]
      [texlive
        [2014
          [bin]
          [readme-html.dir]
          [texmf-config]
          [texmf-dist]
          [texmf-var]
        ]
        [texmf-local]
      ]
    ]
    [usr
      [bin]
      [include]
      [share]
    ]
    [var
      [cache]
      [log]
      [spool]
      [tmp]
    ]
  ]
\end{forest}
\end{document}

v.2 几乎开箱即用

森林 v.1

这是我最初的forest解决方案,它定义了一种新样式dir tree,可以使用 版本 1 来排版这种格式的树forest

\documentclass[tikz, border=5pt, multi]{standalone}
\usepackage{forest}
\usetikzlibrary{arrows.meta}
\forestset{
  dir tree/.style={
    for tree={
      parent anchor=south west,
      child anchor=west,
      anchor=mid west,
      inner ysep=1pt,
      grow'=0,
      align=left,
      edge path={
        \noexpand\path [draw, \forestoption{edge}] (!u.parent anchor) ++(1em,0) |- (.child anchor)\forestoption{edge label};
      },
      font=\sffamily,
      if n children=0{}{
        delay={
          prepend={[,phantom, calign with current]}
        }
      },
      fit=band,
      before computing xy={
        l=2em
      }
    },
  }
}
\begin{document}
\begin{forest}
  dir tree
  [root
    [bin
    ]
    [etc
      [X11]
      [cron.d]
      [default]
    ]
    [local
      [bin]
      [etc]
      [texlive
        [2014
          [bin]
          [readme-html.dir]
          [texmf-config]
          [texmf-dist]
          [texmf-var]
        ]
        [texmf-local]
      ]
    ]
    [usr
      [bin]
      [include]
      [share]
    ]
    [var
      [cache]
      [log]
      [spool]
      [tmp]
    ]
  ]
\end{forest}
\end{document}

目录树

答案4

使用该库的另一个示例tikz trees

\documentclass{standalone}

\usepackage{tikz}
\usetikzlibrary{trees}

\usepackage{xcolor}

\begin{document}

\tikzstyle{every node}=[thick,anchor=west, rounded corners, font={\scriptsize\ttfamily}, inner sep=2.5pt]
\tikzstyle{selected}=[draw=blue,fill=blue!10]
\tikzstyle{root}=[selected, fill=blue!30]

\begin{tikzpicture}[%
    scale=.7,
    grow via three points={one child at (0.5,-0.65) and
    two children at (0.5,-0.65) and (0.5,-1.1)},
    edge from parent path={(\tikzparentnode.south) |- (\tikzchildnode.west)}]
  \node [root] {src}
    child { node [selected] {asf}
      child { node [selected] {avr32}
        child { node [selected] {drivers}
          child { node [selected] {canif}
            child { node {canif.h}}
            child { node {canif.c}}
          }
        }
      }
    }       
    child { node at (0,-3.5) [selected] {net}
      child { node [selected] {can}
        child { node {can.h}}
        child { node {can\_mob.h}}
        child { node {can\_mob.c}}
        child { node {can\_port.h}}
        child { node {can\_port.c}}
        child { node {can\_trcv.h}}
        child { node {can\_trcv.c}}
      }
    }
    child { node at (0,-8) {\dots}};
\end{tikzpicture}

\end{document}

文件夹结构

相关内容