2

I'm a lazy person. The less I type the better, so I'm trying to make a macro to automatically arrange index entries for multi-word terms (composed nouns actually).

Normally you'd have to type:

...some others exhibit \textbf{complex behaviour}\index{behaviour!complex}

I want to reduce it to

...some others exhibit \iterm{complex behaviour}

So I came out with the following macro [MWE]:

\documentclass{book}
\usepackage{xspace,xstring,imakeidx}
\makeindex

\newcommand{\iterm}[1]{%
    \def\myindex{#1}%
    \IfSubStr{#1}{ }{%
        \renewcommand{\myindex}{\StrBehind{#1}{ }!\StrBefore{#1}{ }}%
    }{}%
    #1\index{\myindex}\xspace%
}
\begin{document}

some others exhibit \iterm{behaviour!complex}
\printindex

\end{document}

There's also an optional argument in case I must force an entry, and later on I might add code to deal with prepositions (e.g. \iterm{world of LaTeX} → \index{LaTex!world of}, but its solution is a particular case of the one above.

So far I'm getting the following errors

  • \renewcommand\myindex and \def\myindex:
    • Use of @index doesn't match its definition
    • Argument of @firstoftwo has an extra }.
  • \edef\myindex and \protected\edef\myindex:
    • Use of @xs@IfSubStr@@ doesn't match its definition
    • Argument of @firstoftwo has an extra }.
    • Paragraph ended before @firstoftwo was complete.
    • Too many }'s.
  • \protected\def\myindex and \DeclareRobustCommand:
    • Causes no error but does not add the entry to the index
  • \let\myindex
    • Missing control sequence inserted.
    • Too many }'s.

I'm 100% sure this is doable but haven't figured out yet. Thanks in advance for your suggestions and answers.

3

You need to separate the splitting of the parts from the index making command.

\documentclass{book}
\usepackage{xstring,imakeidx}

\makeindex

\newcommand{\iterm}[1]{%
  #1%
  \IfSubStr{#1}{ }{%
    \StrBehind{#1}{ }[\secondword]%
    \StrBefore{#1}{ }[\firstword]%
    \index{\secondword!\firstword}%
  }{\index{#1}}%
}

\begin{document}

some others exhibit \iterm{complex behaviour}

Another \iterm{term}

And finish \iterm{z}

\printindex

\end{document}

enter image description here

  • Not the most elegant solution coding-wise, but works like a charm! Thank you @egreg, thanks a lot. I'm starting to suspect you know all the answers. – Kyordhel Jan 17 '19 at 17:27

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.