9

I am trying to pdflatex a file but I get the following error:

! Incomplete \iffalse; all text was ignored after line [...].

The source of the error is a patch I used from here: Allowframebreaks causes beamer miniframes to misbehave

I use a construction with \if to load certain packages, depending on which documentclass I use. Normally if something only works with beamer, I put it inside a \iftargetBeamer-\else-\fi-block and at the beginning of the document I just write \targetReporttrue if I don’t wont to use it.

My problem now is that LaTeX does not ignore the text if the condition is false.

I have created a minimum “working” example of my problem:

\newif\iftargetReport
\newif\iftargetBeamer

\targetReporttrue

\iftargetReport
\documentclass[a4paper, 12pt, ngerman]{scrreprt}
\else\iftargetBeamer
\documentclass[ignorenonframetext, ngerman]{beamer}
\else
\typeout{no valid class defined, enter Ctrl-D (Linux) or Ctrl-Z (Windows)}
\endinput
\fi\fi

\iftargetBeamer
\makeatletter
\usepackage{etoolbox} % <- You can savely uncomment this if using report. This implies LaTeX does ignore this block.
% HERE is the problem!! Comment out next line to "fix" the issue.
\patchcmd{\slideentry}{\ifnum#2>0}{\ifnum2>0}{}{\@error{unable to patch}}% replace the subsection number test with a test that always returns true
% use frame numbers instead of subsection slide numbers so that frames broken over slides get separate circles
\patchcmd{\slideentry}{\c@subsectionslide}{\c@framenumber}{}{\@error{unable to patch}}
\patchcmd{\beamer@writeslidentry}{\c@subsectionslide}{\c@framenumber}{}{\@error{unable to patch}}
\makeatother
\else
\usepackage{beamerarticle}
\fi

\begin{document}
    \begin{frame}
        Some text.
    \end{frame}
\end{document}

If you comment out the first \patchcmd, everything just works fine. That suggest there is an error with the \ifnum (which I do not understand fully yet). But I think this shouldn’t even occur because LaTeX should ignore everything inside the \iftargetBeamer-block.

Please show me how I can successfully ignore the block when using the report.

6

Usual problem with skipping over conditionals. If the outer condition is false then Tex will be skipping over this

\patchcmd{\slideentry}{\ifnum#2>0}{\ifnum2>0}{

so it will not expand \patchcmd in any way but it will see two \ifnum and add them to its internal \if matching and so will expect to see two \fi closing the inner ifs.

You could give it two \fi with \@gobble{\fi\fi} or similar but less obscure and more maintainable would be to put the patching into an external file that you input so it isn't seen when skipping.

  • The idea of my setup is as follows: If you write a document, you just include two files which contain declarations, usepackages etc. and you just chose with \targetReporttrue or similar what you want. Splitting it up to avoid such errors is a good idea though. Thanks very much for this idea, just using a different file, like \input{beamer-cfg.tex} after \iftargetBeamer would have been a solution too. – Bambino Jan 3 '17 at 12:54
  • 1
    @Bambino in this specific case you could just not use \ifnum in the patch and rely on the fact that #2 is only used in that one place, but I thought I'd answer the general question of why it errors and how to avoid. – David Carlisle Jan 3 '17 at 12:55
5

When skipping tokens in an unused branch of a conditional, TeX still keeps track of conditionals, so when \iftargetBeamer is false, the two \ifnum are paired with the only two \fi tokens you provide.

Just remove \ifnum, because it's not required for the patch.

\newif\iftargetReport
\newif\iftargetBeamer

\targetReporttrue
%\targetBeamertrue

\iftargetReport
  \documentclass[a4paper, 12pt, ngerman]{scrreprt}
\else
  \iftargetBeamer
    \documentclass[ignorenonframetext, ngerman]{beamer}
  \else
    \typeout{no valid class defined, enter Ctrl-D (Linux) or Ctrl-Z (Windows)}
    \expandafter\expandafter\expandafter\endinput
  \fi
\fi

\iftargetBeamer
  \makeatletter
  \usepackage{etoolbox} 
  % replace the subsection number test with a test that always returns true
  \patchcmd{\slideentry}
    {#2>0}
    {2>0}
    {}{\@error{unable to patch}}
  % use frame numbers instead of subsection slide numbers so that frames 
  % broken over slides get separate circles
  \patchcmd{\slideentry}
    {\c@subsectionslide}
    {\c@framenumber}
    {}{\@error{unable to patch}}
  \patchcmd{\beamer@writeslidentry}
    {\c@subsectionslide}
    {\c@framenumber}
    {}{\@error{unable to patch}}
  \makeatother
\else
  \usepackage{beamerarticle}
\fi

\begin{document}
    \begin{frame}
        Some text.
    \end{frame}
\end{document}

Alternatively, use regexpatch, so you can “hide” the conditional.

\newif\iftargetReport
\newif\iftargetBeamer

\targetReporttrue
%\targetBeamertrue

\iftargetReport
  \documentclass[a4paper, 12pt, ngerman]{scrreprt}
\else
  \iftargetBeamer
    \documentclass[ignorenonframetext, ngerman]{beamer}
  \else
    \typeout{no valid class defined, enter Ctrl-D (Linux) or Ctrl-Z (Windows)}
    \expandafter\expandafter\expandafter\endinput
  \fi
\fi

\iftargetBeamer
  \makeatletter
  \usepackage{regexpatch}
  % replace the subsection number test with a test that always returns true
  \regexpatchcmd{\slideentry}
    {\c{ifnum}\cP.2>0}
    {\c{iftrue}}
    {}{\@error{unable to patch}}
  % use frame numbers instead of subsection slide numbers so that frames 
  % broken over slides get separate circles
  \xpatchcmd{\slideentry}
    {\c@subsectionslide}
    {\c@framenumber}
    {}{\@error{unable to patch}}
  \xpatchcmd{\beamer@writeslidentry}
    {\c@subsectionslide}
    {\c@framenumber}
    {}{\@error{unable to patch}}
  \makeatother
\else
  \usepackage{beamerarticle}
\fi

\begin{document}
    \begin{frame}
        Some text.
    \end{frame}
\end{document}
  • Thanks very much to you too. For my specific problem I now use your solution. I accepted David Carlisle‘s answer though because I think he explains the overall problem better. Could you direct me somewhere where I can read about how to use \ifnum and \patchcmd correctly? I don‘t understand what the patch really does yet and I think I could have answered the question myself if I would. – Bambino Jan 3 '17 at 13:09
  • 1
    @Bambino It's not a problem of using \ifnum in the argument to \patchcmd, which is generally harmless; the issue is having \ifnum in code that is skipped over in a conditional. I added a different solution. – egreg Jan 3 '17 at 15:28

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.