14

I'm currently in the process of writing my first document class file (a personalized resume class), and I want to get a better understanding of what exactly I'm doing. So, right now I'm setting up commands that allow for values to be assigned to variables (not sure if that's really the word I should be using), through a structure like this:

\newcommand{\institution}[1]{\def\@institution{#1}}
\newcommand{\datesattended}[1]{\def\@datesattended{#1}}
\newcommand{\degree}[1]{\def\@degree{#1}}

So, in the .tex file, the user can use the command \institution{University of Whatever} to save the string "University of Whatever" to \@institution, which is then later called within the class file by another command.

All of this works as I want it to, but now I'm hoping to create some conditional expressions to control the output. Like, I have a command \education that when called in the document will format an education section for a resume given the institution name, dates attended, degree info, etc. that the user had already entered. I want to be able to set it up in the class file to check if these \@variable variables have been defined, and then format the output differently based on which are defined and which are empty.

Primarily, I think a lot of my problem is that I don't actually understand what the \@variable definitions are or the scope of what I can do with them.

A full example of what I'm trying to achieve would be along the lines of (in LaTeX/pseudo):

\newcommand{\showeducation}{%
    \@institutionname -- \@degree
    if \@datesattended is defined:
        \newline \@datesattended
    clear \@institutionname, \@datesattended, \@degree
}

So, if \@datesattended were defined, the formatting would change to accommodate it. Otherwise, the command would just pass over it, printing the information that was given.

4
  • question's a bit vague to answer but note \def is just the primitive underlying \newcommand so there is no difference in the type of construct defined \degree and \@degree are both just control sequences referring to macros defined in your document, the @ is just a letter in this context, it does not denote a "variable". You could use \newcommand{\degree}[1]{\newcommand\@degree{#1}} or \def\degree#1{\def\@degree{#1}} Apr 18, 2015 at 18:31
  • The \@somename macros are 'considered' internal commands which are not to be applied by the 'ordinary' LaTeX user (thereby being kernel or somewhat critical commands controlling a lot of internal setups, which may be corrupted by an unexperienced user)
    – user31729
    Apr 18, 2015 at 18:36
  • Your are after \ifdefined\somecommand ... \else... \fi . It's a primitive
    – user31729
    Apr 18, 2015 at 18:40
  • For this sort of thing, you might find a key-value approach offers a lot more flexibility. Nesting conditions can quickly become a frustrating experience.
    – jon
    Apr 18, 2015 at 20:27

2 Answers 2

13

There is nothing special about \@variable commands. They are just macros, for storing content rather than performing other operations. As such it's possible to test for being defined, by using \ifdefined, a (e-TeX) primitive.

\documentclass[11pt,a4paper]{article}


\makeatletter

\newcommand{\@institutionname}{Ministry of Silly Walks}
\newcommand{\@degree}{Minster of Silly Walks}

%\newcommand{\@datesattended}{1969}


\newcommand{\showeducation}{%
    \@institutionname\ -- \@degree
    \ifdefined\@datesattended 
        \newline \@datesattended  % Please use some 'better' setup here
        \else
     \let\@institutionname\relax
     \let\@datesattended\relax 
     \let\@degree\relax
     \fi
}

\makeatother


\begin{document}

\showeducation   % Date should not be printed

\makeatletter
\newcommand{\@datesattended}{1969}
\makeatother

\showeducation % Now it should be printed, but the rest is \relax`ed


\end{document}

Edit The same should be achievable using \ifdef from etoolbox package

5
  • Perfect! That is exactly what I wanted. Thank you!
    – Kevin
    Apr 18, 2015 at 18:51
  • @Kevin: You're welcome ;-)
    – user31729
    Apr 18, 2015 at 19:04
  • @barbarabeeton: That's the original code by the OP, not mine.. It's not my intention to introduce whatever improvements, just to show how \ifdefined works. But thanks
    – user31729
    Apr 18, 2015 at 19:15
  • @barbarabeeton What improvements were you suggesting? I'm certainly open to constructive criticism regarding whatever things I've inevitably done wrong or poorly.
    – Kevin
    Apr 18, 2015 at 19:32
  • @Kevin: She referred to the -- stuff. See my edited example, where I added a ` after \@institutionname` to provide the correct spacing
    – user31729
    Apr 18, 2015 at 19:33
11

Maybe better than \newcommand[1]... is usage of toks registers:

\newtoks\institution  \newtoks\datesattended  \newtoks\degree

If user says

\institution{Ministry of Silly Walks}

then you can use this value in your macros as:

\the\institution

If you need to test, if the value of the "variable" was already set, you can do:

\if\relax\the\degree\relax The degree isn't set.\else The degree is set.\fi

You must log in to answer this question.

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