I'm creating my personal package. I'd like to use an option to turn on/off the line numbering provided by the package lineno.

So, my sty file contains


But if one does not have the lineno package installed it will produce an error. It one does have the package installed it will enumerate the lines.

I'd like to check if one does have lineno first and in affirmative case I'd like to be able to use my package as

\usepackage[lineno]{mysty} % to turn on the numbering


\usepackage{mysty} % default with no numbering if `lineno` does not exists

I tried this


and it works if lineno is installed. But what about if it is not?

2 Answers 2

  • Files can be tested via \IfFileExists{file}{yes}{no}.
  • The following snipset uses a switch \if@mysty@lineno that remembers the option setting lineno for package mysty. Package lineno and \linenumbers are only executed, if the option lineno was given. This way, the package lineno is not loaded unnecessarily if it is not needed.
  • Packages cannot be loaded during the option part of package files (because it would lead to reentrance problems of LaTeX's option code).

Snipset for package mysty:

\newif\if@mysty@lineno % default: false

% Option declarations of package `mysty'

    \PackageWarning{mysty}{Package lineno is not installed}%

% Execute package options

% Afterwards it is again safe to load packages

Answer to comment:

LaTeX's implementation of \IfFileExists puts the second and third argument in a macro definition. Therefore further definitions with parameters in this arguments make trouble, because the # would need doubling. The following workaround can be used:

  • I'm comparing your solution with @egregs one. I understand that both work and they only differ on the sequence of statements, that is, they are logically equivalent. Do you agree or do you see some advantage/disadvantage? Thanks.
    – Sigur
    Commented Apr 26, 2013 at 0:10
  • 1
    @Sigur Both solutions are not logically equivalent, but pretty much similar. egreg's solution only tests for the file, if needed -- in my case the warning is given earlier. (I would have deleted my solution, but my answer has more remarks/hints.) Commented Apr 26, 2013 at 0:14
  • Why is \IfFileExists{color.sty}{\RequirePackage{color}\def\alerta#1{\textcolor{red}{#1}}}{} producing the error Illegal parameter number in definition of \reserved@a {}?
    – Sigur
    Commented Apr 26, 2013 at 0:48
  • 3
    @Sigur "Suboptimal" implementation of \IfFileExists in the LaTeX kernel. Instead of \IfFileExists{file}{yes}{no} the workaround \IfFileExists{file}\@firstoftwo\@secondoftwo{yes}{no} can be used. Here \IfFileExists{color.sty}\@firstofone\@gobble{\RequirePackage{color}\newcommand*{\alerta}[1]{\textcolor{red}{#1}}} can be used. Commented Apr 26, 2013 at 1:07

Here's what you can put in mysty.sty:





    {\PackageWarningNoLine{mysty}{You requested `lineno.sty' which\MessageBreak
       doesn't exist on your system}}

Then if you call \usepackage[lineno]{mysty} you'll load the package or will be warned it doesn't exist. Otherwise lineno won't be loaded.

  • Just a question: \ifmysty@lineno must have this format or it is only an easy way to remember some names? That is, is necessary to use \if<name of the package>@<name of the option>?
    – Sigur
    Commented Apr 26, 2013 at 0:02
  • 1
    @Sigur The conditional can be named as you wish (so long as it begins with if). But it's common (and good) practice to use some kind of prefix for your package's commands to avoid name clashes.
    – egreg
    Commented Apr 26, 2013 at 0:07
  • 2
    A switch name that is defined by \newif must start with \if. The rest of the name is free. But \newif does not check, whether the name is already defined. Using the package name (or similar unique prefix) for internal commands make it easier to avoid name clashes. Commented Apr 26, 2013 at 0:09
  • 1
    @HeikoOberdiek Actually LaTeX doesn't enforce \newif\if..., but funny things happen if you say \newif\foo. ;-)
    – egreg
    Commented Apr 26, 2013 at 0:11
  • 2
    @egreg Yes, I should have used "should" instead of "must". \newif needs to define \<foo>true and \<foo>false for \newif\if<foo>. LaTeX just gobbles the first two characters from if<foo> to get <foo>. The implementation of plain TeX for \newif requires that the switch name starts with if. Otherwise it triggers a TeX error. In LaTeX the setter functions for \newif\foo would become \otrue and \ofalse. Commented Apr 26, 2013 at 0:20

You must log in to answer this question.

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