[Tex/LaTex] Automatic wrapping of a \multicolumn table cell

multicolumntables

I output lots of tables to LaTeX using the estout/esttab package in Stata. I frequently want to have long footnotes on the bottom of the table, explaining coefficients, sources, etc. The estout package inserts footnotes using \multicolumn{#}{l}{...} at the bottom of the table, but requires me to figure out line breaks. That is, it will print several rows of \multicolumn{#}{l}{...} \\, but I have to tell estout what I want on each row. This is a pain.

I would like to find a way to make a \multicolumn wrap at the length of the table. I know that I can make \multicolumn wrap using the p{<width>} alignment specifier, but all the width macros I've been able to come up with (\hsize, \textwidth, \linewidth, etc.) cause the \multicolumn to wrap at the width of the page (or whatever fixed fraction I tell it), thus either stretching out my table or wrapping too short.

Basically I want LaTeX to set the table width automatically (no tabular* or tabularx), but ignore the \multicolumn for the purposes of setting the width of the table, but have the \multicolumn wrap at the full width of the table.

Here's an example of the type of table I'm working with

\documentclass{article}
\usepackage{booktabs}
\begin{document}
\begin{table}
\centering
\caption{This is a table}
\begin{tabular}{l*{6}c}\toprule
& Something & Something & Something & Something & Something & Something \\\midrule
Amazing regression results & 100 & 100 & 100 & 100 & 100 & 100 \\\bottomrule
\multicolumn{7}{p{\textwidth}}{This is a footnote that's really really  really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really long}\\ %Ideally this should wrap without distorting the table
\end{tabular}
\end{table}
\end{document}

Any thoughts? I feel like there must be some LaTeX parameter containing the width of the table.

Best Answer

Werner's answer is really close to what I needed, but I figured out a more streamlined way to do it that (sort of) avoids the duplication: The \multicolumn is set to be \linewidth, which is initially re-set to be really small. The whole tabular environment (with the \multicolumn) is then put into a macro. The macro is then put in a \setbox, \linewidth is reset to the width of the box, and then the table is printed as a macro. Like so:

\documentclass{article}
\usepackage{booktabs,calc}
\begin{document}
\begin{table}
\centering
\caption{This is a table}
\setlength{\linewidth}{.1cm}\newcommand{\contents}{\begin{tabular}{l*{4}c}\toprule
& Something & Something & Something & Something  \\\midrule
Amazing regression results & 100 & 100 & 100 & 100  \\\bottomrule
\multicolumn{5}{p{\linewidth}}{This is a footnote that's really really  really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really long}\\ %Ideally this should wrap without distorting the table
\end{tabular}}
\setbox0=\hbox{\contents}
\setlength{\linewidth}{\wd0-2\tabcolsep-.25em}
\contents
\end{table}
\end{document}

It's a similar idea to Werner's answer, in that the table is first set in a box that is not printed, and the size of the box is used to set the \multicolumn. But this way while the table is technically duplicated from the perspective of the compiler, you don't have to duplicate the source code, and it's easier to put together (and to output from Stata, my goal here), since you're really just surrounding the tabular environment with a few commands.

Update 11/16

Since I wrote this post there have been a couple other answers regarding the Stata implementation of this wrapper approach. My approach (devised back when I wrote the question and answer) addresses the concerns BeingQuisitive and grossdpg mention, while preserving most of the functionality of the estout options. Specifically, I use the substitute() option on estout/esttab, which replaces a given string in the LaTeX output with another. Doing it this way rather than using postfoot() and prehead() allows you to employ the various estout options that add content to those areas, without having to set them manually (including e.g. title() and longtable()). Example Stata code:

#delimit ;
esttab * using output.tex, replace booktabs 
substitute(\begin{tabular} \setlength{\linewidth}{.1cm}\newcommand{\contents}{\begin{tabular}
           \end{tabular} \end{tabular}}\setbox0=\hbox{\contents}\setlength{\linewidth}{\wd0-2\tabcolsep-.25em}\contents
           {l}{\footnotesize {p{\linewidth}}{\footnotesize )
addnote{"This is a footnote that's really really  really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really really long")
;

Note: I seem to recall that the default for substitute() replaces _ and $ with _ and \$, respectively. If you need this, simply add that to the substitute option.

Related Question