%D \module %D [ file=page-mar, % moved here from main-001 %D version=1997.03.31, %D title=\CONTEXT\ Page Macros, %D subtitle=Marginal Things, %D author=Hans Hagen, %D date=\currentdate, %D copyright={PRAGMA ADE \& \CONTEXT\ Development Team}] %C %C This module is part of the \CONTEXT\ macro||package and is %C therefore copyrighted by \PRAGMA. See mreadme.pdf for %C details. %D Support for margin words is one of the reasons for writing %D \CONTEXT. Over time support for marginal content has been %D extended en enhanced. Therefore it's always good to watch %D out for unexpected side effects. \writestatus{loading}{ConTeXt Page Macros / Maginal Things} \unprotect %D There are three categories and their historically grown meaning is %D as follows: %D %D marginlines: these are flushed relative to the start of a line and %D need to be invoked there. %D %D marginwords: these can be issued in the text flow and will migrate %D sidewards; in spite of the name, it can be a paragraph of text as %D well, but normally it's words. %D %D margintexts: these can be set beforehand and are flushed at the %D next paragraph of text (of header) %D %D While these mechanisms were rather separated, they now are slightly %D more integrated. Instead of low level instances we now have a mechanism %D for defining additional ones. %D \macros %D {inleftedge,inleftmargin,inrightmargin,inrightedge} %D %D The fast and clean way of putting things in the margin is %D using \type{\rlap} or \type{\llap}. Unfortunately these %D macro's don't handle indentation, left and right skips. We %D therefore embed them in some macro's that (force and) %D remove the indentation and restore it afterwards. \def\definemarginline {\dodoubleargument\dodefinemarginline} \def\dodefinemarginline[#1][#2]% {\getparameters [\??im\??im#1] [\c!location=\v!left, \c!distance=\zeropoint, \c!width=\leftmarginwidth, \c!hoffset=\leftmargindistance, \c!command=, #2]% \unexpanded\setvalue{#1}{\dohandlemarginline{#1}}} \def\marginlineparameter #1{\csname\??im\??im\currentmarginline#1\endcsname} \def\marginlineexecuter #1#2{\executeifdefined{\??im\??im\currentmarginline#1}{#2}} \def\dohandlemarginline#1% #2 {\def\currentmarginline{#1}% \csname\s!do\??im\??im\executeifdefined{\??im\??im#1\c!location}\v!left\endcsname{#1}} % {#2} \def\doleftmarginline#1#2% #1 is redundant (we can remove it when we group dohandlemarginline; maybe ... {\pushindentation \llap {\def\currentmarginline{#1}% \postsignalrightpage \hsize\marginlineparameter\c!width\relax \marginlineexecuter\c!command\firstofoneargument{#2}\relax \hskip\dimexpr +\leftskip +\compensatedinnermakeupmargin +\marginlineparameter\c!hoffset +\marginlineparameter\c!distance \relax}% \popindentation \ignorespaces} \def\dorightmarginline#1#2% #1 is redundant {\pushindentation \rlap {\def\currentmarginline{#1}% \postsignalrightpage \hskip\dimexpr +\hsize -\rightskip +\compensatedinnermakeupmargin +\marginlineparameter\c!hoffset +\marginlineparameter\c!distance \relax \hsize\marginlineparameter\c!width \marginlineexecuter\c!command\firstofoneargument{#2}}% \popindentation \ignorespaces} \long\def\installmarginlinehandler#1#2{\setvalue{\s!do\??im\??im#1}{#2}} \installmarginlinehandler \v!left {\doleftmarginline} \installmarginlinehandler \v!right {\dorightmarginline} \installmarginlinehandler \v!inner {\presignalrightpage\doifrightpageelse\doleftmarginline \dorightmarginline} \installmarginlinehandler \v!outer {\presignalrightpage\doifrightpageelse\dorightmarginline\doleftmarginline } \definemarginline[inleftmargin] [\c!location=\v!left, \c!width=\leftmarginwidth, \c!distance=\leftmargindistance, \c!hoffset=\zeropoint] \definemarginline[inrightmargin][\c!location=\v!right,\c!width=\rightmarginwidth,\c!distance=\rightmargindistance,\c!hoffset=\zeropoint] \definemarginline[inleftedge] [\c!location=\v!left, \c!width=\leftedgewidth, \c!distance=\leftedgedistance, \c!hoffset=\leftmargintotal] \definemarginline[inrightedge] [\c!location=\v!right,\c!width=\rightedgewidth, \c!distance=\rightedgedistance, \c!hoffset=\rightmargintotal] \definemarginline[inoutermargin][\c!location=\v!outer,\c!width=\outermarginwidth,\c!distance=\outermargindistance,\c!hoffset=\zeropoint] \definemarginline[ininnermargin][\c!location=\v!inner,\c!width=\innermarginwidth,\c!distance=\innermargindistance,\c!hoffset=\zeropoint] \definemarginline[inouteredge] [\c!location=\v!outer,\c!width=\outeredgewidth, \c!distance=\outeredgedistance, \c!hoffset=\outermargintotal] \definemarginline[ininneredge] [\c!location=\v!inner,\c!width=\inneredgewidth, \c!distance=\inneredgedistance, \c!hoffset=\innermargintotal] \definemarginline[atleftmargin] [\c!location=\v!left, \c!command=\lrlap,\c!width=\zeropoint,\c!distance=\zeropoint,\c!hoffset=\zeropoint] \definemarginline[atrightmargin][\c!location=\v!right,\c!command=\rllap,\c!width=\zeropoint,\c!distance=\zeropoint,\c!hoffset=\zeropoint] \ifx\lrlap\undefined \def\lrlap#1{\llap{\rlap{#1}}} \fi \ifx\rllap\undefined \def\rllap#1{\rlap{\llap{#1}}} \fi \def\lrlap#1{\llap{\rlap{#1}}} \def\rllap#1{\rlap{\hskip\hsize\llap{#1}}} %D We want to keep things efficient and therefore only handle %D situations like: %D %D \startbuffer %D \inleftedge {fine} some text \par %D \strut \inleftmargin {fine} some text \par %D \noindent \inrightmargin {fine} some text \par %D \noindent \strut \inrightedge {fine} some text \par %D \stopbuffer %D %D \typebuffer %D %D which looks like: %D %D \bgroup %D \getbuffer %D \parindent 30pt %D \getbuffer %D \egroup %D %D A torture test: %D %D \starttyping %D \def\TestLine#1#2{\backgroundline[#1]{\strut\white\tttf#2~\recurselevel}} %D %D \startbuffer %D \inleftmargin {\TestLine{red} {lm}} test test test \par %D \inrightmargin{\TestLine{green} {rm}} test test test \par %D \inleftedge {\TestLine{red} {le}} test test test \par %D \inrightedge {\TestLine{green} {re}} test test test \par %D \inoutermargin{\TestLine{blue} {om}} test test test \par %D \ininnermargin{\TestLine{yellow}{im}} test test test \par %D \inouteredge {\TestLine{blue} {oe}} test test test \par %D \ininneredge {\TestLine{yellow}{ie}} test test test \par %D \atleftmargin {\TestLine{red} {alm}} \hfill test \par %D \atrightmargin{\TestLine{green} {arm}} test \hfill \par %D \stopbuffer %D %D \dorecurse{40}\getbuffer \page %D \stoptyping %D New, yet undocumented: %D %D used for pascal: %D %D \starttyping %D \index {test} test \index {west} west \index {rest} rest %D %D \startnarrower %D \placeregister[index][alternative=b,command=\atleftmargin] %D \stopnarrower %D \stoptyping % todo: compensate distance when setuplayout[textwidth=..] % todo: generalize margin/edge model, now too much duplication %D The next bunch of macros looks messy which is due to its %D multi-purpose character. \chardef\margincontentdisplacement \zerocount \let \margincontentdistance \!!zeropoint \let \margincontenthoffset \!!zeropoint \def \margincontentlines {1} \def \margincontenttag {0} \let \margincontentseparator \empty \def \margincontentstrutheight {\strutht} \newcount\margincontentlevel \newdimen\margincontentheight \def\setupinmargin {\dodoubleempty\dosetupinmargin} \def\dosetupinmargin[#1][#2]% {\ifsecondargument \processcommalist[#1]{\dodosetupinmargin[#2]}% becomes [#2]{##1} \else \getparameters[\??im][#1]% \fi} % \def\dodosetupinmargin[#1]#2% [settings]{class} % {\checkinmargin[#2]% % \getparameters[\??im#2][#1]} \def\dodosetupinmargin[#1]#2% [settings]{class} {\checkinmargin[#2]% \getparameters[\??im#2][#1]% % will become an \everyinmarginsetup thing \ifcase\executeifdefined{\??im#2\c!sidemethod}{0}\else \enableparpositions \fi} \def\checkinmargin[#1]% {\ifundefined{\??im#1\c!offset}% this offset is related to framed ! \addtocommalist{#1}\inmargintaglist \presetmargintext[#1]% \fi} \def\presetmargintext[#1]% {\presetlocalframed [\??im#1]% \getparameters [\??im#1] [\c!frame=\v!off, \c!offset=\v!overlay, \c!line=1, \c!separator=, \c!width=\v!broad, \c!distance=, % empty = signal \c!hoffset=\zeropoint, \c!style=\@@imstyle, \c!color=\@@imcolor, \c!strut=\@@imstrut, \c!location=\@@imlocation, \c!align=\@@imalign, \c!before=\@@imbefore, \c!after=\@@imafter]} \newdimen\naturalmargincontentheight \def\makemargintextblock#1#2#3% width l r content {\bgroup \forgetall % added, else problems with 'center' and nested itemize \dontcomplain \hsize\getvalue{\??im#1\c!width}\relax \doifnumberelse\margincontenttag {\ifcase\margincontenttag\relax \edef\margincontenttag{#1}% first one is setups id as well \fi} \donothing \doifnumberelse\margincontenttag {\ifnum\margincontenttag>25 % to be translated \writestatus\m!systems{potential margin stack overflow (\margincontenttag)}% \fi} \donothing % we need to preserve {a,b,c} kind of settings \let\margincontentalign#1% \processallactionsinset [\getvalue{\??im\margincontenttag\c!align}] [ \v!yes=>\let\margincontentalign#1, \v!no=>\let\margincontentalign\v!normal, \v!inner=>\let\margincontentalign#1, \v!outer=>\let\margincontentalign#2, \v!left=>\let\margincontentalign\v!left, \v!middle=>\let\margincontentalign\v!middle, \v!right=>\let\margincontentalign\v!right]% \doifvaluesomething{\??im\margincontenttag\c!align} % watch {} around set {\edef\margincontentalign{{\getvalue{\??im\margincontenttag\c!align},\margincontentalign}}}% % \expanded{\getparameters[\??im\margincontenttag][\c!align=\margincontentalign]}% % \edef\margincontentstrut{\getvalue{\??im\margincontenttag\c!strut}}% \savestrut % \setbox\scratchbox\vbox\localframed [\??im\margincontenttag] [\c!strut=\v!no,\c!offset=\v!overlay] % strut handled internally {\decrement\margincontentlines \dorecurse\margincontentlines{\savedstrut\endgraf\nointerlineskip}% ! savedstrut \@@imbefore \dostartattributes{\??im\margincontenttag}\c!style\c!color\empty \dosetupstrut[\margincontentstrut]% was: \setstrut % yes or no \begstrut#3\endstrut\endgraf \xdef\margincontentstrutheight{\the\strutht}% so that it's known outside the framed \dostopattributes \@@imafter}% \global \naturalmargincontentheight\ht\scratchbox \global\advance\naturalmargincontentheight\dp\scratchbox \doif\@@imstack\v!yes {\def\overlappingmargin{-20\scaledpoint}% test value, maybe .25\strutboxdp, maybe configurable \setbox\scratchbox\vbox{\stackeddown\vbox{\box\scratchbox}}}% new \ht\scratchbox\strutht \dp\scratchbox\strutdp % nieuw \box\scratchbox \egroup} %D The stacker permits constructs like: %D %D \starttyping %D \setupinmargin[stack=yes] %D %D \inleft{test 1}test\break %D \inleft{test 2}test\break %D \inleft{test 1} %D \input tufte %D \inleft{test 1} %D \inleft{test 2} %D \inleft{test 3} %D \input tufte %D \inleft{test 1} %D \inleft{test 2\endgraf test 3} %D \inleft{test 4} %D \input tufte %D \inleft{test 1} %D \inleft{test 2\endgraf test 3} %D \inleft{test 4\endgraf test 5\endgraf test 6} %D \inleft{test 7\endgraf test 8\endgraf test 9} %D \input tufte %D \stoptyping %D This approach permits us to implement a better mechanism %D later. We need the \type {\graphicvadjust} in order to %D handle: %D %D \starttyping %D \inleft{test} {\red \dorecurse{40}{test }\par} %D {\red \inleft{test} \dorecurse{40}{test }\par} %D \stoptyping %D %D The outer margin color is either black or color set as %D main text color. \newif\ifrightmargin % documenteren \ifx\dopositionmarginbox\undefined \def\dopositionmarginbox#1{\graphicvadjust{\box#1}} \fi % watch out, margin dimensions are swapped locally (\swapmargins) % with \margincontentmethod one can control pagebreaks % % 0 no break % 1 each entry is one line % 2 only natural height % 3 also stack height \chardef\margincontentmethod \plusthree % beware: 1 = old method \chardef\marginpagecheckmethod\plusone \def\margincontentextralines{1} % old method, play safe \def\nofmargincontentlines {0} \def\doplacemargintext#1#2#3#4% {\dontcomplain \strut \doifsomething{#1} {\def\margincontenttag{#1}}% \doifinsetelse{\margincontenttag}{\v!left,\v!right} % ugly hack {\let \margincontentdistance \empty % signal \let \margincontenthoffset \zeropoint} {\edef\margincontentdistance{\executeifdefined{\??im\margincontenttag\c!distance }\empty }% signal \edef\margincontenthoffset {\executeifdefined{\??im\margincontenttag\c!hoffset }\zeropoint}}% \edef\margincontentlines {\executeifdefined{\??im\margincontenttag\c!line }\plusone }% \edef\margincontentseparator {\executeifdefined{\??im\margincontenttag\c!separator}\donothing}% \setbox\scratchbox\hbox{#4}% % todo: make sure that color stack works \ifcase\margincontentmethod \scratchdimen\zeropoint \or % old method \scratchdimen\ht\scratchbox \advance\scratchdimen\dp\scratchbox \or \scratchdimen\naturalmargincontentheight \or \scratchdimen\naturalmargincontentheight \ifx\laststackvmove\undefined\else\global\advance\scratchdimen\laststackvmove\fi \fi \ifdim\scratchdimen>\margincontentheight \global\margincontentheight\scratchdimen \fi \setbox\scratchbox\hbox {#2{\hskip#3\strut \ifcase\margincontentdisplacement % normal, move strutheight up \scratchdimen\strutdp \advance\scratchdimen \margincontentstrutheight \advance\scratchdimen -\strutht \raise\scratchdimen \or % low, obey vadjust \fi \box\scratchbox}}% \ht\scratchbox\zeropoint \dp\scratchbox\zeropoint \gdef\margincontentstrutheight{\the\strutht}% %\graphicvadjust{\box\scratchbox}} % fails in high math lines, let it be %\hbox{\lower\strutdp\box\scratchbox}} % alas, wrong lapping, therefore useless \dopositionmarginbox\scratchbox} % \def\domarginblockskip#1% % {\hskip\margincontenthoffset % \hskip\compensatedinnermakeupmargin\relax % \doifelsenothing\margincontentdistance % {\hskip\getvalue{\??im#1\c!distance}} % {\hskip\margincontentdistance}% % \relax} \def\domarginblockskip#1% {\doifelsenothing\margincontentdistance {\hskip\dimexpr +\margincontenthoffset +\compensatedinnermakeupmargin +\csname\??im#1\c!distance\endcsname \relax} {\dimexpr +\margincontenthoffset +\compensatedinnermakeupmargin +\margincontentdistance \relax}% \relax} \def\doleftmarginblock#1#2% {\doplacemargintext{#1}\llap\zeropoint {\llap{\placemargincontentseparator}% \makemargintextblock\v!left\v!right{#2}% \domarginblockskip\v!left}} \def\dorightmarginblock#1#2% {\doplacemargintext{#1}\rlap\hsize {\hskip\textwidth\hskip-\hsize % new: hsize correction \domarginblockskip\v!right \makemargintextblock\v!right\v!left{#2}% \rlap{\placemargincontentseparator}}} \def\placemargincontentseparator {\ifnum\margincontentlevel>\zerocount \ifx\margincontentseparator\empty\else \bgroup \scratchdimen\margincontentlines\lineheight \advance\scratchdimen -\lineheight \lower\scratchdimen\hbox{\margincontentseparator}% \egroup \fi \fi} \newbox\marginconstructbox \def\doinmarginswapped#1#2#3#4% {\iffirstsidefloatparagraph\nowhitespace\fi % zo laat mogelijk \setbox\marginconstructbox\hbox\bgroup % prevents page break in the middle of construction \startsignalrightpage \doifswappedrightpageelse {\rightmargintrue #2} {\rightmarginfalse#1} {#3}% setups {#4}% content \stopsignalrightpage \egroup \unhbox\marginconstructbox} % history made this a bit complicated, the +/- was needed before % we had enough mem/hash to do the page correction \edef\inmargintaglist{+,-,\v!low,\v!left,\v!right,\v!inner,\v!outer} % the old one: % % \def\doinmargin[#1][#2][#3][#4][#5]% #6 #7 % {\doifcommonelse{+,-,\v!laag}{#4} % {\dodoinmargin[#1][#2][#3][#4][#5]} % {\dodoinmargin[#1][#2][#3][][#4]}} % % an alternative: % % \letvalue{\??im\v!laag\c!offset}\empty % \letvalue{\??im +\c!offset}\empty % \letvalue{\??im -\c!offset}\empty % % \def\doinmargin[#1][#2][#3][#4][#5]% #6 #7 % {\doifnumberelse{#4} % {\dodoinmargin[#1][#2][#3][#4][#5]} % {\doifdefinedelse{\??im#4\c!offset} % {\dodoinmargin[#1][#2][#3][#4][#5]} % {\dodoinmargin[#1][#2][#3][][#4]}}} % % the problem is that we need to keep downward compatibility % with respect to the first argument thing a reference or a % directive; the alternative is to force users to pass a % directive along with a reference; anyhow, as long as one % does not use references that have the same name as a % directive we can use the (slow) alternative \def\doinmargin[#1][#2][#3][#4][#5]% #6 #7 {\expanded{\doifinsetelse{#4}{\inmargintaglist}} {\dodoinmargin[#1][#2][#3][#4][#5]} {\dodoinmargin[#1][#2][#3][][#4]}} \def\defineinmargin {\doquadrupleempty\dodefineinmargin} \def\dodefineinmargin[#1][#2][#3][#4]% {\doifassignmentelse{#4} {\setupinmargin[#1][#4]% \setvalue{#1}{\indentation\doquintupleempty\doinmargin[#2][#3][#1]}} {\setvalue{#1}{\indentation\doquintupleempty\doinmargin[#2][#3][#4]}}} \defineinmargin [inleft] [\v!left] [\v!normal] % takes left settings \defineinmargin [inright] [\v!right] [\v!normal] % takes right settings \defineinmargin [ininner] [\v!inner] [\v!normal] % takes left/right settings \defineinmargin [inouter] [\v!outer] [\v!normal] % takes left/right settings \defineinmargin [inmargin] [\@@imlocation] [\v!normal] % takes left/right settings \defineinmargin [inother] [\@@imlocation] [\v!reverse] % takes left/right settings \def\inothermargin{\inother} %D This permits definitions like: %D %D \starttyping %D \defineinmargin [SomePlace] [inner] [normal] [distance=1cm] %D \defineinmargin [SomePlace] [inner] [normal] [SomePlace] \setupinmargin[SomePlace][distance=1cm] %D \defineinmargin [MyPlace] [inner] [normal] [SomePlace] %D \defineinmargin [YourPlace] [inner] [normal] [SomePlace] %D \stoptyping %D %D A torture test: %D %D \starttyping %D \startbuffer %D \inleft {\TestLine{red} {l}} test test test \par %D \inright {\TestLine{green} {r}} test test test \par %D \inmargin {\TestLine{blue} {m}} test test test \par %D \inothermargin{\TestLine{yellow} {x}} test test test \par %D \ininner {\TestLine{cyan} {i}} test test test \par %D \inouter {\TestLine{magenta}{o}} test test test \par %D \stopbuffer %D %D \dorecurse{80}\getbuffer \page %D \stoptyping %D %D and %D %D \starttyping %D \defineinmargin [InOuterA] [outer] [normal] [distance=0cm] %D \defineinmargin [InOuterB] [outer] [normal] [distance=1cm] %D \defineinmargin [InOuterC] [outer] [normal] [distance=2cm,line=2] %D %D \startbuffer %D \InOuterA{\TestLine{red} {A}} test test test \par %D \InOuterB{\TestLine{green}{B}} test test test \par %D \InOuterC{\TestLine{blue} {C}} test test test \par %D \stopbuffer %D %D \dorecurse{80}\getbuffer \page %D %D \dorecurse{10}{\inleft {one} test \inleft {two} test } \page %D %D \start %D \margintext {one} \margintext {two} \input thuan \par %D \setupinmargin[1][line=3,distance=1cm] %D \margintext [1]{one} %D \margintext [2]{two} %D \input thuan \page %D \stop %D %D \setupinmargin[3][location=inner,distance=1cm] %D \setupinmargin[4][location=outer,distance=2cm] %D %D % \setupinmargin[left] [line=2] %D % \setupinmargin[right][line=2] %D %D \dorecurse %D {10} %D {\margintext {\kern3cm\TestLine{blue}{none}} %D \margintext[3] {\TestLine{darkgray}{3}} %D \margintext[4] {\TestLine{darkgray}{4}} %D \margintext[left] {\TestLine{red} {left}} %D \margintext[right]{\TestLine{green} {right}} %D \margintext[inner]{\TestLine{cyan} {inner}} %D \margintext[outer]{\TestLine{magenta} {outer}} %D \input thuan \endgraf} %D %D \dorecurse{10}{\margintext{test\\test\\test} \input thuan \endgraf} %D \stoptyping % Test case: % % \setuppagenumbering[alternative=doublesided] \setupwhitespace[medium] % % \placefigure[right]{}{\externalfigure[dummy][width=2cm]} % \input tufte \inothermargin{test} \input tufte % \def\dodoinmargin[#1][#2][#3][#4][#5]#6% % {\bgroup % \forgetall % otherwise sidefloat problems, added 2005/07/20, maybe dangerous % \postponenotes % group is (somehow) needed % \doifinsetelse\v!low{#4} % {\chardef\margincontentdisplacement\plusone} % {\chardef\margincontentdisplacement\zerocount}% % \doif\v!reverse{#2} % {\swapmacros\dorightmarginblock\doleftmarginblock}% % \processaction % [#1] % [ \v!left=>\let\next\doleftmarginblock, % no swapping % \v!right=>\let\next\dorightmarginblock, % no swapping % \v!inner=>\def\next{\doinmarginswapped\dorightmarginblock\doleftmarginblock }, % \v!outer=>\def\next{\doinmarginswapped\doleftmarginblock \dorightmarginblock}, % \s!unknown=>\ifdoublesided % \doifcommonelse{+,-}{#4} % {\def\next{\doinmarginswapped\dorightmarginblock\doleftmarginblock }} % {\def\next{\doinmarginswapped\doleftmarginblock \dorightmarginblock}}% % \else % \let\next\doleftmarginblock % \fi]% % \next{#3}{#6}% % \rawpagereference\s!mar{#5}% naar binnen ! ! ! ! % \flushnotes % \egroup % don't forget the group % \ignorespaces} % test first % % setupsystem[random=1235] % % \setupinmargin[left][sidemethod=3] % \dorecurse{10}{test \fakewords{20}{40} test \inleft{test\\test} test \fakewords{20}{40} \par} % \page % \setupinmargin[left][sidemethod=4] % \dorecurse{40}{test \fakewords{50}{80} test \inleft{test\\test} \par} % \page \def\dodoinmargin[#1][#2][#3][#4][#5]#6% {\bgroup % \tracingall % old stuff, a bit tricky, but now interfaced \edef\currentmargincontent{#1}% \chardef\marginrepositionmethod\executeifdefined{\??im\currentmargincontent\c!sidemethod }\plusone \chardef\margincontentmethod \executeifdefined{\??im\currentmargincontent\c!textmethod }\plusthree \chardef\marginpagecheckmethod \executeifdefined{\??im\currentmargincontent\c!splitmethod}\plusone % so far \forgetall % otherwise sidefloat problems, added 2005/07/20, maybe dangerous \postponenotes % group is (somehow) needed \doifinsetelse\v!low{#4} {\chardef\margincontentdisplacement\plusone} {\chardef\margincontentdisplacement\zerocount}% \doif\v!reverse{#2} {\swapmacros\dorightmarginblock\doleftmarginblock}% \processaction [#1] [ \v!left=>\let\next\doleftmarginblock, % no swapping \v!right=>\let\next\dorightmarginblock, % no swapping \v!inner=>\def\next{\doinmarginswapped\dorightmarginblock\doleftmarginblock }, \v!outer=>\def\next{\doinmarginswapped\doleftmarginblock \dorightmarginblock}, \s!unknown=>\ifdoublesided \doifcommonelse{+,-}{#4} {\def\next{\doinmarginswapped\dorightmarginblock\doleftmarginblock }} {\def\next{\doinmarginswapped\doleftmarginblock \dorightmarginblock}}% \else \let\next\doleftmarginblock \fi]% \next{#3}{#6}% \rawpagereference\s!mar{#5}% naar binnen ! ! ! ! \flushnotes \egroup % don't forget the group \ignorespaces} % dit zijn voorlopig lokale commando's / vervallen % % \def\woordinmarge {\indentation\doquintupleempty\doinmargin[\@@implaats][\inleftmargin][\inrightmarge]} % % \def\woordinlinker {\inleftmargin } % vervallen % \def\woordinrechter{\inrechtermarge} % vervallen % Some day: \definemarking[\v!margetitel] %D Now come the margin text collectors. The collected content is %D flushed at every paragraph by the following macro. Note for %D myself: here the location (plaats) is no longer a tag (number). % gone: \def\doflushmargincontent{\doinmargin[\@@implaats][\v!normaal][]} % + [#1][#2]{#3}} %D These are now all the same (long ago they had different %D implementations, somewhere in Sork time if I remember %D right). \def\margintext {\dodoubleempty\domargincontent} \def\marginword {\margintext} \def\margintitle{\margintext} % txt mark as well \newtoks\collectedmargintexts % so .. delayed! \chardef\margintextcollected \zerocount \def\domargincontent[#1][#2]#3% we used to check for #2/#1 being number, no longer now {\global\chardef\margintextcollected\plusone \edef\margincontenttag{#1}% \ifx\margincontenttag\empty \global\advance\margincontentlevel\plusone \edef\margincontenttag{\number\margincontentlevel}% \fi \checkinmargin[\margincontenttag]% \doglobal \appendetoks \noexpand \checkinmargin[\margincontenttag]% \noexpand \doinmargin[\executeifdefined{\??im\margincontenttag\c!location}\@@imlocation][\v!normal][\margincontenttag][\margincontenttag][#2]% \to \collectedmargintexts \doglobal \appendtoks {#3}% \to \collectedmargintexts} \let\restoreinterlinepenalty\relax \def\flushmargincontents % plural {\restoreinterlinepenalty % here? \ifcase\margintextcollected\else % called quite often, so we \expandafter\doflushmargincontents % speed up the \fi scan by \fi} % using a \do.. \def\doflushmargincontents % links + rechts {\bgroup \forgetall \global\margincontentheight\zeropoint \startsignalrightpage \the\collectedmargintexts \signalrightpage \stopsignalrightpage \resetmargincontent % dirty tricks \ifcase\margincontentmethod \donefalse \else\ifinsidecolumns % brrrr \donetrue % how fuzzy \else\ifdim\margincontentheight>\lineheight\relax \donetrue % how dirty \else \donefalse % how needed \fi\fi\fi \savemargincontentlines \ifdone \advance\margincontentheight \margincontentextralines\lineheight \ifdim\pagegoal>\pagetotal \bgroup % preserve \margincontentheight \advance\margincontentheight \pagetotal \ifdim\margincontentheight>\pagegoal \egroup \ifcase\marginpagecheckmethod % disabled \or \setmargincontentpenalties \or % potentially dangerous, maybe better a \goodbreak; the problem is that % there can be a penalty there, which we then overload and we also introduce % nasty side effects, so, we drop this option % \vadjust pre {\page}% \fi \else \egroup \fi \fi \else % We need the above because interlinepenalties overrule vadjusted \nobreaks. % a bit dangerous \vadjust{\nobreak}% \fi \egroup} \def\setmargincontentpenalties {\getnoflines\margincontentheight \keeplinestogether\noflines} \def\savemargincontentlines {\bgroup \advance\margincontentheight \margincontentextralines\lineheight % 1 by default \getnoflines\margincontentheight \xdef\nofmargincontentlines{\the\noflines}% \egroup} \def\fillupmargincontentlines % etex ! ! ! {\endgraf \begingroup \scratchcounter\numexpr\nofmargincontentlines-\prevgraf\relax\relax \ifnum\scratchcounter>\zerocount \forgetall\dorecurse\scratchcounter{\nobreak\crlf}% \fi \endgroup} % Yet undocumented, for a manual flush in for instance headers. \def\resetmargincontent {\global\margincontentlevel\zerocount \global\chardef\margintextcollected\zerocount \global\collectedmargintexts\emptytoks} % \def\placemargincontent % {\ifcase\margintextcollected\else % \bgroup % \chardef\graphicvadjustmode\zerocount % \doflushmargincontents % \egroup % \fi} % % font fix: \def\placemargincontent {\ifcase\margintextcollected\else % was level check \bgroup \redoconvertfont % !! \chardef\graphicvadjustmode\zerocount \doflushmargincontents \egroup \fi} % For old times sake (i use it in project styles) we provide \def\placemargintexts {\placemargincontent} \def\resetmargetitels {\resetmargincontent} \def\margewoordpositie{\margewoord} % obsolete, now no longer range % but never use them yourself since they may disappear. \def\oplinker#1% {\strut \graphicvadjust {\dontcomplain \setbox\scratchbox\vtop{\forgetall\strut#1}% \getboxheight\scratchdimen\of\box\scratchbox \vskip-\scratchdimen % waarom stond hier een \ ? \box\scratchbox}} \setupinmargin [\c!style=\v!bold, \c!color=, \c!strut=\v!auto, \c!location=\v!both, \c!align=\v!inner, \c!stack=\v!no, \c!before=, \c!after=] \setupinmargin [\v!left] [\c!distance=\leftmargindistance, \c!width=\leftmarginwidth, %\c!align=\v!left, % no \c!location=\v!left] \setupinmargin [\v!right] [\c!distance=\rightmargindistance, \c!width=\rightmarginwidth, %\c!align=\v!right, % no \c!location=\v!right] % bonus needed when [inner/outer] is used as tag \setupinmargin[\v!inner][\c!location=\v!inner,\c!align=\v!inner] \setupinmargin[\v!outer][\c!location=\v!outer,\c!align=\v!inner] % more efficient (5K less fotmat file) % % \letvalue{\??im\v!inner\c!location}\v!inner \letvalue{\??im\v!inner\c!align}\v!inner % \letvalue{\??im\v!outer\c!location}\v!outer \letvalue{\??im\v!outer\c!align}\v!inner \protect \endinput