3

I am taking the code I put together in With TikZ, is it possible to split a node horizontally and vertically?, and make it into a pic. This is doable, but placing successive pics is problematic: pics, even if named cannot reference each other, though named nodes within a pic can be referenced.

If the height of each pic is measured, it is possible, after the fact, to adjust the position of the pics using half of the pic height (in the optional argument to \step (see example code).

I am having trouble wrapping my head around how to get this to happen with a minimum of manual intervention. The answers at Anchoring TiKZ pics seem to suggest that, under some circumstances, this is possible, but I have not found a way to use them so far...

\documentclass{article}

\usepackage{fontspec,tikz}

\usetikzlibrary{calc,positioning,shapes.multipart,fit,backgrounds}

\newcounter{stepnum} \newcounter{tmpnum} \newlength{\recwd}

\setlength{\recwd}{2.5in}

%% |=====8><-----| %%

\makeatletter \newcommand{\dist}[3]{% #1 cs for result; #2 tikz coord. 1; #3 tikz coord. -- uses calc \tikz@scan@one@point\pgfutil@firstofone($(#2)-(#3)$)\relax
\pgfmathsetlengthmacro{#1}{veclen(\the\pgf@x,\the\pgf@y)}% <<<--->>> }% \makeatother

\tikzset{pics/hvmpnode/.style n args={3}{% The basic mechanism: #1=L; #2=UR; #3=LR code={% \node[name=L\thestepnum,rounded corners=1.5pt,fill=cyan!20] {% Left \hbox to 1.25em{\hss\textbf{#1}\hss} }; \node[rounded corners, rectangle split, rectangle split parts=2, rectangle split part fill={yellow!80!orange!20,none}, align=center, rounded corners=1.5pt, name=R, right= 0pt of L\thestepnum.east] {% \nodepart{one}\parbox{\recwd}{\centering\strut#2\strut}% UR \nodepart{two}\parbox{\recwd}{\parskip1ex\strut#3\strut} };% LR \draw[thick] (R.text split east) -- (R.text split west); \node[inner sep=0pt, draw, thick, rounded corners=1.5pt, name=W\thestepnum, anchor=south west, fit=(L\thestepnum)(R)] {};% W = enclosing box \draw[thick] (W\thestepnum.south west -| R.west) -- (W\thestepnum.north west -| R.west);% L/R rule \begin{scope}[on background layer] \fill[cyan!20,rounded corners=1.5pt] (W\thestepnum.north west) rectangle (R.south west); \end{scope} }% } }

\NewDocumentEnvironment{example}{s O{} m o}{% \setcounter{stepnum}{0}% \parbox{\textwidth}{% \begingroup \bfseries \itshape \Large #3 \par \endgroup \IfNoValueF{#4}{% \par\small\itshape\rightskip=0.5\textwidth plus 3em#4\par }% }% \par \medskip \begin{tikzpicture}[] }{% \end{tikzpicture} \bigskip }

\NewDocumentCommand{\step}{O{24pt} m +m}{% #1=materials; #2=technique \stepcounter{stepnum}% \setcounter{tmpnum}{\numexpr\thestepnum-1\relax} \ifnum\thestepnum=1 \path (0,0) pic{hvmpnode={\thestepnum}{#2}{#3}}; \else \path ([yshift=-#1]0,0 |- W\thetmpnum.south west)%% manually setting yshift as optional argument to \step is possible but icky; this aligns but is suspicious pic{hvmpnode={\thestepnum}{#2}{#3}};%% faulty \fi \dist{\mydist}{W\thestepnum.north}{W\thestepnum.south}\typeout{!!mydist=\mydist!!} }

%% |=====8><-----| %%

\parindent0pt

\begin{document}

\thispagestyle{empty}

\begin{example}{Foobar}[This is a meaningless bunch of bla bla bla to see if this works in any way, shape, or form.] \step{1 2 3 4 5 6}{bla bla bla lkfjdlkj} \step[49.66pt]{z b c d e f 7 8 9}{Much more bla bla bla and this is so much more jejune nonsense and a lot more bubbishy stuff that makes no sense. Much more bla bla bla and this is so much more jejune nonsense and a lot more bubbishy stuff that makes no sense.} \step[49.66pt]{z b c d e f 7 8 9}{Much more bla bla bla, Much more bla bla bla and this is so much more jejune nonsense and a lot more bubbishy stuff that makes no sense. Much more bla bla bla and this is so much more jejune nonsense an} \step[19.66pt]{z b c d e f 7 8 9}{Much more bla bla bla} \end{example}

For the height of each \texttt{pic}, \texttt{\string\typeout} says:

\begin{tabular}{l} !!mydist=39.33188pt!!\ !!mydist=99.33188pt!!\ !!mydist=99.33188pt!!\ !!mydist=39.33188pt!! \end{tabular}

\end{document}

pic chain ex

sgmoye
  • 8,586
  • This seems to be fairly simple to achieve by use of tables in nodes and nodes put in sequence by using chains library ... – Zarko Dec 21 '23 at 15:11
  • I was hoping to get some interesting insights into pics... I frequently use the chains library, but pics and chains do not seem to get on well together :>( – sgmoye Dec 21 '23 at 15:22
  • Ok, than wait for such suggestion. Use of pic may be tricky, but why simple if complex solution is challenge ... – Zarko Dec 21 '23 at 15:28
  • I'm a glutton for punishment... ;>) That, and I really want to get to the bottom of pics... – sgmoye Dec 21 '23 at 15:36
  • In a moment of panic, I did try a solution with just chains and nodes, but that was an exercise in frustration as well... – sgmoye Dec 21 '23 at 15:38
  • Have you tried using the tikzmark method for positioning pics? The question you link to is where it was introduced, and there's more detail in the documentation. – Andrew Stacey Dec 21 '23 at 19:28
  • @AndrewStacey I did though I didn't get far. I'll experiment a bit more. – sgmoye Dec 21 '23 at 20:41
  • @AndrewStacey I didn't see any examples in the documentation, so that has impeded my progress. – sgmoye Dec 21 '23 at 20:46
  • @AndrewStacey Though I begin to understand a few of the possibilities that tikzmark make available, I can't make the connection of how to use them for this problem. Could you give me a pointer? – sgmoye Dec 23 '23 at 10:05
  • @sgmoye I ended up going down a rabbit hole on one aspect, but I think I can throw something together next time I have my computer on. – Andrew Stacey Dec 23 '23 at 11:36

1 Answers1

2

Here's an answer using the ideas that started in Anchoring TiKZ pics. As is fairly inevitable, in figuring out this answer I found a bug in one part of the necessary code which I have fixed in the version of tikzmark on github (date of posting December 2023, if reading this a few months after that date then it has almost certainly been updated on CTAN by now).

The key surround pic puts a rectangular node around a pic with the same name as the pic, so that can be used to define coordinates, such as (<pic name>.south), after the pic has been defined.

The key pic anchor then installs the code that shifts the pic so that its "anchor" is at the specified location. Using the positioning library, this means that things like below=0pt of <previous pic> can be used to specify this pic's location.

Lastly, in figuring out what your current code does then I made a few cosmetic changes, mainly just to TikZ-ify stuff that was already there such as using keys to bold and centre the numbers rather than hard coding it.

\documentclass{article}
%\url{https://tex.stackexchange.com/q/705474/86}
\usepackage{fontspec,tikz}

\usetikzlibrary{ calc, positioning, shapes.multipart, fit, backgrounds, tikzmark }

\newcounter{stepnum} \newcounter{tmpnum} \newlength{\recwd}

\setlength{\recwd}{2.5in}

%% |=====8><-----| %%

\tikzset{ pics/hvmpnode/.style n args={3}{% The basic mechanism: #1=L; #2=UR; #3=LR code={% \node[ name=L\thestepnum, rounded corners=1.5pt, fill=cyan!20, text width=1.25em, node font=\bfseries, align=center, node contents={#1} ]; \node[rounded corners, rectangle split, rectangle split parts=2, rectangle split part fill={yellow!80!orange!20,none}, align=center, rounded corners=1.5pt, name=R, right= 0pt of L\thestepnum.east] {% \nodepart{one}\parbox{\recwd}{\centering\strut#2\strut}% UR \nodepart{two}\parbox{\recwd}{\parskip1ex\strut#3\strut} };% LR \draw[thick] (R.text split east) -- (R.text split west); \node[inner sep=0pt, draw, thick, rounded corners=1.5pt, name=W\thestepnum, anchor=south west, fit=(L\thestepnum)(R)] {};% W = enclosing box \draw[thick] (W\thestepnum.south west -| R.west) -- (W\thestepnum.north west -| R.west);% L/R rule \begin{scope}[on background layer] \fill[cyan!20,rounded corners=1.5pt] (W\thestepnum.north west) rectangle (R.south west); \end{scope} }% } }

\NewDocumentEnvironment{example}{s O{} m o}{% \setcounter{stepnum}{0}% \parbox{\textwidth}{% \begingroup \bfseries \itshape \Large #3 \par \endgroup \IfNoValueF{#4}{% \par\small\itshape\rightskip=0.5\textwidth plus 3em#4\par }% }% \par \medskip \begin{tikzpicture}[] }{% \end{tikzpicture} \bigskip }

\tikzset{ if number/.code n args={3}{ \ifnum#1\relax \pgfkeysalso{#2} \else \pgfkeysalso{#3} \fi } }

\NewDocumentCommand{\step}{O{24pt} m +m}{% #1=materials; #2=technique \stepcounter{stepnum}% \setcounter{tmpnum}{\numexpr\thestepnum-1\relax} \pic[ name=hvmp\thestepnum, surround pic, if number={\thestepnum=1}{}{ pic anchor, below=0pt of hvmp\thetmpnum, } ] {hvmpnode={\thestepnum}{#2}{#3}}; }

%% |=====8><-----| %%

\parindent0pt

\begin{document}

\thispagestyle{empty}

\begin{example}{Foobar}[This is a meaningless bunch of bla bla bla to see if this works in any way, shape, or form.] \step{1 2 3 4 5 6}{bla bla bla lkfjdlkj} \step[49.66pt]{z b c d e f 7 8 9}{Much more bla bla bla and this is so much more jejune nonsense and a lot more bubbishy stuff that makes no sense. Much more bla bla bla and this is so much more jejune nonsense and a lot more bubbishy stuff that makes no sense.} \step[49.66pt]{z b c d e f 7 8 9}{Much more bla bla bla, Much more bla bla bla and this is so much more jejune nonsense and a lot more bubbishy stuff that makes no sense. Much more bla bla bla and this is so much more jejune nonsense an} \step[19.66pt]{z b c d e f 7 8 9}{Much more bla bla bla} \end{example}

\end{document}

Result (after a few compilations to allow the coordinates to settle):

Output of the above code, showing pics positioned in a vertical stack

Andrew Stacey
  • 153,724
  • 43
  • 389
  • 751
  • 1
    Ah. That is excellent and, better yet, I've learned something. Thank you. – sgmoye Dec 23 '23 at 21:07
  • @sgmoye Happy to help. And, as hinted in the answer, this is a fairly recent feature of the tikzmark library so if you spot any niggles please let me know. Preferably on the issue tracker at the github repository, but if that's not feasible then feel free to use other means of getting in touch. – Andrew Stacey Dec 23 '23 at 21:11