%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
% CD labeling macros, version 0.93, February 2001.
% Copyright Victor Eijkhout 2001
% file name: CD_labeler.tex
% CTAN location: macros/generic/eijkhout
% uses: repeat.tex
%
% Author:
% Victor Eijkhout
% Department of Computer Science
% University of Tennessee, Knoxville TN 37996
%
% victor@eijkhout.net
%
% This program is free software; you can redistribute it and/or
% modify it under the terms of the GNU General Public License
% as published by the Free Software Foundation; either version 2
% of the License, or (at your option) any later version.
% 
% This program 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.  See the
% GNU General Public License for more details.
%
% For a copy of the GNU General Public License, write to the 
% Free Software Foundation, Inc.,
% 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA,
% or find it on the net, for instance at
% http://www.gnu.org/copyleft/gpl.html
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
% Use this file as follows:
%
% \input CD_labeler
% \CDLlabel{ <label content> }
%
% where the <label content> is usually comprised of
% one or more of the following:
% 
% \CDLbackground{ <picture material> }
% \CDLunderhole{<setup>}{ <material printed below the hole> }
% \CDLlowerhalf{<setup>}{ <material on the lower half of the label,
%                 left of and below the hole> }
% \CDLleft{<setup>}{ <material printed on the left side of the label> }
% \CDLright{<setup>}{ <material printed on the right side of the label> }
%
% (You can insert your own material, which gets processed in
% horizontal mode. However, you'll have a hard time controlling
% its elevation in the label.)
%
% These commands can be given in any order, since basically
% everything is printed on top of each other.
%
% Make sure to put %-signs at line ends:
% \CDLlabel{%
%     \CDLbackground{<stuff>}%
%     \CDLleft{<text>}%
% }
%
% The <setup> material contains such things as \baselineskip
% settings. If you use a non-standard baselineskip, it is
% *essential* that you put that declaration in the first 
% argument. Things such as font choices can go in the second.
%
% With the material left and right of the label, you may want to
% leave a few lines blank at the top. Here's how:
% To leave some blank lines: \CDLblank{ <number of lines to skip> }
%
% For guidance, a box is printed around the label. You can suppress
% this by \CDLboxfalse.
%
% Adjustable dimensions:
% \CDLdiscsize (default 120mm, which is CD size)
% \CDLinnerdiameter (default 40mm, the hole and ring around it)
% \CDLedgemargin (default 4mm, stay away this much from the edge)
% \CDLgutterwidth (default 0mm, keep this much space between
%                  \CDLleft and \CDLright text)
%
% Auxiliary commands:
% \CDLraggedright suppress hyphenation and use ragged right margin
%
% If you also use my DB_process macros, you can do things like
%
% \CDLlabel{%
%   \CDLunderhole{\baselineskip8pt}{\smallfont \DBPtabfile{cd_file}}%
%   \CDLleft{\baselineskip22pt \rightskip0pt plus 1cm}%
%           {\CDLblank{3}\titlefont My favourite bedtime songs}%
%   \CDLright{\baselineskip8pt}{\CDLblank{7}\smallfont
%             \leftskip=1cm \rightskip=0pt plus 1cm
%             Compiled for his own
%             private use, by Victor Eijkhout, 1998}}
% where the cd_file is dumped from your favourite database.
%
% Share and enjoy!
%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% revision history:
% 0.9 first release, December 1998
% 0.91 fixed documentation, use repeat.tex for loop macro,
%      copyright notice, bug in lower half macro, Feb 1999
% 0.92 \CDLlabel made \long
%      \CDLinnerradius changed to \CDLinnerdiameter
%      fixed double subtracting of offset in \CDL{left,right},
%      and added empty line, suggestions by Yotam Medini. April 1999
% 0.93 added \CDLragged{left,right} \CDLgutterwidth \CDLsquash.
%      Major improvement in \CDL{left,right}. February 2001.
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%
%%
%% Prevent multiple loading of this file
%%
\expandafter\ifx\csname CDLcount\endcsname\relax
  \message{Loading CD labeler, version 0.92}%
\else
  \message{CD labeling macros already loaded ... }\endinput \fi

\newtoks\CDLtoks \newbox\CDLbox
\newdimen\CDLdiscsize \CDLdiscsize=120mm
\newdimen\CDLinnerdiameter \CDLinnerdiameter=40mm
\newdimen\CDLedgemargin \CDLedgemargin=4mm
\newdimen\CDLgutterwidth \CDLgutterwidth=0mm
\newif\ifCDLbox \CDLboxtrue

%%
%% Load auxiliary files: loop macro
%%
\input repeat.tex

%%
%% CDLlabel
%% main routine, this draws an empty box, with any
%% background and content supplied by the user
%% in \CDLbackground and \CDL{left,right,underhole,overhole}
%%
\long\def\CDLlabel#1%
   {\vbox{\ifCDLbox\hrule\fi
          \hbox to \CDLdiscsize
             {\hsize=\CDLdiscsize \ifCDLbox\vrule\fi
              \ignorespaces #1\hss \ifCDLbox\vrule\fi}
          \ifCDLbox\hrule\fi}}
%%
%% CDLbackground
%% user macro
%% place a dimensionless item, presumably a picture
%%
\def\CDLbackground#1{
    \setbox\CDLbox=\vbox to 0pt{\hsize=0pt
                 \hbadness\maxdimen \vbadness\maxdimen #1}%
    \wd\CDLbox=0pt \raise \CDLdiscsize\box\CDLbox}
%%
%% CDLlabelbox
%% basic macro for shape macros below
%%
\long\def\CDLlabelbox#1{%
    \setbox\CDLbox=\vbox to \CDLdiscsize{\hsize=\CDLdiscsize
        \hrule width \CDLdiscsize height 0pt depth 0pt \nointerlineskip
        \vskip\CDLedgemargin
        #1\vfil
        }%
    \wd\CDLbox=0pt \box\CDLbox \ignorespaces}

%%
%% Shapes macros: various loops of calling CDLline, and building
%% up a \parshape. This is built around CDLline, which computes 
%% length and indents left/right of a line somewhere on the label.
%% #1 is an option for setup: baselineskip and such
%%
\def\CDLlowerhalf#1#2{\CDLlabelbox{#1\relax
  \vskip.5\CDLdiscsize
  \CDLtoks={}%
  \begingroup
    \repeat \for{CDLcount} \from{0} \do {%
      \count1=\CDLcount \advance\count1 by 1
      \CDLline{\count1}\a\t\c
      \CDLline\CDLcount\t\b\t
      \if\CDLerror \expandafter\breakrepeat \fi
          \dimen1=\c\relax \dimen2=\a\relax
          \ifdim\b=0pt \multiply\dimen2 by 2 \fi
          \edef\temp{\global\CDLtoks={\the\CDLtoks 
               \space\the\dimen1 \space\the\dimen2}}\temp
      }%
    \noindent \parshape \CDLcount \the\CDLtoks #2\par
  \endgroup
  }}
\def\CDLunderhole#1#2{\CDLlabelbox{#1\relax
  \vskip.5\CDLdiscsize \vskip.5\CDLinnerdiameter \vskip\baselineskip
  \CDLtoks={}%
  \begingroup
    \count0=0
    \repeat \for{CDLcount} \from{0} \do {%
      \count1=\CDLcount \advance\count1 by 1
      \CDLline{\count1}\a\t\c
      \CDLline\CDLcount\t\b\t
      \if\CDLerror \expandafter\breakrepeat \fi
          \ifdim\b>0pt \advance\count0 by 1
          \else \dimen1=\c\relax \dimen2=\a\relax
              \multiply\dimen2 by 2
              \edef\temp{\global\CDLtoks={\the\CDLtoks 
                   \space\the\dimen1 \space\the\dimen2}}\temp
          \fi
      }%
    \advance\CDLcount by -\count0
    \noindent \parshape \CDLcount \the\CDLtoks #2\par
  \endgroup 
  }}
\def\CDLleft#1#2{\CDLlabelbox{
  \CDLtoks={}#1\relax
  \begingroup
    \repeat \for{CDLcount} \from{0} \do {%
      \CDLline\CDLcount\a\b\c
      \if\CDLerror \expandafter\breakrepeat \fi
      % if we're not next to the hole, leave a gutter
      \ifdim\b=0pt \dimen0=\a \advance\dimen0 by -\CDLgutterwidth
        \edef\a{\the\dimen0 }\fi
      \edef\temp{\CDLtoks={\c\space\a \space\the\CDLtoks \space \c\space\a}}\temp
      }%
    \noindent
    \multiply\CDLcount by 2 \advance\CDLcount by 1
    \parshape \CDLcount 0pt 0pt \the\CDLtoks \hfill\break #2\par
  \endgroup 
  }}
\def\CDLright#1#2{\CDLlabelbox{
  \CDLtoks={}#1\relax
  \begingroup
    %\count0=\CDLdiscsize \divide\count0 by \baselineskip
    %\message{Should fit \the\count0 lines}%
    \repeat \for{CDLcount} \from{0} \do {%
      % get \a=length \b=inner gap \c=outer gap
      \CDLline\CDLcount\a\b\c
      \if\CDLerror \expandafter\breakrepeat \fi
      % if we're not next to the hole, leave a gutter
      \ifdim\b=0pt \dimen0=\a \advance\dimen0 by -\CDLgutterwidth
          \edef\a{\the\dimen0 }%
        \else
          \dimen0=\a \advance\dimen0 by -\baselineskip \edef\a{\the\dimen0 }%
          \dimen0=\b \advance\dimen0 by \baselineskip \edef\b{\the\dimen0 }%
        \fi
      \dimen0=\CDLdiscsize \divide\dimen0 by 2
      \advance\dimen0 by \b
      \edef\temp{\CDLtoks={
               \the\dimen0 \space\a \space\the\CDLtoks
               \the\dimen0 \space\a}}\temp
      }%
    \noindent \multiply\CDLcount by 2 \advance\CDLcount by 1
    \parshape \CDLcount 0pt 0pt \the\CDLtoks \hfill\break #2\par
  \endgroup 
  }}
\def\CDLleftandunder#1#2{\CDLlabelbox{
  \CDLtoks={}#1\relax
  \begingroup
    \repeat \for{CDLcount} \from{1} \do {%
      % get \a=length \b=inner gap \c=outer gap
      \CDLline\CDLcount\a\b\c
      \if\CDLerror \expandafter\breakrepeat \fi
      % if we're not next to the hole, leave a gutter
      \ifdim\b=0pt \dimen0=\a \advance\dimen0 by -\CDLgutterwidth
        \edef\a{\the\dimen0 }\fi
      \edef\temp{\CDLtoks={\c\space\a \space\the\CDLtoks}}\temp
      }%
    \CDLline0\a\b\c
    \edef\temp{\CDLtoks={\the\CDLtoks \space \c\space\a \space \c\space\a}}\temp
    \advance\CDLcount by 3
    \edef\tempc{\the\CDLcount}%
    \repeat \for{CDLcount} \from{0} \do {%
      \count1=\CDLcount \advance\count1 by 1
      \CDLline{\count1}\a\t\c
      \CDLline\CDLcount\t\b\t
      \if\CDLerror \expandafter\breakrepeat \fi
          \dimen1=\c\relax \dimen2=\a\relax
          \ifdim\b=0pt \multiply\dimen2 by 2 \fi
          \edef\temp{\global\CDLtoks={\the\CDLtoks 
               \space\the\dimen1 \space\the\dimen2}}\temp
      }%
    \advance\CDLcount by \tempc
    \noindent
    \parshape \CDLcount 0pt 0pt \the\CDLtoks \hfill\break #2\par
  \endgroup 
  }}
\def\CDLblank#1{\begingroup\count0=#1\relax
    \ifnum\count0>0 \hfill\break \advance\count0 by -1
    \expandafter\CDLblank\expandafter{\number\count0}\fi\endgroup}

%%%%%%%%%%%%%%%% Auxiliaries %%%%%%%%%%%%%%%%
%%
%% \CDLraggedright & \CDLraggedleft
\def\CDLraggedright{\hyphenchar\font=-1
    \rightskip=0pt plus .5\CDLdiscsize}
\def\CDLraggedleft{\hyphenchar\font=-1
    \leftskip=0pt plus .5\CDLdiscsize}
\def\CDLsquash#1{{\setbox0\hbox{#1}\ht0=0pt \dp0=0pt \box0\relax}}

%%%%%%%%%%%%%%%% Interal macros %%%%%%%%%%%%%%%%
%%
%% CDLline
%% from #1 line number compute #2 length, #3 inner gap #4 outer gap
%%
\def\CDLline#1#2#3#4{\CDLsetnoerror
  \begingroup \dimen0=\baselineskip
    \multiply\dimen0 by #1\relax
    \divide\CDLdiscsize by 2 \divide\CDLinnerdiameter by 2
    \dimen1=\CDLdiscsize \advance\dimen1 by -\CDLedgemargin
    \CDLcircle{\dimen1}{\dimen0}\blen
    \if\CDLerror \aftergroup\CDLseterror \else
        \CDLcircle\CDLinnerdiameter{\dimen0}\slen
        \dimen0=\blen sp
        \dimen2=\CDLdiscsize \advance\dimen2 by -\dimen0
        \xdef#4{\the\dimen2}%
        \if\CDLerror
            \xdef#2{\the\dimen0}\gdef#3{0pt}%
        \else
            \dimen1=\slen sp\relax \advance\dimen0 by -\dimen1
            \xdef#2{\the\dimen0}\xdef#3{\the\dimen1}%
    \fi \fi
  \endgroup}
%%
%% CDLcircle
%% from #1=r #2=y compute #3=x so that x^2+y^2=r^2
%%
\def\CDLcircle#1#2#3{\CDLsetnoerror
  \begingroup
    \count2=#1\advance\count2 by #2\edef\a{\number\count2}%
    \count3=#1\advance\count3 by -#2\edef\b{\number\count3}%
    \ifnum\count3<0 \aftergroup\CDLseterror \else
        \CDLsqrt\a\aa \CDLsqrt\b\bb
        \count0=\aa \multiply\count0 by \bb
        \xdef#3{\number\count0}%
    \fi
  \endgroup}
%%
%% CDLsqrt
%% #1 is dimension, #2 is receiving control sequence
%%
\def\CDLsqrt#1#2{\begingroup
    \count1=#1\relax
    \repeat \do {
      \count2=#1\relax \divide\count2 by \count1
      \advance\count2 by \count1 \divide\count2 by 2
      \ifnum\count2<\count1 \count1=\count2 
        \else \expandafter\breakrepeat \fi}
    \xdef#2{\the\count1}\endgroup}

%%
%% Error handling
%%
\def\CDLsetnoerror{\def\CDLerror{10}}
\def\CDLseterror{\def\CDLerror{11}}

\endinput

