3

I am using a class from EMS (European Math. Society), which is largely based on amsart.cls but which has a specific line saying (so I read in the comments) that they redefine sub(sub)section(*) so that subsections are typeset with a dot at the end. The following is the (relevant part of the) code that I find in the .cls file:

\let\s@bsection=\subsection

\newcommand{\c@mda}[2][]{\s@bsection[#1]{#2.}}

\newcommand{\c@mdb}[1]{\s@bsection*{#1.}}

\renewcommand{\subsection}{\secdef\c@mda\c@mdb}

We see why a dot is appearing. I have two questions, then:

  1. Can someone tell me where to read what is going on? I can make some educated guess (for instance, the dots after #2 in the second line and after #1 in the third should have something to do with my issue) but it is out of hope that I understand what the guy who wrote this had in mind...
  2. How to maintain the .cls file (which I am not allowed to modify), so having all subsections ending with a dot, but for a very single one whose titles ends with a question mark, hence creating the horrible double punctuation.

I have tried using \nopunct but it did not work, and since I'm here I'd like to ask

  1. Why it did not? What is the difference between this code and the amsart one which is otherwise affected by \nopunct?
5
  • Please provide a complete, compilable small example rather than a code fragment. Fragments are harder to work with and you are much more likely to end up with answers which turn out not to address your issue.
    – cfr
    Nov 7, 2015 at 1:37
  • Also, please don't quote code. It is better not to format it at all than to apply incorrect formatting as it takes much more time to undo it than it does just to apply the format for code.
    – cfr
    Nov 7, 2015 at 1:39
  • By default amsart.cls does not insert any kind of punctuation when typesetting section titles. So it is not clear what you mean about \nopunct working in that case.
    – cfr
    Nov 7, 2015 at 1:46
  • You are right about where the . is coming from. This may help? tex.stackexchange.com/questions/257364/…
    – Au101
    Nov 7, 2015 at 2:08
  • Can you give a small example with a pointer to the class? I think that the same method as I suggested for tex.stackexchange.com/questions/272913/… can be used.
    – egreg
    Nov 7, 2015 at 11:13

1 Answer 1

4

I found QT.cls, one of the EMS classes; since it features the same code as you show, the method I suggested for How to suppress the final period (".") in paragraph titles? seems to work as well.

\RequirePackage[2014/05/01]{latexrelease} % if you have an updated LaTeX distribution

\documentclass{QT}

\makeatletter
\renewcommand{\c@mda}[2][]{\s@bsection[#1]{#2\@addpunct{.}}}
\renewcommand{\c@mdb}[1]{\s@bsection*{#1\@addpunct{.}}}
\renewcommand{\subsection}{\secdef\c@mda\c@mdb}

\renewcommand{\c@mdsuba}[2][]{\s@bsubsection[#1]{#2\@addpunct{.}}}
\renewcommand{\c@mdsubb}[1]{\s@bsubsection*{#1\@addpunct{.}}}
\renewcommand{\subsubsection}{\secdef\c@mdsuba\c@mdsubb}
\makeatother

\title{A title}
\author{A. Uthor}
\address[[email protected]]{Somewhere}}

\begin{document}
\maketitle

\section{Section title}
Some text

\subsection{This has a period}
Some text

\subsection{Will this have one?}
Some text

\subsubsection{This has a period}
Some text

\subsubsection{Will this have one?}
Some text

\end{document}

enter image description here

The call of latexrelease is necessary in order to circumvent an issue due to the fact that the class loads a copy of amsthm in a bad place, so it's not really compatible with the most recent kernel.

The definition of \c@mda is still bad, however, because it would add an empty entry in the table of contents for all subsections where no optional argument is specified. It should be something like

\renewcommand{\c@mda}[2][]{%
  \if\relax\detokenize{#1}\relax
    \s@bsection[#2]{#2\@addpunct{.}}%
  \else
    \s@bsection[#1]{#2\@addpunct{.}}%
  \fi
}

and similarly for \c@mdsuba.


How does \@addpunct work? Let's look at its definition in amsthm.sty:

\def\@addpunct#1{%
  \relax\ifhmode
    \ifnum\spacefactor>\@m \else#1\fi
  \fi}

The \relax is a precaution in case \@addpunct comes first in a table cell or is preceded by something that performs expansion. It does nothing else. The bulk of the macro is in the inner conditional (if \@addpunct is found in vertical or math mode it does nothing, as it shouldn't be there in the first place and, perhaps more importantly, examining \spacefactor is disallowed in vertical and math modes). The current value of \spacefactor is examined: it is greater than 1000 (written \@m, but it's the same) only if the last character was punctuation and not, for instance, a period from an abbreviation such as B.C.; also something like i.e.\@ would result in the space factor to be 1000. If the space factor is above 1000, nothing is done, otherwise the argument to \@addpunct is printed.

Thus in the case of Will this have one?\@addpunct{.}, the period is effectively gobbled, but not in This has a period\@addpunct{.}.

The \nonfrenchspacing command, that's set by default (and by several language setups with babel) is defined by

% latex.ltx, line 530:
\def\nonfrenchspacing{\sfcode`\.3000\sfcode`\?3000\sfcode`\!3000%
  \sfcode`\:2000\sfcode`\;1500\sfcode`\,1250 }

so the characters that trigger the gobbling by \@addpunct are those listed there. The LaTeX kernel has

% latex.ltx, line 528:
\def\frenchspacing{\sfcode`\.\@m \sfcode`\?\@m \sfcode`\!\@m
  \sfcode`\:\@m \sfcode`\;\@m \sfcode`\,\@m}

so amsthm.sty redefines \frenchspacing as

\def\frenchspacing{\sfcode`\.1006\sfcode`\?1005\sfcode`\!1004%
  \sfcode`\:1003\sfcode`\;1002\sfcode`\,1001 }

Such space factors will not influence visibly the typesetting, for instance the space after a period would be multiplied by 1.006, so the difference would be about 0.02pt with Computer Modern at 10pt size. Different values are chosen in order to be able to still distinguish between punctuation characters, for possible extension of how \@addpunct or other macros work.

5
  • Thank you very much, it indeed works fine. Would it be possible to have more details on (1) Why is latexrealese needed? I have tried without it and nothing seems to bug, so I am wondering how would the bug become visible; (2) What are the commands \c@mda and \c@mdsuba? Are they low-level LaTeX programming, do you have a reference where things of this kind are discussed? Nov 8, 2015 at 19:42
  • @FilippoAlbertoEdoardo I got an error without latexrelease, it may depend on the version of the LaTeX kernel you have. The macros \c@mda and \c@mdsuba are defined in the QT class (and probably in the other classes provided by the EMS) as subsidiary macros for \subsection and \subsubsection.
    – egreg
    Nov 8, 2015 at 20:36
  • Thanks, I am trying to progress little by little. As a matter of fact, I have been looking at the definition of \@addpunct in the documentation for amsclass and I see that the definition is \def\@addpunct#1{%\relax\ifhmode\ifnum\spacefactor>\@m \else#1\fi\fi} which sounds more or less clear, except for the "%1\relax\ifhmode" part: already I do not understant %1, then why is \relax there (what does he want to stop?) and even more, why does it want to check if we are in horizontal mode? Nov 8, 2015 at 20:47
  • 1
    @FilippoAlbertoEdoardo I'll add an explanation of \@addpunct
    – egreg
    Nov 8, 2015 at 20:52
  • Thank you, everything is very clear and the explanation is useful. Nov 9, 2015 at 10:21

You must log in to answer this question.

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