% MULTINOTE (MUF) MACROS for LaTeX2e, version 1.11, % written by Herman Haverkort, 13 may 1995 % See end of file for information on warranty, distribution etc. \NeedsTeXFormat{LaTeX2e} \ProvidesPackage{hhmuf}[1995/05/13 Multinote system] \RequirePackage{hhqueue}[1995/02/14] \RequirePackage{hhutils0}[1995/03/08] % ============================================================================= % - \muf... (to set footnotes) % % \muf:{TEXT} for a ordinary footnote % \muf LABEL:{TEXT} for a footnote which is labelled LABEL, % to make it possible to reuse the footnote % later on by stating: % \muf LABEL:{} which sets the previously defined footnote % labelled LABEL. % Labels should not contain commas, periods or colons! % If you use the same footnote several times, the multinote macros try % to ensure that the actual footnote text appears at most once on % every page. % ============================================================================= \long\def\muf#1:#2{\@covermufpunct{% \h@ifespecified{#1}{\@mufsymonly #1:{#2}\muftxtonly #1:}% {\@mufsymonly tmp@:{#2}\muftxtonly tmp@:\muffire tmp@:}}} % If no label is specified, a temporary label is used. % ============================================================================= % - \mufsym... (to postpone the setting of footnote texts) % % If you use \mufsym instead of \muf, only the footnote's marker will be % set. The footnote text itself will not be set until \muffin is called. % \mufsym's syntax is similar to \muf's: you can use \mufsym:{TEXT}, % \mufsym LABEL:{TEXT} and \mufsym LABEL:{}. \mufsym is especially useful % for footnotes in `forbidden' environments, like tables and parboxes. % Just say \mufsym in the forbidden environment, and call \muffin as soon % as you get out of it. % ============================================================================= \long\def\mufsym#1:#2{\@covermufpunct{% \h@ifespecified{#1}{\edef\@@@lab{#1}}% {\stepcounter{@muftmps}\edef\@@@lab{tmp@\roman{@muftmps}}}% \h@enqueue{@@@lab}{mufs@postponed}% \@mufsymonly \@@@lab:{#2}}} % If no label is specified, one of the temporary labels tmp@i, tmp@ii etc. % is used. The label is appended to the list of postponed footnotes. % ============================================================================= % - \muffin (to set postponed footnote texts) % % \muffin sets all footnote texts which were postponed by using \mufsym % since the last call to \muffin. % ============================================================================= \def\muffin{{% \@muffin \setcounter{@muftmp}{0}% \@whilenum \value{@muftmp}<\value{@muftmps}\do {\stepcounter{@muftmp}\muffire tmp@\roman{@muftmp}:}% \setcounter{@muftmps}{0}}} \def\@muffin{% \h@ifqnonempty{mufs@postponed}{% \h@getfirst{@@@lab}{mufs@postponed}% \muftxtonly \@@@lab:% \@muffin}} % \muffin calls \@muffin to set alle postponed footnotes. Then it frees % all temporary labels and the markers assigned to them. % ============================================================================= % - \mufoff % % The \mufoff macro makes handling forbidden environments even easier % than \mufsym. This is the way to use it: % \begin{ForbiddenEnvironment} % \mufoff % Lots of bla, possibly containing calls to \muf with fingers itching % to set a footnote. However, \mufoff guarantees that those footnotes % will be postponed like \muf were \mufsym. % \end{ForbiddenEnvironment} % \muffin % % Nesting several forbidden environments which all insist on calling % \mufoff and \muffin is no problem. \mufoff redefines \muffin to do % nothing, so that only the outer \muffin will result in an attempt % to set footnotes, and that is exactly what should be done. % ============================================================================= % - \mufoff[ENVIRONMENTNAME] % % \mufoff[ENVIRONMENTNAME] makes handling forbidden environments even % easier than basic \mufoff en \muffin. Type \mufoff[ForbiddenEnvironment] % and all multinotes between \begin{ForbiddenEnvironment} and % \end{ForbiddenEnvironment} will be postponed to just after closing % the forbidden environment. % For example: if you type \mufoff[tabular] in the preamble of your % document, then \muf's in the tabular environment will be handled % correctly automatically. Because that is so useful I already included % it in this style file, like I did with \mufoff[array] and % \mufoff[eqnarray]. % ============================================================================= \def\mufoff{\@ifnextchar[\@mufoff{\def\muf{\mufsym}\def\muffin{}}} \def\@mufoff[#1]{% Stole a great deal of this macro from % Kresten Krab Thorup's ftn.sty! \@ifundefined{h@mf@#1}{% \expandafter\let\csname h@mf@#1\expandafter\endcsname \expandafter=\csname #1\endcsname \expandafter\let\csname h@mf@end#1\expandafter\endcsname \expandafter=\csname end#1\endcsname \@namedef{#1}{\bgroup\mufoff\@nameuse{h@mf@#1}}% \@namedef{end#1}{\@nameuse{h@mf@end#1}\egroup\muffin}}{}} \mufoff[tabular] \mufoff[array] \mufoff[eqnarray] \mufoff[minipage] % - \mufhire LABEL:{TEXT} (to define a footnote) % % The footnote labelled LABEL will be defined, but neither the text % nor the marker will be set. % ============================================================================= \long\def\mufhire#1:#2{{% \edef\@@@lab{#1}% \h@ifnonempty{mufgrp@\@@@lab}% {\PackageWarning{hhmuf}{Refusing to redefine multinote `#1'.\MessageBreak Muffire it first}}% {\h@ifqempty{mufsyms@avail}% {\PackageWarning{hhmuf}{Out of multinote symbols.\Messagebreak Using `?' instead}% \@namexdef{mufsym@\@@@lab}{?}}% {\h@getfirst{mufsym@\@@@lab}{mufsyms@avail}}% \h@enqueue{@@@lab}{mufgrp@\arabic{@mufgrplevel}}% \@namexdef{mufgrp@\@@@lab}{\arabic{@mufgrplevel}}% \@namegdef{muftxt@\@@@lab}{#2}% \@namexdef{mufpag@\@@@lab}{}}}} % If footnote symbols are available, the first one is chosen from the % symbol queue \mufsyms@avail. The footnote text is stored and the % page identifier is reset (see \muftxtonly for further explanation) % ============================================================================= % - \muffire LABEL: (to undefine a footnote) % % \muffire frees the footnote's label and marker, to enable their use % for footnotes which will be defined later on. % ============================================================================= \def\muffire#1:{{% \edef\@@@lab{#1}% \h@ifnonempty{mufgrp@\@@@lab}% {\edef\@tempa{\@arabic{\c@@mufgrplevel}}% \edef\@tempb{\@nameuse{mufgrp@\@@@lab}}% \ifx\@tempa\@tempb \expandafter\ifx\@nameuse{mufsym@\@@@lab}?\else \h@enqueue{mufsym@\@@@lab}{mufsyms@avail}\fi \h@delete{@@@lab}{mufgrp@\arabic{@mufgrplevel}}% \@namegdef{mufgrp@\@@@lab}{}% \else \PackageWarning{hhmuf}{Multinote `#1' was defined at level \@tempb,% \MessageBreak so cannot muffire it at level \@tempa}% \fi}% {\PackageWarning{hhmuf}{Cannot muffire multinote `#1':\MessageBreak it is not defined}}% }} % \muffire will free the footnote's label by emptying the footnote text, % and free the footnote's marker by appending it to the footnote symbol % queue \mufsyms_avail. Thus the available footnote symbols will usually be % used in turn, which establishes some nice variation in the type-setting % of your article, report or book. % ============================================================================= % - \mufsymonly... (to set a footnote's marker without the text) % % The same as \mufsym, except for the footnote text, which will _not_ % be set automatically by a following call to \muffin % ============================================================================= \def\mufsymonly#1:#2{\@covermufpunct{\@mufsymonly{#1}:{#2}}} \def\@mufsymonly#1:#2{% \h@ifspecified{#2}{\mufhire #1:{#2}}{}% \h@ifnonempty{mufgrp@#1}% {\@makemufmark{\@nameuse{mufsym@#1}}}% {\PackageWarning{hhmuf}{Reference to undefined multinote `#1'% \MessageBreak}% \@makemufmark{??}}} % ============================================================================= % - \muftxtonly LABEL: (to set a footnote's text without its marker) % % The footnote text will be set, but no marker will show up at the % reference point. % ============================================================================= \def\muftxtonly#1:{{% \h@ifnonempty{mufgrp@#1}% {\edef\@tempa{\@arabic{\c@page}}\edef\@tempb{\@nameuse{mufpag@#1}}% \ifx\@tempa\@tempb\else \@mufinsert{\@nameuse{mufsym@#1}}{\@nameuse{muftxt@#1}}% \@namexdef{mufpag@#1}{\@tempa}\fi}% {\PackageWarning{hhmuf}{Cannot type-set multinote `#1':\MessageBreak it is not defined}}}} % \muftxtonly checks if the identifier of the current page equals % the page identifier which is stored for the footnote to be set. % If so, the footnote is already set on this page, so it should not be set % again. If not so, it is set, and the current page identifier is stored. % ============================================================================= % - \mufbegin{GROUP} (to start a multinote group) % % See \mufend for explanation % ============================================================================= \def\mufbegin#1{% \muffin \stepcounter{@mufgrplevel}% \h@initqueue{mufgrp@\arabic{@mufgrplevel}}{}% \@namexdef{mufgrpname@\arabic{@mufgrplevel}}{#1}} % \mufbegin increases the nesting level counter and initializes the list % of footnote labels for the new level. It stores the group name for % matching it with the \mufend later on. % ============================================================================= % - \mufend{GROUP} (to end a multinote group) % % \mufend sets all postponed footnotes (like \muffin), and then muffires % all footnotes which had been defined since the corresponding call to % \mufbegin{GROUP}. Thus \mufbegin and \mufend establish some kind of % footnote definition environment, called a mufgroup. % Mufgroups can be nested, but if you do nest them, nest them properly. % So this is not permitted: % % \mufbegin{A}\mufbegin{B}\mufend{A}\mufend{B}, % % while this is OK: % % \mufbegin{A}\mufbegin{B}\mufend{B}\mufend{A}. % % Whenever you enter a new group, a \muffin is performed and then all % footnotes which have already been defined are frozen. You cannot fire % them until the new group is closed with \mufend. So the following is OK: % % \mufhire F:{Foo}\mufbegin{B}\mufend{B}\muffire F: % % while this is not: % % \mufhire F:{Foo}\mufbegin{B}\muffire F:\mufend{B} % % Whenever you are in a group, you cannot redefine footnotes which have % been defined already in some outer group, because in that case you % would have to muffire the footnote, which is not allowed. You cannot % even define a new footnote which is local to the group but gets the % same label as some footnote which has been defined in some outer group % (e.g. a global footnote). The muf macros are not that smart. So the % following is not allowed: % % \mufhire F:{Foo}\mufbegin{A}\mufhire F:{bar} % % If you have closed all the groups you had opened (or if you never % opened any), then you are in the outermost, nameless group. You can % close that group with \mufend{}. It will muffire all footnotes you % had defined, and automatically reopen a outermost nameless group. % So it is a kind of: \muffin \muffire ALL. % ============================================================================= \def\mufend#1{{% \edef\@tempa{#1}\edef\@tempb{\@nameuse{mufgrpname@\arabic{@mufgrplevel}}}% \ifx\@tempa\@tempb \muffin {\def\\##1{\muffire ##1:}\h@processq{mufgrp@\arabic{@mufgrplevel}}} \global\advance\c@@mufgrplevel-1 \ifnum\value{@mufgrplevel}=0\mufbegin{}\fi \else \PackageWarning{hhmuf}{Refusing to end multinote group \@tempb\ by\MessageBreak\protect\mufend{\@tempa}} \fi}} % *************************** % * LAY-OUT * % *************************** % ============================================================================= % \mufword defines the word which is used in references to multinotes. % It is `footnote'; redefine it if you like, preferably by defining the % appropriate language option (see below). % ============================================================================= \def\mufword{footnote~} % ============================================================================= % \@makemufword defines how to format a footnote's marker (in the text, not % in the insertion at the foot of the page). Redefine it if you like. % ============================================================================= \def\@makemufmark#1{\hbox{$^{#1}$}} % ============================================================================= % by default \@covermufpunct will pull periods and commas following a % footnote's marker under the marker. With some definitions of \@makemufmark % this will not be desirable: \@covermufpunct should be redefined to % \def\@covermufpunct{} then. % ============================================================================= \def\@covermufpunct#1{\def\next{\@@covermufpunct{#1}}\futurelet\@@@tok\next} \newcount\@gsavsf \def\@@covermufpunct#1{\ifx\@@@tok.\def\next{\@@@covermufpunct{#1}}\else \ifx\@@@tok,\def\next{\@@@covermufpunct{#1}}\else \def\next{#1}\fi\fi\next} \def\@@@covermufpunct#1{\global\@gsavsf=\spacefactor \rlap{\spacefactor=\@gsavsf\@@@tok\global\@gsavsf=\spacefactor}\nobreak #1% \spacefactor=\@gsavsf\@gobble} % ============================================================================= % \@makemuftext defines how to format a footnote. It takes two arguments: % #1 is the footnote's marker; #2 is the footnote text. Redefine it if you like. % ============================================================================= \long\def\@makemuftext#1#2{% \sbox\@tempboxa{ $#1$ }% \@tempdima\smallunitindent{\wd\@tempboxa}% \parindent\z@ \parskip\z@ \@setpar{% \@@par \@tempdimb\hsize\advance\@tempdimb-\@tempdima \parshape \@ne \@tempdima \@tempdimb}% \par \noindent\llap{\hbox to \smallunitindent\z@{\hss$#1$ \hss}}#2} \providecommand{\smallunitindent}[1]{10pt} % This is to prepare hhmuf for use with the hhtext class (when I write this it's % still under construction). The hhtext class will provide a \smallunitindent % macro with some self-scaling features. % ============================================================================= % The following has been taken from LaTeX2e (\@footnotetext), % with the necessary modifications. % ============================================================================= \long\def\@mufinsert#1#2{\insert\footins{% \reset@font\footnotesize \interlinepenalty\interfootnotelinepenalty \splittopskip\footnotesep \splitmaxdepth \dp\strutbox \floatingpenalty \@MM \hsize\columnwidth \@parboxrestore \protected@edef\@currentlabel{\mufword\@makemufmark{#1}}% \color@begingroup \@makemuftext{#1}{% \rule\z@\footnotesep\ignorespaces #2\@finalstrut\strutbox} \color@endgroup}} % *************************** % * SOME INTERNAL UTILITIES * % *************************** \long\def\h@ifnonempty#1#2#3{% \@ifundefined{#1}{#3}{\h@ifespecified{\csname #1\endcsname}{#2}{#3}}} % ****************************** % * OPTIONS AND INITIALIZATION * % ****************************** \newcounter{@muftmps} \newcounter{@muftmp} \newcounter{@mufgrplevel} \h@initqueue{mufs@postponed}{} \mufbegin{} \AtEndDocument{\mufend{}} % ============================================================================= % Below is a list of recognized language options. Probably their only use % is the ability to redefine \mufword. % ============================================================================= \DeclareOption{dutch}{\def\mufword{voetnoot~}} % ============================================================================= % The following specifies the footnote markers which will be used for % multinotes. You can replace it with your own specification if you like. % Please note that it makes no sense to use symbols with a well-defined % order: the muf macros will not respect it. % To make it easier to choose out of the numerous possibilities for % footnote markers I defined some sets of markers which can be selected by % specification of the appropriate option. The recognized options are: % - black 8 black symbols (requires amssymb.sty) % - circlox 12 circle and box symbols (requires amssymb.sty) % - fuss 10 miscellaneous symbols (requires amssymb.sty) % - geometry 10 geometrical symbols (requires amssymb.sty) % - misc 19 miscellaneous symbols (default) % - music 3 music symbols % - strokes 8 symbols made of thin strokes (requires amssymb.sty) % Take care that you do not select a set which is too small for your purposes. % ============================================================================= \def\@@@mufset{\mufset@misc} \DeclareOption{black}{\def\@@@mufset{\mufset@black}} \def\mufset@black{% \RequirePackage{amssymb} \h@initqueue{mufsyms@avail}{% 7 symbols \\{\bullet}\\{\blacklozenge}\\{\blacktriangledown}% \\{\clubsuit}\\{\blacksquare}\\{\blacktriangle}% \\{\blacktriangleleft}\\{\spadesuit}}} \DeclareOption{circlox}{\def\@@@mufset{\mufset@circlox}} \def\mufset@circlox{% \RequirePackage{amssymb} \h@initqueue{mufsyms@avail}{% 12 symbols \\{\oslash}\\{\odot}\\{\boxtimes}\\{\oplus}\\{\square}% \\{\circledast}\\{\boxminus}\\{\otimes}\\{\circledcirc}% \\{\boxdot}\\{\circleddash}\\{\boxplus}}} \DeclareOption{fuss}{\def\@@@mufset{\mufset@fuss}} \def\mufset@fuss{% \RequirePackage{amssymb} \h@initqueue{mufsyms@avail}{% 10 symbols \\{\ast}\\{\diamondsuit}\\{\circledast}\\{\divideontimes}% \\{\sharp}\\{\star}\\{\clubsuit}\\{\aleph}\\{\infty}% \\{\circlearrowleft}}} \DeclareOption{geometry}{\def\@@@mufset{\mufset@geometry}} \def\mufset@geometry{% \RequirePackage{amssymb} \h@initqueue{mufsyms@avail}{% 10 symbols \\{\blacklozenge}\\{\square}\\{\blacktriangledown}\\{\vartriangle}% \\{\blacksquare}\\{\triangleleft}% \\{\blacktriangle}\\{\lozenge}\\{\blacktriangleleft}\\{\triangledown}}} \DeclareOption{misc}{\def\@@@mufset{\mufset@misc}} \def\mufset@misc{% \h@initqueue{mufsyms@avail}{% 19 symbols \\{\spadesuit}\\{\triangle}\\{\ominus}\\{\clubsuit}% \\{\times}\\{\diamondsuit}\\{\otimes}\\{\wr}\\{\odot}\\{\vee}% \\{\oplus}\\{\infty}\\{\star}\\{\oslash}\\{+}\\{\triangleleft}% \\{\top}\\{\bullet}\\{\nabla}}} \DeclareOption{music}{\def\@@@mufset{\mufset@music}} \def\mufset@music{% 3 symbols \h@initqueue{mufsyms@avail}{\\{\sharp}\\{\flat}\\{\natural}}} \DeclareOption{strokes}{\def\@@@mufset{\mufset@strokes}} \def\mufset@strokes{% \RequirePackage{amssymb} \h@initqueue{mufsyms@avail}{% 8 symbols \\{\top}\\{\times}\\{\curlyvee}\\{+}\\{\veebar}\\{\nshortparallel}% \\{\barwedge}\\{\wr}}} \ProcessOptions \@@@mufset \endinput% *********************** % * FAILURES AND POSSIBLE CAUSES * % ******************************** % % ! Package hhmuf Warning: Refusing to redefine multinote `LABEL'. % (hhmuf) Muffire it first. % % If you defined a footnote labelled LABEL, using \muf, \mufsym, % \mufsymonly or \mufhire, you should call \muffire LABEL: before % defining another footnote having the same label. % % % ! Package hhmuf Warning: Out of multinote symbols. % (hhmuf) Using `?' instead. % % A marker is assigned to each footnote which has been defined. Because % the number of markers is limited, you will run out of markers if % too many footnotes have been defined at the same time. To prevent this % from happening, use \muffire to undefine footnotes as soon as you % do not need them anymore. % Keep in mind that each call to \mufsym:{TEXT} (even without a explicit % label) reserves a marker, which will not be released until the % next call to \muffin, \mufbegin or \mufend. % Also each call to \muf:{TEXT} which is placed in a `forbidden' environment % protected by \mufoff reserves a marker, which will not be released until % the environment is closed. % % % ! Package hhmuf Warning: Reference to undefined multinote `LABEL'. % % ! Package hhmuf Warning: Cannot type-set multinote `LABEL': % (hhmuf) it is not defined. % % ! Package hhmuf Warning: Cannot muffire multinote `LABEL': % (hhmuf) it is not defined. % % Should be evident. If it is not, please check if you did not close % the group in which the multinote was defined already (using \mufend). % One other mistake you could have made, is calling \muffire LABEL: % somewhere between \mufsym LABEL:{OPTIONAL-TEXT} and the first \muffin % following it. This happens implicitely if you call \muffire LABEL: % somewhere between \muf LABEL:{OPTIONAL-TEXT} in a protected forbidden % environment and the closure of that environment. % Note that if the multinote LABEL is undefined, calling for example % \muf LABEL:{} results in two warnings: one for the in-text % multinote reference marker (`Reference to undefined...'), and another % for the type-setting of the footnote itself (`Cannot type-set...'). % % % ! Package hhmuf Warning: Reference to undefined multinote `tmp_'. % (and similar messages) % % You used \muf:{} or \mufsym:{}, which does not make any sense. % % % ! Package hhmuf Warning: Multinote `LABEL' was defined at level 1, % (hhmuf) so cannot muffire it at level 3. % (and similar messages) % % Since you defined the multinote LABEL, you opened another group which % is still open. It is not possible to undefine the multinote then. % Muffire before opening the current group, or after closing it. % % % ! Package hhmuf Warning: Refusing to end multinote group `GROUPA' by % (hhmuf) \mufend{GROUPB}. % (and similar messages) % % This warning should be caused by mismatched \mufbegins and \mufends. % Remember mufgroups should be properly nested. % % % - The footnote's marker appears all right, but the text is missing % % Two possible causes: % 1. You used \mufsym but forgot \muffin. % 2. You used \muf, \muftxtonly or \muffin in some `forbidden' % environment. The constraints are the same as for ordinary % LaTeX footnotes, unless the environment is protected by % \mufoff[ENVIRONMENT-NAME]. % % % - A footnote text is set although it should not be there. % % You probably forgot some \muffin some time ago, so that the footnote % texts, which should have been set by that \muffin, are set by a following % \muffin. % % % - A footnote text appears twice on the same page. % % LaTeX could have floated a identical footnote from the previous page to % this one which cannot be detected by the multinote macros. % Another possible cause is probably the multinote macros getting the % the page number of the in-text marker wrong. This problem is very % much like the inability to start the footnote numbering every page % (which - by the way - is no problem if you use multinotes, because % they use a shift-system for their numbering). This problem can be % solved, and probably will be solved as soon as I encounter it in % practice. % In both cases correct the error `manually' by using \mufsymonly once % instead of \muf or \mufsym, or by omitting a \muftxtonly. % % % ************************************************** % * PROBLEMS TO BE SOLVED / EXTENSIONS TO BE MADE: * % ************************************************** % % - The last mentioned failure. % - Enabling multinotes under minipages. % - A switch to force muf to set footnote texts at most once at % a pair of opposite pages. % % % ******************************* % * WARRANTY, DISTRIBUTION ETC. * % ******************************* % % This is a TeX style file by Herman Haverkort. This file is distributed % in the hope that it will be useful, but without any warranty; without % even the implied warranty of merchantability or fitness for a particular % purpose. The author does not accept any responsability for any damage, % loss, injury, psychosis, annoyance, marital problems, murders etc. which % are caused by this file. % % This style file has not been tested systematically, so there are % probably undiscoverd errors in it. If you find one, if you have % trouble using this file, if you have a suggestion for an extension or % another modification, or if you are just a happy user, please report % it to: % Herman Haverkort % Heyenoordseweg 40 % NL-6813 GA Arnhem % herman@fgbbs.iaf.nl % % You are allowed to change this file, but you are not allowed to distribute % the changed version unless you obey the following: % - give the changed version another file name than the original one; % - record clearly in the changed version: % - the original name of the file; % - its original author; % - that it is a changed version; % - do not remove the restrictions on distributing this file. % % You are not allowed to take money for the distribution or use of either % this file or a changed version, except for a nominal charge for copying % etc. % % Have fun!