1

So I have this in my document.

\documentclass[a4paper,12pt]{article}
\usepackage{hyperref}
\hypersetup{
  pdfborder=0 0 0,
  pdfinfo={
    Author={Me},
    Creator={Me},
    Title={The title},
    Subject={A subject},
    Producer={LaTeX}
  }
}

How do I set each of these values one at a time (author, creator, title, etc.) and plug them in? So this is how I would like to use it:

\documentclass{foo}

\fooauthor{Me}
\footitle{A Title}
...

Then plug it in somehow in the .cls file or some .sty file:

\hypersetup{
  pdfborder=0 0 0,
  pdfinfo={
    Author={@fooauthor},
    Creator={@fooauthor},
    Title={@footitle}
    ...
  }
}

How to do something like this?

Lance
  • 1,799

1 Answers1

2

You did not state anything about whatsoever TeX-extensions may be used (ε-TeX, \expanded, ...).

Therefore my first example doesn't make use of whatsoever extensions at all.

Instead with that example a lot of \romannumeral0-expansion takes place.

The gist of \romannumeral0-expansion is:

\romannumeral gathers digits and a terminating space-token for finding the number to convert to roman notation.
Expansion of expandable tokens is not suppressed but triggered when seeking for more digits or the terminating space-token of the number to convert.
A space-token terminating the sequence of digits that forms the number to convert is silently discarded.
In case the number to convert is not positive, \romannumeral0 will silently just swallow the digit-sequence that forms the number and not deliver any token in return.

Therefore you can nicely (ab?)use \romannumeral for triggering a lot of expansion- and argument-exchanging-work during the search for more digits or a space-token that terminates the digit-sequence as long as it is ensured that in the end the number found is not positive.

\documentclass[a4paper,12pt]{article}
\usepackage{hyperref}

\makeatletter

\newcommand\Exchange[2]{#2#1}%    

% Be aware that two consecutive hashes in the definition-text of a macro will be collapsed 
% into a single hash within the result of expanding that macro.
% Therefore something must be done for having hashes doubled within the macros that serve as
% place-holders for values of variables:
\newcommand\definemacrowithhashdoubling[2]{%
  \expandafter\Exchange\expandafter{%
     \expandafter\toks@\expandafter{\the\toks@}%
  }{%
    \toks@{#2}%
    \@ifdefinable#1{\edef#1{\the\toks@}}%
  }%
}%

\newcommand\foopdfborder[1]{\definemacrowithhashdoubling\@foopdfborder{#1}}%
\newcommand\fooauthor[1]{\definemacrowithhashdoubling\@fooauthor{#1}}%
\newcommand\foocreator[1]{\definemacrowithhashdoubling\@foocreator{#1}}%
\newcommand\footitle[1]{\definemacrowithhashdoubling\@footitle{#1}}%
\newcommand\foosubject[1]{\definemacrowithhashdoubling\@foosubject{#1}}%
\newcommand\fooproducer[1]{\definemacrowithhashdoubling\@fooproducer{#1}}%

% \DeliverHyperSetupKeyValList delivers keyval-list for \hypersetup according
% to the definitions of \@foopdfborder, \@fooauthor, \@foocreator, \@footitle, 
% \@foosubject and \@fooproducer.
%
% Due to \romannumeral0-/\Exchange-expansion-trickery, the result is delivered
% after triggering two expansion-steps/after two "hits" with \expandafter:
%
\newcommand\DeliverHyperSetupKeyValList{%
  \romannumeral0%
  \expandafter\Exchange\expandafter{%
    \romannumeral0%
    \csname @\@ifundefined{@fooauthor}{%
      \@ifundefined{@foocreator}{%
        \@ifundefined{@footitle}{%
          first%
        }{second}%
      }{second}%
    }{second}oftwo\endcsname{ }{%
      \expandafter\Exchange\expandafter{\expandafter{\romannumeral0%
        \expandafter\Exchange\expandafter{%
          \romannumeral0\@ifundefined{@footitle}{ %
          }{\expandafter\Exchange\expandafter{\expandafter{\@footitle}}{ Title=},}%
        }{%
          \expandafter\Exchange\expandafter{%
            \romannumeral0\@ifundefined{@foocreator}{ %
            }{\expandafter\Exchange\expandafter{\expandafter{\@foocreator}}{ Creator=},}%
          }{%
            \expandafter\Exchange\expandafter{%
              \romannumeral0\@ifundefined{@fooauthor}{ %
              }{\expandafter\Exchange\expandafter{\expandafter{\@fooauthor}}{ Author=},}%
            }{%
              \expandafter\Exchange\expandafter{%
                \romannumeral0\@ifundefined{@foosubject}{ %
                }{\expandafter\Exchange\expandafter{\expandafter{\@foosubject}}{ Subject=},}%
              }{%
                \expandafter\Exchange\expandafter{%
                  \romannumeral0\@ifundefined{@fooproducer}{ %
                  }{\expandafter\Exchange\expandafter{\expandafter{\@fooproducer}}{ Producer=},}%
                }{ }%
              }%
            }%
          }%
        }%
      }}{ pdfinfo=},%
    }%
  }{%
    \expandafter\Exchange\expandafter{%
      \romannumeral0\@ifundefined{@foopdfborder}{ %
      }{\expandafter\Exchange\expandafter{\expandafter{\@foopdfborder}}{ pdfborder=},}%
    }{ }%
  }%
}%
\makeatother

\foopdfborder{0 0 0}
\fooauthor{Me}
\foocreator{Me}
\footitle{The title}
\foosubject{A subject}
\fooproducer{LaTeX}

\expandafter\expandafter\expandafter\def
\expandafter\expandafter\expandafter\test
\expandafter\expandafter\expandafter{\DeliverHyperSetupKeyValList}%

\show\test

\expandafter\expandafter\expandafter\hypersetup
\expandafter\expandafter\expandafter{\DeliverHyperSetupKeyValList}%

\begin{document}

Some text.

\end{document}

In case ε-TeX-extensions which bring along the \unexpanded-primitive are available, you can combine \edef and \unexpanded for defining a temporary macro and passing its expansion to \hypersetup:

\documentclass[a4paper,12pt]{article}
\usepackage{hyperref}

\makeatletter

\newcommand\Exchange[2]{#2#1}%    

% Be aware that two consecutive hashes in the definition-text of a macro will be collapsed 
% into a single hash within the result of expanding that macro.
% Therefore something must be done for having hashes doubled within the macros that serve as
% place-holders for values of variables:
\newcommand\definemacrowithhashdoubling[2]{\@ifdefinable#1{\edef#1{\unexpanded{#2}}}}%

\newcommand\foopdfborder[1]{\definemacrowithhashdoubling\@foopdfborder{#1}}%
\newcommand\fooauthor[1]{\definemacrowithhashdoubling\@fooauthor{#1}}%
\newcommand\foocreator[1]{\definemacrowithhashdoubling\@foocreator{#1}}%
\newcommand\footitle[1]{\definemacrowithhashdoubling\@footitle{#1}}%
\newcommand\foosubject[1]{\definemacrowithhashdoubling\@foosubject{#1}}%
\newcommand\fooproducer[1]{\definemacrowithhashdoubling\@fooproducer{#1}}%

% \DefineMyHyperSetupTempMacro defines the macro \MyHyperSetupTempMacro
% to expand to a keyval-list for \hypersetup according
% to the definitions of \@foopdfborder, \@fooauthor, \@foocreator, \@footitle, 
% \@foosubject and \@fooproducer.
%
\newcommand\DefineMyHyperSetupTempMacro{%
  \edef\MyHyperSetupTempMacro{%
    \@ifundefined{@foopdfborder}{}{pdfborder={\unexpanded\expandafter{\@foopdfborder}},}%
    \csname @\@ifundefined{@fooauthor}{%
      \@ifundefined{@foocreator}{%
        \@ifundefined{@footitle}{%
          first%
        }{second}%
      }{second}%
    }{second}oftwo\endcsname{}{%
      pdfinfo={%
        \@ifundefined{@fooproducer}{}{Producer={\unexpanded\expandafter{\@fooproducer}},}%
        \@ifundefined{@foosubject}{}{Subject={\unexpanded\expandafter{\@foosubject}},}%
        \@ifundefined{@fooauthor}{}{Author={\unexpanded\expandafter{\@fooauthor}},}%
        \@ifundefined{@foocreator}{}{Creator={\unexpanded\expandafter{\@foocreator}},}%
        \@ifundefined{@footitle}{}{Title={\unexpanded\expandafter{\@footitle}},}%
      },%
    }%
  }%
}%
\makeatother

\foopdfborder{0 0 0}
\fooauthor{Me}
\foocreator{Me}
\footitle{The title}
\foosubject{A subject}
\fooproducer{LaTeX}

\DefineMyHyperSetupTempMacro

\show\MyHyperSetupTempMacro

\expandafter\hypersetup\expandafter{\MyHyperSetupTempMacro}%

\begin{document}

Some text.

\end{document}

In case besides the ε-TeX-extensions the \expanded-primitive is available also, you can combine \unexpanded with \expanded and do without temporary macro—this is a shorter implementation of the first example:

\documentclass[a4paper,12pt]{article}
\usepackage{hyperref}

\makeatletter

\newcommand\Exchange[2]{#2#1}%    

% Be aware that two consecutive hashes in the definition-text of a macro will be collapsed 
% into a single hash within the result of expanding that macro.
% Therefore something must be done for having hashes doubled within the macros that serve as
% place-holders for values of variables:
\newcommand\definemacrowithhashdoubling[2]{\@ifdefinable#1{\edef#1{\unexpanded{#2}}}}%

\newcommand\foopdfborder[1]{\definemacrowithhashdoubling\@foopdfborder{#1}}%
\newcommand\fooauthor[1]{\definemacrowithhashdoubling\@fooauthor{#1}}%
\newcommand\foocreator[1]{\definemacrowithhashdoubling\@foocreator{#1}}%
\newcommand\footitle[1]{\definemacrowithhashdoubling\@footitle{#1}}%
\newcommand\foosubject[1]{\definemacrowithhashdoubling\@foosubject{#1}}%
\newcommand\fooproducer[1]{\definemacrowithhashdoubling\@fooproducer{#1}}%

% \DeliverHyperSetupKeyValList delivers keyval-list for \hypersetup according
% to the definitions of \@foopdfborder, \@fooauthor, \@foocreator, \@footitle, 
% \@foosubject and \@fooproducer.
%
% Due to \romannumeral0-/\Exchange-expansion-trickery, the result is delivered
% after triggering two expansion-steps/after two "hits" with \expandafter:
%
\newcommand\DeliverHyperSetupKeyValList{%
  \romannumeral0\expandafter\Exchange\expandafter{%
    \expanded{%
      \@ifundefined{@foopdfborder}{}{pdfborder={\unexpanded\expandafter{\@foopdfborder}},}%
      \csname @\@ifundefined{@fooauthor}{%
        \@ifundefined{@foocreator}{%
          \@ifundefined{@footitle}{%
            first%
          }{second}%
        }{second}%
      }{second}oftwo\endcsname{}{%
        pdfinfo={%
          \@ifundefined{@fooproducer}{}{Producer={\unexpanded\expandafter{\@fooproducer}},}%
          \@ifundefined{@foosubject}{}{Subject={\unexpanded\expandafter{\@foosubject}},}%
          \@ifundefined{@fooauthor}{}{Author={\unexpanded\expandafter{\@fooauthor}},}%
          \@ifundefined{@foocreator}{}{Creator={\unexpanded\expandafter{\@foocreator}},}%
          \@ifundefined{@footitle}{}{Title={\unexpanded\expandafter{\@footitle}},}%
        },%
      }%
    }%
  }{ }%
}%
\makeatother

\foopdfborder{0 0 0}
\fooauthor{Me}
\foocreator{Me}
\footitle{The title}
\foosubject{A subject}
\fooproducer{LaTeX}

\expandafter\expandafter\expandafter\def
\expandafter\expandafter\expandafter\test
\expandafter\expandafter\expandafter{\DeliverHyperSetupKeyValList}%

\show\test

\expandafter\expandafter\expandafter\hypersetup
\expandafter\expandafter\expandafter{\DeliverHyperSetupKeyValList}%

\begin{document}

Some text.

\end{document}
Ulrich Diez
  • 28,770