我正在使用 listing 包。是否可以使用花括号将列表中的某些行分组,以便能够将解释放在右侧?
我正在尝试使用给出的代码彼得·格里尔的精彩回答如何在算法内部放置花括号来对代码行进行分组?但是将 tikzmark 的列表功能给出的标记传递给 AddNote 似乎不起作用。
这是我目前的代码:
\documentclass{article}
\usepackage{tikz}
\usepackage{listings}
\usetikzlibrary{decorations.pathreplacing,calc,tikzmark}
\usetikzmarklibrary{listings}
\newcommand*{\AddNote}[4]{%
\begin{tikzpicture}[overlay, remember picture]
\draw [decoration={brace,amplitude=0.5em},decorate,ultra thick,red]
($(#3)!(#1.north)!($(#3)-(0,1)$)$) --
($(#3)!(#2.south)!($(#3)-(0,1)$)$)
node [align=center, text width=2.5cm, pos=0.5, anchor=west] {#4};
\end{tikzpicture}
}%
\begin{document}
\begin{lstlisting}[name=listing]
Example code line 1
Example code line 2
Example code line 3
Example code line 4
Example code line 5
Example code line 6
Example code line 7
Example code line 8
Example code line 9
Example code line 10
\end{lstlisting}
\AddNote{pic cs:line-listing-4-end}{pic cs:line-listing-7-end}{pic cs:line-listing-4-end}{Example annotation.}
\end{document}
输出内容如下:
答案1
自从提出这个问题以来,很多事情可能都发生了变化。我不太清楚为什么你的用法不起作用,因为它与文档中列出的一致。也许最近的更新中出现了一些不兼容的情况。
无论如何,这里有一个使用listings
'mathescape
功能的解决方法,但也许有人会提出真正的答案,然后我会删除这个答案。
代码
\documentclass{article}
\usepackage{tikz}
\usepackage{listings}
\usetikzlibrary{decorations.pathreplacing,calc}
\newcommand{\tikzmark}[1]{\tikz[overlay,remember picture] \node (#1) {};}
\newcommand*{\AddNote}[4]{%
\begin{tikzpicture}[overlay, remember picture]
\draw [decoration={brace,amplitude=0.5em},decorate,ultra thick,red]
($(#3)!([yshift=1.5ex]#1)!($(#3)-(0,1)$)$) --
($(#3)!(#2)!($(#3)-(0,1)$)$)
node [align=center, text width=2.5cm, pos=0.5, anchor=west] {#4};
\end{tikzpicture}
}%
\begin{document}
\begin{lstlisting}[mathescape]
Example code line 1
Example code line 2
Example code line 3
Example code line 4 $\tikzmark{listing-4-end}$
Example code line 5
Example code line 6
Example code line 7 $\tikzmark{listing-7-end}$
Example code line 8
Example code line 9
Example code line 10
\end{lstlisting}
\AddNote{listing-4-end}{listing-7-end}{listing-4-end}{Example annotation.}
\end{document}
请记住,这些数学转义符是按字面意思放置的(空格很重要)。因此,水平位置仍由 的第三个参数控制\AddNote
,但您必须在数学转义符前添加/删除空格才能更改位置。
输出
答案2
研究@PaulGessler 代码后,我想出了另一个解决方案。
唯一的主要优点是,在这种情况下,我们不必定义两个标记(代码内部)中的哪一个是最右边的。这是通过rectangle
在这些位置周围安装一个(无色)并brace
沿其east
侧面绘制一个来实现的。
包含一个宏:drawBrace
。它可以接收一个可选参数,设置绘制括号时相对于rectangle
代码中两个标记形成的水平偏移量。
该代码产生了两个示例,唯一的区别在于节点和箭头在其内部的样式tikzpicture
。
代码:
\documentclass{article}
\usepackage{tikz}
\usepackage{listings}
\usetikzlibrary{positioning,decorations.pathreplacing,fit}
\newcommand{\tikzmark}[2][]{%
\tikz[remember picture,overlay,baseline=-.5ex] \node[#1] (#2) {};%
}
% \drawBrace[xshift]{beginningNode}{endingNode}
% This command draws a brace between two tikzmarks, to their right,
% no matter which one is the rightmost, and includes
% a node midway the brace, to write the comment.
% This command also creates a new node
% whose name is the concat of the names of beginning and ending nodes.
\newcommand*{\drawBrace}[4][0pt]{%
\node[draw=none, fit={(#2) (#3)}, inner sep=0pt] (rectg) {};%
\draw [decoration={brace,amplitude=0.3em},decorate,very thick,red]%
([xshift=#1]rectg.north east) --%
coordinate[right=1em, midway] (#2#3)
([xshift=#1]rectg.south east);%
\node[right=1.5em of #2#3] (#2#3-comment) {#4};
\draw (#2#3-comment.west) edge (#2#3);
}%
\begin{document}
\begin{lstlisting}[name=listing,escapechar=!]
Example code line 1 !\tikzmark{bgnShifted}!
Example code line 2
Example code line 3
Example code line 4 !\tikzmark{bgnBrace}\tikzmark{trmShifted}!
Example code line 5
Example code line 6
Example code line 7 !\tikzmark{trmBrace}!
Example code line 8
Example code line 9 !\tikzmark{bgnOther}!
Example code line 10 !\tikzmark{trmOther}!
\end{lstlisting}
\begin{tikzpicture}[overlay, remember picture]
\drawBrace[.6em]{bgnShifted}{trmShifted}{Example xshifted.};
\drawBrace{bgnBrace}{trmBrace}{Example annotation.};
\drawBrace{bgnOther}{trmOther}{Another example.};
\end{tikzpicture}
\begin{lstlisting}[name=listing,escapechar=!]
Example code line 1 !\tikzmark{bgnShifted}!
Example code line 2
Example code line 3
Example code line 4 !\tikzmark{bgnBrace}\tikzmark{trmShifted}!
Example code line 5
Example code line 6
Example code line 7 !\tikzmark{trmBrace}!
Example code line 8
Example code line 9 !\tikzmark{bgnOther}!
Example code line 10 !\tikzmark{trmOther}!
\end{lstlisting}
\begin{tikzpicture}[overlay, remember picture,
every edge/.append style = { ->, thick, >=stealth, red!70},
every node/.style={draw=red,red,rounded corners}]
\drawBrace[.6em]{bgnShifted}{trmShifted}{Example xshifted.};
\drawBrace{bgnBrace}{trmBrace}{Example annotation.};
\drawBrace{bgnOther}{trmOther}{Another example.};
\end{tikzpicture}
\end{document}