3

Is it possible to define a command that works like \afterpage, but only applies to minipage environments? The usage I have in mind is as follows

\begin{minipage}
See the graph in Figure~\ref{foo}.
\afterminipage{\begin{figure}
etc.
}
\end{minipage}

This example would cause the figure environment to be executed at the end of the minipage.

3
  • 1
    ...but you know that the figure won't be placed after the minipage environment. It'll be floating to somewhere different.
    – Werner
    Nov 3, 2015 at 22:41
  • Why not placing it directly after the minipage (manually)?
    – user31729
    Nov 3, 2015 at 22:57
  • why would you do this? Nov 4, 2015 at 0:00

2 Answers 2

3

A trial -- the spacing is not nice and it depends on the correct setup by the user:

\afterminipage{...} stores its argument into a helper macro \@afterminipage which is used after the end of the minipage enviroment only if \@afterminipage is defined. At the end of the usage \@afterminipage is let to \relax, so it's effectively undefined. The next usage of a minipage will not add this \afterminipage code again, unless a new \afterminipage statement is applied.

\documentclass{article}

\usepackage{graphicx}
\usepackage{caption}
\usepackage{xpatch}

\usepackage{blindtext}

\makeatletter
\newcommand{\afterminipage}[1]{%
  \gdef\@afterminipagehook{#1}%
}

\AfterEndEnvironment{minipage}{%
  \@ifundefined{@afterminipagehook}{%
  }{%
    \@afterminipagehook%
  }
  \global\let\@afterminipagehook\relax
}
\makeatother

\begin{document}

\begin{minipage}[t]{\textwidth}
  See the graph in Figure~\ref{foo}.
  \afterminipage{%

    \blindtext

    \centering
    \includegraphics[scale=1]{beeduck}%
    \captionof{figure}{A figure} \label{foo}
}
\end{minipage}


\begin{minipage}{\textwidth}
  See the graph in Figure~\ref{foo}.

 \blindtext
\end{minipage}


\end{document}

enter image description here

2

An implementation using environ:

enter image description here

\documentclass{article}

\usepackage{environ}

\makeatletter
\newcommand{\@afterminipage}{}
\newcommand{\afterminipage}[1]{\xdef\@afterminipage{\@afterminipage#1}}

\let\oldminipage\minipage
\let\endoldminipage\endminipage

\newsavebox{\minipagesavebox}
\RenewEnviron{minipage}[2][c]{%
  \savebox{\minipagesavebox}{\BODY}%
  \let\afterminipage\@gobble
  \begin{oldminipage}[#1]{#2}
    \BODY
  \end{oldminipage}
  \@afterminipage
  \gdef\@afterminipage{}%
}
\makeatother

\begin{document}

\begin{minipage}{.5\textwidth}
Something.
\afterminipage{abc}%
def
\end{minipage}

\begin{minipage}[b]{.5\textwidth}
Something 
\afterminipage{multiple }%
completely different here that should span multiple lines of
\afterminipage{lines}%
code
\afterminipage{ of code.}%
\end{minipage}

\end{document}

One problem with this approach is a dual processing of the contents of the minipage environment. The first time only the contents provided by \afterminipages are added together, with everything else captured in a box that is never set. The second time, the box is set with the contents. This could be modified to just set the already-captured contents, if need be.

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .