Take the 2-minute tour ×
TeX - LaTeX Stack Exchange is a question and answer site for users of TeX, LaTeX, ConTeXt, and related typesetting systems. It's 100% free, no registration required.

I have a situation where I have a tabular environment with repeated labels:

\documentclass{article}

\begin{document}

\begin{tabular}{ll}\hline
        Label 1 & Bunch of text\\
        Label 2 & More text\\
        Label 3 & Even more things to write\\
        Label 4 & Lots of stuff\\\hline

        Label 1 & Second set of entries\\
        Label 2 & Can be written here\\
        Label 3 & All sorts of stuf\\
        Label 4 & Last of the second entries\\\hline

        Label 1 & Third set of entries\\
        Label 2 & With its own unique text\\
        Label 3 & But the same set of labels\\
        Label 4 & Off to the left\\\hline
\end{tabular}

\end{document}

Essentially, I have a table with a bunch of small tables where all of the labels are the same. As the above example shows, I have to repeat each of these labels by hand. Is there a way to automatically create these labels? Alternatively, is there a way to way to make a tabular schema where we only fill in the missing information?

share|improve this question
    
Are those the labels? Or do you have a different list of labels that you want to post? –  Werner Mar 3 at 18:31
    
Those aren't the exact labels. I guess the primary difference between this situation and what I have is that the actual set of labels isn't numbered. Basically, the set of labels are arbitrary strings like: "Default", "Type", and "Dependencies". –  wyer33 Mar 3 at 18:41
add comment

4 Answers 4

up vote 7 down vote accepted

Here's a possible solution, with a counter that's reset automatically; it should be clear how to modify the labels to your real ones.

\documentclass{article}
\usepackage{array}

\newcommand{\rowlabels}{%
  \ifcase\value{rowlabelcount}\or
    Label 1\or
    Label 2\or
    Label 3\or
    Label 4\fi
}
\newcommand{\printlabel}{%
  \stepcounter{rowlabelcount}%
  \ifnum\value{rowlabelcount}=5 % change here the value when resetting is needed
    \setcounter{rowlabelcount}{1}%
  \fi
  \rowlabels
}
\newcounter{rowlabelcount}

\begin{document}

\begin{tabular}{>{\printlabel}ll}\hline
 & Bunch of text\\
 & More text\\
 & Even more things to write\\
 & Lots of stuff\\\hline

 & Second set of entries\\
 & Can be written here\\
 & All sorts of stuf\\
 & Last of the second entries\\\hline

 & Third set of entries\\
 & With its own unique text\\
 & But the same set of labels\\
 & Off to the left\\\hline
\end{tabular}

\end{document}

enter image description here

share|improve this answer
    
Worked beautifully. Thanks for the code. –  wyer33 Mar 3 at 19:30
add comment

You can also use the collcell package to define a custom column environment. I have defined the L environment below to automatically add the label if there is no text provided. If there is data already in that column then that text is used as the label. The red coloring here is added just to show where the automatic labels are added.

enter image description here

The default below is to require a call to \RestartLabelCounter to restart the label when desired. However with a call to

\toggletrue{AutoResetCounter}
\setcounter{LabelCounter}{0}

the code will auto reset every 4 entries:

enter image description here

Notes:

  • In the current implementation you need to call

    \setcounter{LabelCounter}{0}
    

    before every table, unless you desire the labels to continue from one table to the next This can also be automated if desired.

Code:

\documentclass{article}

\usepackage{xcolor}
\usepackage{collcell}
\usepackage{ifmtarg}
\usepackage{etoolbox}

% http://tex.stackexchange.com/questions/125714/use-of-ifmtarg-yields-spurious-space
\makeatletter
\newcommand{\IfIsEmptyArg}[3]{%
  \expandafter\@ifmtarg\expandafter{#1}{#2}{#3}
}
\makeatother


\newtoggle{AutoResetCounter}%
\togglefalse{AutoResetCounter}%

\newcounter{LabelCounter}%
\setcounter{LabelCounter}{0}%
\newcommand*{\StepCounter}[1]{%
    \iftoggle{AutoResetCounter}{%
        \ifnum\value{#1}=4\relax%
            \setcounter{#1}{1}%
        \else
            \stepcounter{#1}%
        \fi
    }{%
        \stepcounter{#1}%
    }%
}%
\newcommand*{\RestartLabelCounter}{\setcounter{LabelCounter}{0}}%
\newcommand*{\ApplyLabel}[1]{%
    \IfIsEmptyArg{#1}{%
        \textcolor{red}{Label \theLabelCounter}%
        \StepCounter{LabelCounter}%
    }{%
        #1%
    }%
}%
\newcolumntype{L}{>{\collectcell\ApplyLabel}l<{\endcollectcell}}

\begin{document}
\begin{tabular}{Ll}\hline
        & Bunch of text\\
        & More text\\
        & Even more things to write\\
        & Lots of stuff\\
        \hline
        Label X & Second set of entries\\
        Label Y & Can be written here\\
                 & All sorts of stuf\\
                 & Last of the second entries \RestartLabelCounter\\
        \hline
        & Third set of entries\\
        & With its own unique text\\
        & But the same set of labels\\
        & Off to the left\\\hline
\end{tabular}

\bigskip
\toggletrue{AutoResetCounter}
\setcounter{LabelCounter}{0}
With auto reset enabled:\medskip

\begin{tabular}{Ll}\hline
        & Bunch of text\\
        & More text\\
        & Even more things to write\\
        & Lots of stuff\\
        \hline
        & Another set of entries\\
        & With its own unique text\\
        & But the same set of labels\\
        & Off to the left\\\hline
\end{tabular}

\end{document}
share|improve this answer
add comment

Rather than use a counter and empty cells, I would just use a custom syntax to fill in an internal table, also use array package's \extrarowheight to keep the text away from the hlines.

enter image description here

\documentclass{article}

\usepackage{array}

\newenvironment{foolist}
{\par
\setlength\extrarowheight{2pt}%
\centering\begin{tabular}{ll}\hline}
{\end{tabular}\par}

\newcommand\foo[4]{%
        Label 1 & #1\\
        Label 2 & #2\\
        Label 3 & #3\\
        Label 4 & #4\\\hline
}
\begin{document}

\begin{foolist}

\foo{Bunch of text}
    {More text}
    {Even more things to write}
    {Lots of stuff}

\foo{Second set of entries}
    {Can be written here}
    {All sorts of stuf}
    {Last of the second entries}

\foo{Third set of entries}
    {With its own unique text}
    {But the same set of labels}
    {Off to the left}

\end{foolist}

\end{document}
share|improve this answer
    
I've a different use case where this works well. Thanks! –  wyer33 Mar 3 at 19:35
add comment

There's not much to go on here. So, I'll just illustrate one approach you could use

\documentclass{article}

\makeatletter

\newcounter{mytablelabel}
\newcommand{\myentry}{%%
  \@ifnextchar*{\setcounter{mytablelabel}{0}\@myentry}
               {\@myentry*}}
\def\@myentry*#1{\stepcounter{mytablelabel}Label \arabic{mytablelabel} & #1 \\}

\makeatother

\pagestyle{empty}
\begin{document}

\begin{tabular}{ll}\hline
  \myentry{Bunch of text}
  \myentry{More text}
  \myentry{Even more htings to write}
  \myentry{Lots of stuff}\hline

  \myentry*{Bunch of text}
  \myentry{More text}
  \myentry{Even more things to write}
  \myentry{Last of the second entries}\hline

  \myentry*{Third set of entries}
  \myentry{With its own unique text} 
  \myentry{But the same set of labels}
  \myentry{Off to the left}
\end{tabular}

\end{document}

Here I've created a counter and a command that format the content of each line of the table. I've allowed a starred version of the command to reset the counter. That could be tweaked if you have something more convoluted in mind.

share|improve this answer
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.