6

From this question Creating PDF bookmarks in custom order arose another. (I hope it is correct to create a new question instead of commenting or editing/answering my old question.)

Using this macro (after creating counter nops):

\newcommand{\nop}{
  \stepcounter{nops}\hypertarget{nop\arabic{nops}}{}
  \BookmarkAtEnd{
    \bookmark[dest=nop\arabic{nops}]{page \arabic{nops}}
  }
}

I want \nop to mark the current place and add a bookmark to it to the end of my bookmark list. what happens is that the correct number of bookmarks is created, but they all reference the last occurence of \nop. It seems that this is because the text within \BookmarkAtEnd is practically copied to the end instead of inserting the current values first. How can i change this?

1 Answer 1

8

\BookmarkAtEnd simply stores the token list given as its argument, but you need that \arabic{nops} is expanded before storing.

The more common trick is to say

\newcommand{\nop}{%
  \stepcounter{nops}\hypertarget{nop\arabic{nops}}{}%
  \begingroup\edef\x{\endgroup\noexpand\BookmarkAtEnd{%
    \noexpand\bookmark[dest=nop\arabic{nops}]{page \arabic{nops}}}}\x
}

The \begingroup and \endgroup are used just in order to avoid that \x has a definition after being used. We protect from expansion the commands \BookmarkAtEnd and \bookmark (\endgroup doesn't need to be protected because it's unexpandable); in this way the token list to be stored will contain the actual value of nops and not a command to get at its representation.

Update

With a recent TeX distribution you can exploit expl3 and obtain an abstraction which you can then use also for other counters.

\usepackage{xparse}

\ExplSyntaxOn
\NewDocumentCommand{\nop}{}
 {
  \peter_bookmark:nne { nop } { nops } { \arabic{nops} }
 }
\cs_new_protected:Nn \peter_bookmark:nnn
 {
  \stepcounter{#2}
  \hypertarget{#1#3}{}
  \BookmarkAtEnd{\bookmark[dest=#1#3]{page~#3}}
 }
\cs_generate_variant:Nn \peter_bookmark:nnn { nne }
\ExplSyntaxOff

The idea is to expand the third argument of \peter_bookmark:nnn before expanding it, which is obtained by using the e variant.

2
  • There is a } missing before \x, but otherwise it works! Thank you.
    – peter
    Apr 30, 2011 at 23:33
  • @peter: Oops, corrected.
    – egreg
    Apr 30, 2011 at 23:46

You must log in to answer this question.

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