# Accessing multiple arguments in \newcommand in Tikz

I need a figure like this (four vertically stacked rectangles with text; the two numbers in the texts are different and don't follow a pattern):

What I did:

%working
\documentclass{standalone}
\usepackage{tikz,amsmath}

\newcommand{\vrect}[2]{ %%% Need to pass an array of 4 arguments
\foreach \pos [count=\i] in {{(0,-4)},{(0,-3)},{(0,-2)},{(0,-1)}}{
\node[draw=black,thick,minimum size=1cm] (z\i) at \pos {Val#1#2};
}
}
\begin{document}
\begin{tikzpicture}[scale=1]
%%\vrect{{1,1}, {3,5}, {8,7}, {1,0}}} %% How to use this?
\vrect{1}{1}
\end{tikzpicture}
\end{document}


I don't really know

• how to pass an array as an argument
• how to access arguments based on the index (tried #\i with failure)

Any help is appreciated. P.S. I need to draw few figures like this, so I created a \newcommand.

• Is the number of the cells always 4? – CarLaTeX Sep 8 '17 at 10:46
• @CarLaTeX Yes (writing this part as comments must be at least 15 characters). – xxx--- Sep 8 '17 at 10:47
• So the four arguments are the numbers in the four cells? I'd look at using a rectangle split node, no loop will be needed. – Torbjørn T. Sep 8 '17 at 10:54

The \foreach command can iterate over multiple parameters, separated by /. You can use the array of the loop as parameter for your command. The position can be set with the counter \i by (0,-\i).

Note: You can pass an arbitrary number of parameters inside the array (don't have to be 4).

\documentclass{standalone}
\usepackage{tikz,amsmath}

\newcommand{\vrect}[1]{
\foreach \x/\y [count=\i] in #1 {
\node[draw=black,thick,minimum size=1cm] (z\i) at (0,-\i) {Val\x\y};
}
}

\begin{document}
\begin{tikzpicture}[scale=1]
\vrect{{1/1, 3/5, 8/7, 1/0}}
\end{tikzpicture}
\end{document}


If you're not tied to that weird syntax:

\documentclass{standalone}
\usepackage{tikz,amsmath}

\newcommand{\vrect}[1]{%
\def\myarray{{#1}}%
\foreach \pos [count=\i from 0] in {{(0,-4)},{(0,-3)},{(0,-2)},{(0,-1)}}{
\pgfmathsetmacro{\val}{\myarray[\i]}%
\node[draw=black,thick,minimum size=1cm] (z\i) at \pos {Val\val};
}%
}
\begin{document}

\begin{tikzpicture}
\vrect{11,35,87,10}
\end{tikzpicture}

\end{document}


You can give your array as a single argument to \vect, however, it will be easier if instead of using the list {1,1}, {3,5}, {8,7}, {1,0} you instead use 1/1, 3/5, 8/7, 1/0. This way you can loop over your coordinates in the "normal" tikz fashion.

\documentclass{standalone}
\usepackage{tikz,amsmath}

\newcommand{\vrect}[1]{ %%% Need to pass 4 arguments
\foreach \x/\y [count=\i] in {#1} {
\node[draw=black,thick,minimum size=1cm] (z\i) at (\x,\y) {Val\x-\y};
}
}
\begin{document}
\begin{tikzpicture}[scale=1]
\vrect{1/1, 3/5, 8/7, 1/0} %% How to use this!
\end{tikzpicture}
\end{document}


which produces

Notice that this will work for any number of arguments in the array.

EDIT

If you want the boxes stacked vertically this is marginally easier:

\documentclass{standalone}
\usepackage{tikz,amsmath}

\newcommand{\vrect}[1]{ %%% Need to pass 4 arguments
\foreach \x/\y [count=\i] in {#1} {
\node[draw=black,thick,minimum size=1cm] (z\i) at (0,-\i) {Val\x-\y};
}
}
\begin{document}
\begin{tikzpicture}[scale=1]
\vrect{1/1, 3/5, 8/7, 1/0} %% How to use this?
\end{tikzpicture}
\end{document}


which produces:

Again, this will accept an arbitrary number of arguments.