9

I use \newcommand to quickly include figures. But combined with endfloat, it throws an error. Any ideas how to send floats to end when included this way?

\documentclass{article}
\usepackage{graphicx}
%\usepackage{endfloat}  % this causes an error

\newcommand{\addfig}[1]{ 
\begin{figure}[htbp]  % when float environment is included here
\centering 
  \includegraphics[width=\textwidth]{#1}  
\end{figure} 
} 

\begin{document}
\addfig{fig1}
\end{document} 
  • 3
    I won't work. See the documentation "10.6. environments names" – Ulrike Fischer Aug 22 '15 at 20:42
  • 10.6 of which documentation? thanks – dzeltzer Aug 22 '15 at 20:45
  • The documentation of endnotes. – Ulrike Fischer Aug 22 '15 at 21:07
  • I see, 10.3 of endfloats. The literal figure environment name must be included – dzeltzer Aug 22 '15 at 21:32
3

Although you cannot, as far as I can tell, configure endfloat to recognise the command \addfig appropriately, you can configure it to recognise additional floating environments such as addfig.

For example:

\documentclass{article}
\usepackage{graphicx}
\newenvironment{addfig}[1]{%
\begin{figure}
\centering
  \includegraphics[width=\textwidth]{#1}
}{\end{figure}}
\usepackage{endfloat}
\DeclareDelayedFloatFlavor{addfig}{figure}

\begin{document}
\begin{addfig}{example-image-a}
\end{addfig}
\end{document}

delayed custom float type

  • works perfect even when I modified addfig environment to include a minipage. – dzeltzer Sep 17 '15 at 15:19
  • @selig Glad it helped! – cfr Sep 17 '15 at 20:43
  • The markup would be a lot nicer if you could do \addfig{example-image-a} and not \begin{addfig}{example-image-a} \end{addfig} – StrongBad Jun 10 '16 at 17:56
  • @cfr Why are you putting \DeclareDelayedFloatFlavor{addfig}{figure} inside endnotes.cfg instead of applying it directly right after \usepackage{endnotes}? – Axel Sommerfeldt Jun 10 '16 at 18:07
  • 1
    @cfr I think this part of the documentation is misleading. Any endfloat-related code can be either placed in the document after loading the endfloat package or within the configuration file. (I guess I should have made this more clear when adding \DeclareDelayedFloatFlavor to the documentation.) And in fact when testing \DeclareDelayedFloatFlavor after implementation I never have used configuration files ;-) – Axel Sommerfeldt Jun 10 '16 at 20:28
3
+250

Here's one approach that writes each figure used in the command form \addfig[<opts>]{<image>} to a file tmpfig.tex and then immediately reads in that file:

enter image description here

\documentclass{article}

\usepackage{graphicx,newfile,endfloat}

\newoutputstream{tmpimg}

\newcommand{\addfig}[2][width=\textwidth]{%
  \openoutputfile{tmpfig.tex}{tmpimg}% Open tmpfig.tex for (over)writing
  % Add figure environment...
  \addtostream{tmpimg}{\protect\begin{figure}[htbp]}
  \addtostream{tmpimg}{\protect\centering}
  \addtostream{tmpimg}{\protect\includegraphics[#1]{#2}}
  \addtostream{tmpimg}{\protect\end{figure}}
  \closeoutputstream{tmpimg}% Close tmpfig.tex
  \input{tmpfig}% Input tmpfig.tex
}

\begin{document}

Some text.

\begin{figure}[htbp]  % when float environment is included here
  \centering
  \includegraphics[width=\textwidth]{example-image-a}
\end{figure} 

\addfig{example-image-b}

\addfig[width=.5\textwidth]{example-image-c}

\end{document}
  • Great Idea! (This is just some stuff to make this comment at least 15 characters in length ;-)) – Axel Sommerfeldt Jun 10 '16 at 20:29
  • This is very neat. – cfr Jun 10 '16 at 21:01
3

Last but not least a solution which tries to patch the endfloat package as less as possible:

\documentclass{article}
\usepackage{graphicx}
\usepackage{mwe}

\newcommand{\addfig}[1]{%
\begin{figure}[htbp]  % when float environment is included here
\centering 
  \includegraphics[width=\textwidth]{#1}  
\end{figure} 
} 

\usepackage{endfloat}[2011/12/25] % we need at least v2.5d
\usepackage{etoolbox}

% Adapt \addfig to the endfloat package
% First of all we make \addfig known to the endfloat package as variant of the figure environment
\DeclareDelayedFloatFlavour{addfig}{figure}
\makeatletter
% Special variant of \efloat@xfloat for commands (instead of environments):
% This macro will be expanded with every line read until \efloat@found@end is used.
% The original version tests if #2 (the actual line read) is "\end{}",
% and uses \efloat@iwrite in case of no and \efloat@found@end in case of yes.
% Our version just writes the line (containing the command and the rest of the line)
% using \efloat@iwrite and finishes the verbatim reading using \efloat@found@end afterwards.
{\catcode`\^^M=12 \endlinechar=-1 %
 \long\gdef\my@efloat@xfloat#1#2^^M{%
  \efloat@iwrite{#1}{#2}% write 1st line (containing the command)...
  \efloat@found@end{#1}%  ...and end verbatim reading afterwards
  \next}}              %  process next line
% Since \addfig is a command and not an environment we need to start a group for our own
% using \begingroup, so it behaves like we would have written \begin{addfig}.
% (Note: The endfloat package is designed to work with environments, not with commands.)
% Additionally we patch \efloat@xfloat to use our own variant of it for this command.
\pretocmd\addfig{%
  \begingroup
  \let\efloat@xfloat\my@efloat@xfloat}{}{}
\makeatother

\begin{document}
\addfig{example-image}
\end{document}

But this solution has two caveats:

  1. Everything written in the same line after usage of the command will be written to the file containing the floating environments as well. So it's not possible to write \addfig{example-image} Some text... in one line since otherwise "Some text..." would be delayed, too.

  2. The command and its arguments must be written in the same line. So it's not possible to split its usage to more lines, e.g. \addfig{% as 1st and example-image} as 2nd line.

In total we are using the three internal commands \efloat@xfloat, \efloat@iwrite, and \efloat@float@end here.

Addendum 2018-03-25

Since endfloat v2.6 things get a little easier since the test "is this the last line of the environment" is now available as \efloat@if@end, so this is the only internal command we need to patch:

\documentclass{article}
\usepackage{graphicx}
\usepackage{mwe}

\newcommand{\addfig}[1]{%
\begin{figure}[htbp]  % when float environment is included here
\centering
  \includegraphics[width=\textwidth]{#1}
\end{figure}
}

\usepackage{endfloat}[2018/01/01] % we need at least v2.6
\usepackage{etoolbox}

% Adapt \addfig to the endfloat package
% First of all we make \addfig known to the endfloat package as variant of the figure environment
\DeclareDelayedFloatFlavour{addfig}{figure}
\makeatletter
% Since \addfig is a command and not an environment we need to start a group for our own
% using \begingroup, so it behaves like we would have written \begin{addfig}.
% (Note: The endfloat package is designed to work with environments, not with commands.)
% Additionally we patch \efloat@if@end (usually expanding to \@firstoftwo or \@secondoftwo)
% so the very first command line will be written to the file and the verbatim reading will be
% finished afterwards.
\newcommand\my@efloat@if@end[3]{#3#2}
\pretocmd\addfig{%
  \begingroup
  \let\efloat@if@end\my@efloat@if@end}{}{}
\makeatother

\begin{document}
\addfig{example-image}
\end{document}
1

Here's a solution based on Werner's answer but which does away with the use of endfloat altogether. Once we are writing the figures to an external file anyhow, there doesn't seem much need for endfloat as we can just read the figures in from the file at the end of the document.

It happens to use the expl3 syntax, but that is really by-the-by. expl3 doesn't buy you anything special here - it is just an alternative syntax.

There is one macro:

\addfig[<options>]{<filename>}{<caption>}

Obviously, the optional argument is for options to be passed to \includegraphics, the second argument is for the name of the image file and the third is for the caption.

\documentclass{article}
\usepackage{graphicx,xparse,kantlipsum}
\ExplSyntaxOn
\AtBeginDocument
{
  \iow_new:N \l_strongbad_addfigs_stream
  \iow_open:Nn \l_strongbad_addfigs_stream { \jobname.addfigs }
}
\AtEndDocument
{
  \iow_close:N \l_strongbad_addfigs_stream
  \listoffigures
  \file_input:n { \jobname.addfigs }
}
\cs_new_protected:Nn \strongbad_addfig:nnn
{
  \group_begin:
  \str_set:Nn \l_tmpa_str { \setcounter{figure} }
  \str_put_right:Nx \l_tmpa_str { \c_left_brace_str }
  \str_put_right:Nx \l_tmpa_str { \thefigure }
  \str_put_right:Nx \l_tmpa_str { \c_right_brace_str }
  \iow_now:Nx \l_strongbad_addfigs_stream { \l_tmpa_str }
  \iow_now:Nn \l_strongbad_addfigs_stream
  {
    \begin{ figure }
      \centering
      \includegraphics [ #1 ] { #2 }
      \caption { #3 }
    \end{ figure }
  }
  \stepcounter{figure}
  \skip_vertical:N \bigskipamount
  \centering
  [~\figurename{}~\thefigure{}~about~here~]
  \skip_vertical:N \bigskipamount
  \group_end:
}
\NewDocumentCommand \addfig { O {} m +m }
{
  \strongbad_addfig:nnn { #1 } { #2 } { #3 }
}
\ExplSyntaxOff
\begin{document}
\kant[1]
\addfig{example-image-a}{first end figure}
\kant[2]
\addfig  {example-image-b}{second end figure}
\kant[3]
\addfig [width=.25\textwidth] {tiger} {third end figure}
\kant[4-5]
\end{document}

floats to end without <code>endfloat</code>

  • This is very nice, but endfloat is still useful in the case where you only use \addfig some of the time. – StrongBad Jun 10 '16 at 22:46
  • @StrongBad Yes, but you already have Werner's answer for that. No point in reinventing the wheel. What I like about this is that you can send some figures to the end without sending all of them. (I don't know endfloat so maybe it provides that functionality as well.) – cfr Jun 10 '16 at 22:53
  • I just don't know how the numbering should go in that case. – cfr Jun 10 '16 at 22:57

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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