% ========================================================================= % LAPDF.STY: Version 1.1, Copyright(C) 2006-2011, Detlef Reimers % Lapdf is distributed under the terms of the GNU general public licence % ------------------------------------------------------------------------- % Email: detlefreimers@gmx.de Website: http://detlefreimers.de % ========================================================================= \NeedsTeXFormat{LaTeX2e} \ProvidesPackage{lapdf}[2006/04/09 v1.0 Drawing with pdfTeX] \RequirePackage{calc} \newtoks\@c \newtoks\@d \newtoks\@e \newtoks\@f \let\@ta\@tempcnta \let\@tb\@tempcntb \newcount\@@s \newcount\@@i \newcount\@@k \newcount\@@n \newcount\col \newcount\@az \newcount\@bz \newcount\@cz \newcount\@xz \newcount\@ca \newcount\@cb \newcount\@cc \newcount\@cd \newcount\@ce \newcount\@cf \newcount\@cg \newcount\@ch \newcount\@ci \newcount\@ck \newcount\@cl \newcount\@cm \newcount\@cn \let\@tbox\@tempboxa \let\@@a\@ovdx \let\@@b\@ovdy \let\@@t\@ovxx \let\@@u\@ovyy \newdimen\wid \newdimen\tmp \newdimen\@@d \newdimen\@@m \newdimen\@@x \newdimen\@@y \newdimen\@@A \newdimen\@@B \newdimen\@@C \newdimen\@@D \newdimen\@@T \newdimen\@@U \newdimen\@@X \newdimen\@@Y \newdimen\@CR \newdimen\@CG \newdimen\@CB \newdimen\@ax \newdimen\@ay \newdimen\@az \newdimen\@bx \newdimen\@by \newdimen\@bz \newdimen\@cx \newdimen\@cy \newdimen\@cz \newdimen\@dx \newdimen\@dy \newdimen\@dz \newdimen\@ex \newdimen\@ey \newdimen\@ez \newdimen\@fx \newdimen\@fy \newdimen\@fz \newdimen\@gx \newdimen\@gy \newdimen\@gz \newdimen\@hx \newdimen\@hy \newdimen\@hz \newdimen\@rx \newdimen\@ry \newdimen\@rz \newdimen\@rw \newdimen\@sx \newdimen\@sy \newdimen\@tx \newdimen\@ty \newdimen\@ux \newdimen\@uy \newdimen\@vx \newdimen\@vy \newdimen\@wx \newdimen\@wy \newdimen\@xx \newdimen\@xy \newdimen\@xz \newdimen\@zx \newdimen\@zy \newdimen\@zz \newdimen\@yx \newdimen\@yy % ------------------------------------------------------------------------- \@ck=0 \wid=0.35pt % ------------------------------------------------------------------------- \DeclareOption{black}{% \@cl=0 \gdef\Resetcol{} \gdef\Stepcol(#1,#2,#3){} \gdef\Nextcol(#1,#2){} } \DeclareOption{color}{% \@cl=1 \gdef\Resetcol{\col=-1} \gdef\Stepcol(#1,#2,#3){% \@cc=\col \Add(\@cc,#3) \ifnum#1<0 \@ca=0 \else \@ca=#1 \fi \ifnum#2>95 \@cb=95 \else \@cb=#2 \fi \ifnum\col<\@ca \col=\@ca \else \ifnum\col>\@cb \col=\@ca \else \ifnum\@cc<\@ca \col=\@ca \else \ifnum\@cc>\@cb \col=\@ca \else \col=\@cc \fi\fi\fi\fi \ifnum\col<96% \Colval(\col,8,\@rx) \Colval(\col,0,\@gx) \Colval(\col,16,\@bx) \Setcol(\Np\@rx,\Np\@gx,\Np\@bx) \fi} \gdef\Nextcol(#1,#2){\Stepcol(#1,#2,1)} } % ------------------------------------------------------------------------- % Calculates the cromatic intensity of a specific color. n is the color, % d is the color offset (r: 8, g: 0, b: 16) and r is the result register. % \Colval(n,d,r) % ------------------------------------------------------------------------- \gdef\Colval(#1,#2,#3){% \ifnum#1>71 \@cm=3 \else \ifnum#1>47 \@cm=2 \else \ifnum#1>23 \@cm=1 \else \@cm=0 \fi \fi \fi \@cn=#1 \Add(\@cn,#2) \Mod(\@cn,24) \Sub(\@cn,8) \Abs(\@cn) \ifnum\@cn<4 \Dset(#3,1) \else \ifnum\@cn<8 \Dset(#3,8) \Dsub(#3,\@cn) \Div(#3,4) \else \Dset(#3,0) \fi \fi \Dset(\@tx,5) \Dsub(\@tx,\@cm) \Dmul(#3,\@tx) \Div(#3,5) \Crnd(#3)} % ------------------------------------------------------------------------- % This macro is only necessary, because my TeX compiler under MacOS9.2 % says 'out of color stack space' without the rounding. With this function, % all color values have two digits or less. \Crnd(col) % ------------------------------------------------------------------------- \gdef\Crnd(#1){\Ddiv(#1,0.0999pt) \Mul(#1,10) \Dint(#1) \Ddiv(#1,100pt)} % ------------------------------------------------------------------------- \ExecuteOptions{black} \ProcessOptions \ifnum\@cl>0 \AtBeginDocument{\Resetcol} \fi % ------------------------------------------------------------------------- % Strips the pt dimension % ------------------------------------------------------------------------- {\catcode`t=12\catcode`p=12\gdef\nP#1pt{#1}} \gdef\Np#1{\expandafter\nP\the#1}% % ------------------------------------------------------------------------- % \Lapdf{} the Lapdf logo % ------------------------------------------------------------------------- \def\Lapdf{L\kern-.2em\lower.5ex\hbox{A}\kern-.15emPDF} % ------------------------------------------------------------------------- % \pdfTeX{} a pdfTeX logo % ------------------------------------------------------------------------- \def\pdfTeX{\hbox{pdf}\kern+.05em\TeX{}} % ------------------------------------------------------------------------- % \PDF{cmd} for the pdf specials, which are used here % ------------------------------------------------------------------------- \gdef\PDF#1{\@killglue\special{pdf:#1}} % ------------------------------------------------------------------------- % \lapdf(x1,y1)(x2,y2) the lapdf environment % ------------------------------------------------------------------------- \newcommand{\pdf}{\Gsave \Scale(\Np\unitlength,\Np\unitlength) \Setwidth(0.02) \Setcap(1) \Setdash([] 0)} \def\endpdf{\Grestore} \newcommand{\lapdf}{\@pdfpict} \gdef\@pdfpict(#1,#2)(#3,#4){\begin{picture}(#1,#2)(#3,#4) \begin{pdf}} \def\endlapdf{\end{pdf} \end{picture}} % ------------------------------------------------------------------------- % Gets the unit length from document. Define and set a register. % ------------------------------------------------------------------------- \gdef\Ul{\unitlength} \gdef\Set(#1,#2){#1=#2} \gdef\Dset(#1,#2){#1=#2pt} \gdef\Defnum(#1,#2){\newcount#1 #1=#2} \gdef\Defdim(#1,#2){\newdimen#1 #1=#2pt} % ------------------------------------------------------------------------- % Two macros for count or dimen registers. If nested, you have to use % brackets around the inner looop. % \whilenum{num condition}{commands} \whiledim{dim condition}{commands} % ------------------------------------------------------------------------- \gdef\Whilenum#1#2{\loop\ifnum#1#2\repeat} \gdef\Whiledim#1#2{\loop\ifdim#1pt#2\repeat} % ------------------------------------------------------------------------- % Arithmetic with count registers. % ------------------------------------------------------------------------- \gdef\Add(#1,#2){\advance#1#2} \gdef\Sub(#1,#2){\advance#1-#2} \gdef\Mul(#1,#2){\multiply#1#2} \gdef\Div(#1,#2){\divide#1#2} \gdef\@Abs(#1){\ifnum#1<\z@ #1=-#1 \@@s=-1 \else \@@s=1 \fi} \gdef\Abs(#1){\ifnum#1<\z@ #1=-#1 \fi} \gdef\Sig(#1,#2){\ifnum#1<\z@ \Set(#2,-1) \else \Set(#2,1) \fi} \gdef\Mod(#1,#2){\@@i=#1 \Div(\@@i,#2) \Mul(\@@i,#2) \Sub(#1,\@@i)} % ------------------------------------------------------------------------- % Arithmetic with dimen registers. Dmul & Ddiv use the calc package. % ------------------------------------------------------------------------- \gdef\Dadd(#1,#2){\advance#1#2pt} \gdef\Dsub(#1,#2){\advance#1-#2pt} \gdef\Dmul(#1,#2){\setlength{#1}{#1*\ratio{#2}{1pt}}} \gdef\Ddiv(#1,#2){\setlength{#1}{1pt*\ratio{#1}{#2}}} \gdef\@Dabs(#1){\ifdim#1<\z@ #1=-#1 \@@s=-1 \else \@@s=1 \fi} \gdef\Dabs(#1){\ifdim#1<\z@ #1=-#1 \fi} \gdef\Dint(#1){\@@i=#1 \Div(\@@i,65536) \Dset(#1,\@@i)} \gdef\Dsig(#1,#2){\ifdim#1<\z@ \Set(#2,-1) \else \Set(#2,1) \fi} \gdef\Dmod(#1,#2){\@@m=#1 \Ddiv(\@@m,#2pt) \Dint(\@@m) \Dmul(\@@m,#2pt) \Sub(#1,\@@m)} % ------------------------------------------------------------------------- % Conversion to radian or degree. % \Rad(x,result) \Deg(x,result) % ------------------------------------------------------------------------- \gdef\Rad(#1,#2){\Dset(#2,#1) #2=0.017453#2} \gdef\Deg(#1,#2){\Dset(#2,#1) #2=57.29578#2} % ------------------------------------------------------------------------- % Calculates the sinus of an angle r in radian. The result is returned % in register r. First, we reduce the argument to [0,2pi]. \Sin(x,r) % ------------------------------------------------------------------------- \gdef\Sin(#1,#2){% \Dset(\@@x,#1) \Dmod(\@@x,6.2832) \@@y=\@@x \@@a=\@@x \Dset(\@@d,1) \@ta=1 \@whiledim{\@@d>0pt}\do{% \Dmul(\@@a,\@@x) \Add(\@ta,1) \Div(\@@a,\@ta) \Dmul(\@@a,\@@x) \Add(\@ta,1) \Div(\@@a,\@ta) \@@a=-\@@a \Add(\@@y,\@@a) \@@d=\@@a \Dabs(\@@d)} #2=\@@y} % ------------------------------------------------------------------------- % Calculates the cosinus of an angle r in radian. The result is returned % in register r. First, we reduce the argument to [0,2pi]. \Cos(x,r) % ------------------------------------------------------------------------- \gdef\Cos(#1,#2){% \Dset(\@@x,#1) \Dmod(\@@x,6.2832) \Dset(\@@d,1) \@ta=0 \Dset(\@@y,1) \Dset(\@@a,1) \@whiledim{\@@d>0pt}\do{% \Dmul(\@@a,\@@x) \Add(\@ta,1) \Div(\@@a,\@ta) \Dmul(\@@a,\@@x) \Add(\@ta,1) \Div(\@@a,\@ta) \@@a=-\@@a \Add(\@@y,\@@a) \@@d=\@@a \Dabs(\@@d)} #2=\@@y} % ------------------------------------------------------------------------- % Calculates the tangens of an angle r in radian. The result is returned % in register r. First, we reduce the argument to [0,2pi]. We limit the % maximum value at |n/2*pi| to 5. \Tan(x,r) % ------------------------------------------------------------------------- \gdef\Tan(#1,#2){% \Dset(\@@U,#1) \Dmod(\@@U,6.2832) \Sin(\Np\@@U,\@@X) \Cos(\Np\@@U,\@@Y) \ifdim\@@Y=0pt \Dset(\@@X,5) \else \Ddiv(\@@X,\@@Y) \fi #2=\@@X} % ------------------------------------------------------------------------- % Calculates the arcus sinus of x. The result is returned in register r. % \Asin(x,r) % ------------------------------------------------------------------------- \gdef\Asin(#1,#2){% \Dset(\@@x,#1) \@ta=1 \ifdim\@@x<1.0pt \ifdim\@@x>-1.0pt \@@y=\@@x \@@t=\@@x \Dset(\@@d,1) \@whiledim{\@@d>0pt}\do{% \Mul(\@@t,\@ta) \Dmul(\@@t,\@@x) \Add(\@ta,1) \Div(\@@t,\@ta) \Dmul(\@@t,\@@x) \Add(\@ta,1) \@@u=\@@t \Div(\@@t,\@ta) \Add(\@@y,\@@t) \@@d=\@@t \Dabs(\@@d) \@@t=\@@u} \else \Dset(\@@y,-1.5708) \fi \else \Dset(\@@y,1.5708) \fi #2=\@@y} % ------------------------------------------------------------------------- % Calculates the arcus cosinus of x. The result is returned in register r. % \Acos(x,r) % ------------------------------------------------------------------------- \gdef\Acos(#1,#2){% \Asin(#1,\@@y) \Dset(#2,1.5708) \Sub(#2,\@@y)} % ------------------------------------------------------------------------- % Calculates the arcus tangens of x. The result is returned in register r. % Because the power series of atan converges too slowly, we use the % addition theorem of atan and split the calculation to get accurate % results. \Atan(x,r) % ------------------------------------------------------------------------- \gdef\Atan(#1,#2){% \Dset(\@@x,#1) \@ta=1 \@Dabs(\@@x) \ifdim\@@x<0.2500pt \Dset(\@@u,0.00000) \@@a=1.0\@@x \Dsub(\@@a,0) \@@b=0.0\@@x \Dadd(\@@b,1) \else \ifdim\@@x<0.6875pt \Dset(\@@u,0.46365) \@@a=2.0\@@x \Dsub(\@@a,1) \@@b=1.0\@@x \Dadd(\@@b,2) \else \ifdim\@@x<1.1875pt \Dset(\@@u,0.78540) \@@a=1.0\@@x \Dsub(\@@a,1) \@@b=1.0\@@x \Dadd(\@@b,1) \else \ifdim\@@x<3.375pt \Dset(\@@u,0.98279) \@@a=2.0\@@x \Dsub(\@@a,3) \@@b=3.0\@@x \Dadd(\@@b,2) \else \Dset(\@@u,1.57080) \@@a=0.0\@@x \Dsub(\@@a,1) \@@b=1.0\@@x \Dadd(\@@b,0) \fi\fi\fi\fi \Ddiv(\@@a,\@@b) \@@x=\@@a \@@y=\@@x \@@t=\@@x \Dset(\@@d,1) \@whiledim{\@@d>0pt}\do{% \Dmul(\@@t,\@@x) \Add(\@ta,2) \Dmul(\@@t,\@@x) \Div(\@@t,\@ta) \@@t=-\@@t \Add(\@@y,\@@t) \@@d=\@@t \ifdim\@@d<0pt \@@d=-\@@d \fi} \Add(\@@y,\@@u) \Mul(\@@y,\@@s) #2=\@@y} % ------------------------------------------------------------------------- % Calculates the sinus hyperbolicus. The result is returned in register r. % \Sinh(x,r) % ------------------------------------------------------------------------- \gdef\Sinh(#1,#2){% \Dset(\@@x,#1) \@ta=1 \@@y=\@@x \@@t=\@@x \Dset(\@@d,1) \@whiledim{\@@d>0pt}\do{% \Dmul(\@@t,\@@x) \Add(\@ta,1) \Div(\@@t,\@ta) \Dmul(\@@t,\@@x) \Add(\@ta,1) \Div(\@@t,\@ta) \Add(\@@y,\@@t) \@@d=\@@t \Dabs(\@@d)} #2=\@@y} % ------------------------------------------------------------------------- % Calculates the cosinus hyperbolicus. The result is returned in register % r. \Cosh(x,r) % ------------------------------------------------------------------------- \gdef\Cosh(#1,#2){% \Dset(\@@x,#1) \@ta=0 \Dset(\@@y,1) \Dset(\@@t,1) \Dset(\@@d,1) \@whiledim{\@@d>0pt}\do{% \Dmul(\@@t,\@@x) \Add(\@ta,1) \Div(\@@t,\@ta) \Dmul(\@@t,\@@x) \Add(\@ta,1) \Div(\@@t,\@ta) \Add(\@@y,\@@t) \@@d=\@@t \Dabs(\@@d)} #2=\@@y} % ------------------------------------------------------------------------- % Calculates the tangens hyperbolicus. The result is returned in register % r. \Tanh(x,r) % ------------------------------------------------------------------------- \gdef\Tanh(#1,#2){% \Dset(\@@a,#1) \Dset(\@@b,#1) \Cosh(#1,\@@a) \Sinh(#1,\@@b) \Ddiv(\@@b,\@@a) #2=\@@b} % ------------------------------------------------------------------------- % Calculates the area sinus of x. The result is returned register r. % \Asinh(x,r) % ------------------------------------------------------------------------- \gdef\Asinh(#1,#2){% \Dset(\@@a,#1) \Dmul(\@@a,\@@a) \Dadd(\@@a,1) \Sqrt(\Np\@@a,\@@a) \Dadd(\@@a,#1) \Ln(\Np\@@a,\@@a) #2=\@@a} % ------------------------------------------------------------------------- % Calculates the area cosinus of x. The result is returned register r. % \Acosh(x,r) % ------------------------------------------------------------------------- \gdef\Acosh(#1,#2){% \Dset(\@@a,#1) \ifdim\@@a<12pt \Dmul(\@@a,\@@a) \Dsub(\@@a,1) \Sqrt(\Np\@@a,\@@a) \Dadd(\@@a,#1) \Ln(\Np\@@a,\@@a) \else \Add(\@@a,\@@a) \Ln(\Np\@@a,\@@a) \fi #2=\@@a} % ------------------------------------------------------------------------- % Calculates the area tangens of x. The result is returned register r. % We limit the maximum value of atanh to 5. \Atanh(x,r) % ------------------------------------------------------------------------- \gdef\Atanh(#1,#2){% \Dset(\@@a,#1) \@Dabs(\@@a) \ifdim\@@a>0.9999pt \Dset(\@@a,5) \else \Dset(\@@b,1) \Sub(\@@b,\@@a) \Dadd(\@@a,1) \Ln(\Np\@@a,\@@a) \Ln(\Np\@@b,\@@b) \Sub(\@@a,\@@b) \Div(\@@a,2) \fi \Mul(\@@a,\@@s) #2=\@@a} % ------------------------------------------------------------------------- % Calculates the natural logarithm. The result is returned in register r. % For large numbers we reduce the argument x, using ln(x)=ln(x/e^k)+k. % For small numbers we enlarge the argument x, using ln(x)=ln(x*e^k)-k. % The value of k is added at the end. \Ln(x,r) % ------------------------------------------------------------------------- \gdef\Ln(#1,#2){% \Dset(\@@x,#1) \Dset(\@@t,2.71828) \@ta=1 \@tb=0 \@whiledim{\@@x>\@@t}\do{\Ddiv(\@@x,\@@t) \Add(\@tb,1)} \@whiledim{\@@x<1pt}\do{\Dmul(\@@x,\@@t) \Sub(\@tb,1)} \@@t=\@@x \Dadd(\@@t,1) \Dsub(\@@x,1) \Ddiv(\@@x,\@@t) \@@y=\@@x \@@t=\@@x \Dset(\@@d,1) \@whiledim{\@@d>0pt}\do{% \Dmul(\@@t,\@@x) \Dmul(\@@t,\@@x) \@@u=\@@t \Add(\@ta,2) \Div(\@@t,\@ta) \Add(\@@y,\@@t) \@@d=\@@t \ifdim\@@d<0pt \@@d=-\@@d \fi \@@t=\@@u} \Mul(\@@y,2) \Dadd(\@@y,\@tb) #2=\@@y} % ------------------------------------------------------------------------- % Calculates the logarithm of x to basis a. The result is returned in % register r. \Log(a,x,r) % ------------------------------------------------------------------------- \gdef\Log(#1,#2,#3){% \Ln(#1,\@ax) \Ln(#2,\@@x) \Ddiv(\@@x,\@ax) #3=\@@x} % ------------------------------------------------------------------------- % Calculates the natural power of x. The result is returned in register r. % \Exp(x,r) % ------------------------------------------------------------------------- \gdef\Exp(#1,#2){% \Dset(\@@x,#1) \@ta=1 \Dset(\@@y,1) \Dset(\@@t,1) \Dset(\@@d,1) \@whiledim{\@@d>0pt}\do{% \Dmul(\@@t,\@@x) \Div(\@@t,\@ta) \Add(\@ta,1) \Add(\@@y,\@@t) \@@d=\@@t \Dabs(\@@d)} #2=\@@y} % ------------------------------------------------------------------------- % Calculates the x-th power of number a. The result is returned in % register r. \Pow(a,x,r) % ------------------------------------------------------------------------- \gdef\Pow(#1,#2,#3){% \Dset(\@@x,#1) \Dset(\@@y,#2) \ifdim\@@y=1.0pt #3=\@@x \else \ifdim\@@x>0pt \Ln(#1,\@@y) \Dset(\@@x,#2) \Dmul(\@@x,\@@y) \@ta=1 \Dset(\@@y,1) \Dset(\@@t,1) \Dset(\@@d,1) \@whiledim{\@@d>0pt}\do{% \Dmul(\@@t,\@@x) \Div(\@@t,\@ta) \Add(\@ta,1) \Add(\@@y,\@@t) \@@d=\@@t \Dabs(\@@d)} #3=\@@y \else #3=\@@x \fi \fi} % ------------------------------------------------------------------------- % Calculates the n-th root of a number x. The result is returned in % register r. \Root(x,n,r) % ------------------------------------------------------------------------- \gdef\Root(#1,#2,#3){% \Dset(\@@x,#1) \Dset(\@@y,#2) \ifdim\@@y=1pt #3=\@@x \else \ifdim\@@x>0pt \Ln(#1,\@@x) \Dset(\@@y,#2) \Ddiv(\@@x,\@@y) \@ta=1 \Dset(\@@y,1) \Dset(\@@t,1) \Dset(\@@d,1) \@whiledim{\@@d>0pt}\do{% \Dmul(\@@t,\@@x) \Div(\@@t,\@ta) \Add(\@ta,1) \Add(\@@y,\@@t) \@@d=\@@t \Dabs(\@@d)} #3=\@@y \else #3=\@@x \fi \fi} % ------------------------------------------------------------------------- % Calculates the n-th potenz (pos or neg integer) of a number a. The % result is returned in register r. \Pot(a,n,r) % ------------------------------------------------------------------------- \gdef\Pot(#1,#2,#3){% \Dset(\@@x,1) \@cm=#2 \@Abs(\@cm) \@ta=0 \@whilenum{\@ta<\@cm}\do{% \Dmul(\@@x,#1pt) \Add(\@ta,1)} \ifnum\@@s<0 \Dset(#3,1) \Ddiv(#3,\@@x) \else #3=\@@x \fi} % ------------------------------------------------------------------------- % Calculates the square root of a number x. The result is returned in % register r. First we reduce the argument to get fewer steps. \Sqrt(x,r) % ------------------------------------------------------------------------- \gdef\Sqrt(#1,#2){% \Dset(\@@t,#1) \Dset(\@@x,1) \@@d=\@@x \@@b=\@@x \ifdim\@@t=0pt \Dset(#2,0) \else \@whiledim{\@@t>4pt}\do{\Div(\@@t,4) \Mul(\@@b,2)} \@whiledim{\@@d>0pt}\do{\@@y=\@@t \Ddiv(\@@y,\@@x) \Sub(\@@y,\@@x) \Div(\@@y,2) \@@d=\@@y \Dabs(\@@d) \Add(\@@x,\@@y)} #2=\Np\@@b\@@x \fi} % ------------------------------------------------------------------------- % Calculates the distance between two points. The result is returned in % register r. \Len(x1,y1)(x2,y2)(r) % ------------------------------------------------------------------------- \gdef\Len(#1,#2)(#3,#4)(#5){% \Dset(\@@a,#3) \Sub(\@@a,#1pt) \Dset(\@@b,#4) \Sub(\@@b,#2pt) \Dmul(\@@a,\@@a) \Dmul(\@@b,\@@b) \Add(\@@a,\@@b) \Sqrt(\Np\@@a,#5)} % ------------------------------------------------------------------------- % Calculates the hypothenuse of a rectangular triangle. The result is % returned in register r. \Hypot(a,b,r) % ------------------------------------------------------------------------- \gdef\Hypot(#1,#2,#3){% \Dset(\@@a,#1) \Dset(\@@b,#2) \Dmul(\@@a,\@@a) \Dmul(\@@b,\@@b) \Add(\@@a,\@@b) \Sqrt(\Np\@@a,#3)} % ------------------------------------------------------------------------- % Calculates the directional angle between two points. The result in rad % is returned in register r. The first point is the reference point. % \Direc(x1,y1)(x2,y2)(r) % ------------------------------------------------------------------------- \gdef\Direc(#1,#2)(#3,#4)(#5){% \Dset(\@@X,#3) \Dset(\@@A,#1) \Sub(\@@X,\@@A) \Dset(\@@Y,#4) \Dset(\@@B,#2) \Sub(\@@Y,\@@B) \@@U=\@@X \Abs(\@@U) \ifdim\@@U<0.001pt \Dset(\@@A,1.5708) \ifdim\@@Y<0pt \Dadd(\@@A,3.1416) \fi \else \@@A=\@@Y \Ddiv(\@@A,\@@X) \Atan(\Np\@@A,\@@A) \ifdim\@@X<0pt \Dadd(\@@A,3.1416) \else \ifdim\@@Y<0pt \Dadd(\@@A,6.2832) \fi\fi\fi #5=\@@A} % ------------------------------------------------------------------------- % Rotate a point around the origin by angle a. The result is returned in % x2,y2. \Rotpoint(a)(x1,y1)(x2,y2) % ------------------------------------------------------------------------- \gdef\Rotpoint(#1)(#2,#3)(#4,#5){% \Dset(\@zx,#2) \Dset(\@zy,#3) \Dset(\@yx,#2) \Dset(\@yy,#3) \Rad(#1,\@@U) \Sin(\Np\@@U,\@@A) \Cos(\Np\@@U,\@@B) \Dmul(\@zx,\@@B) \Dmul(\@zy,\@@A) \Dmul(\@yx,\@@A) \Dmul(\@yy,\@@B) \Sub(\@zx,\@zy) \Add(\@yx,\@yy) #4=\@zx #5=\@yx} % ------------------------------------------------------------------------- % Draws a small point, filled with gray value g (0..1) at x,y. % \Point(g)(x,y) % ------------------------------------------------------------------------- \gdef\Point(#1)(#2,#3){\Gsave \Setwidth(0.01) \Setcol(0,0,0)% \Circle(32)(#2,#3,0.065) \Fill(#1,#1,#1) \Grestore} % ------------------------------------------------------------------------- % TeX typesetting a text at x,y with positional specification s. We have % to temporary leave lapdf and reenter afterwords. If you want to add any % macro from the picture environment, you have to use the same procedure. % \Text(x,y,s){text} % ------------------------------------------------------------------------- \gdef\Text(#1,#2,#3)#4{% \end{pdf} \normalsize \put(#1,#2){\makebox(0,0)[#3]{#4}} \begin{pdf}} % ------------------------------------------------------------------------- % \Setcol(r,g,b) set a color % \Setgray(v) set a gray % \@setcol(switch,r,g,b) helper function % rg and g are fore filling (f is first param) % RG and G are fore stroking (s is first param) % ------------------------------------------------------------------------- \gdef\@setcol(#1,#2,#3,#4){\def\@c{#1} \Dset(\@CR,#2) \Dset(\@CG,#3) \Dset(\@CB,#4) \ifnum\@cl=1 \if\@c f \@f={rg} \else \@f={RG} \fi \def\@e{#2 #3 #4} \else \ifdim\@ax=1.0pt \def\@e{1} \else \def\@e{0} \fi \fi \PDF{\@e\space \the\@f}} \gdef\Setcol(#1,#2,#3){\@setcol(s,#1,#2,#3)} \gdef\Setgray(#1){\@setcol(s,#1,#1,#1)} % ------------------------------------------------------------------------- % Some useful predefined colors. All names start with capital letters. % ------------------------------------------------------------------------- \gdef\Black{\Setcol(0,0,0)} \gdef\Dred{\Setcol(0.7,0,0)} \gdef\Dgreen{\Setcol(0,0.7,0)} \gdef\Dblue{\Setcol(0,0,0.7)} \gdef\Dcyan{\Setcol(0,0.7,0.7)} \gdef\Dmagenta{\Setcol(0.7,0,0.7)} \gdef\Dyellow{\Setcol(0.7,0.7,0)} \gdef\Dgray{\Setcol(0.4,0.4,0.4)} \gdef\Gray{\Setcol(0.8,0.8,0.8)} \gdef\Red{\Setcol(1,0,0)} \gdef\Green{\Setcol(0,1,0)} \gdef\Blue{\Setcol(0,0,1)} \gdef\Cyan{\Setcol(0,1,1)} \gdef\Magenta{\Setcol(1,0,1)} \gdef\Yellow{\Setcol(1,1,0)} \gdef\White{\Setcol(1,1,1)} % ------------------------------------------------------------------------- % The first macro strokes with current and fills with specified color. % \Fill(r,g,b) % The second macro simply uses gray instead of a color value % \Gfill(gr) % The third strokes and fills with the current color (CR, CG, CB). % \Sfill % ------------------------------------------------------------------------- \gdef\Fill(#1,#2,#3){\@setcol(f,#1,#2,#3) \PDF{B*}} \gdef\Gfill(#1){\@setcol(f,#1,#1,#1) \PDF{B*}} \gdef\Sfill{\Fill(\Np\@CR,\Np\@CG,\Np\@CB)} % ------------------------------------------------------------------------- % The main PDF commands, please read a PDF-Specification fore their meaning % and also the documentation of Lapdf % ------------------------------------------------------------------------- \gdef\Gsave{\PDF{q}} \gdef\Grestore{\PDF{Q}} \gdef\Setclip{\PDF{W* n}} \gdef\Stroke{\PDF{S}} \gdef\Closepath{\PDF{h}} \gdef\Setwidth(#1){\PDF{#1 w}} \gdef\Thick{\PDF{0.03 w}} \gdef\Thin{\PDF{0.01 w}} \gdef\Setcap(#1){\PDF{#1 J}} \gdef\Setjoin(#1){\PDF{#1 j}} \gdef\Setflat(#1){\PDF{#1 i}} \gdef\Setmiter(#1){\PDF{#1 M}} \gdef\Setdash(#1){\PDF{#1 d}} \gdef\Bezier(#1,#2,#3,#4,#5,#6){\PDF{#1 #2 #3 #4 #5 #6 c}} \gdef\Concat(#1,#2,#3,#4,#5,#6){\PDF{#1 #2 #3 #4 #5 #6 cm}} \gdef\Translate(#1,#2){\PDF{1 0 0 1 #1 #2 cm}} \gdef\Scale(#1,#2){\PDF{#1 0 0 #2 0 0 cm}} \gdef\Rotate(#1){\Cos(#1,\@ax) \Sin(#1,\@bx) \@cx=-\@bx \@rotate(\Np\@ax,\Np\@bx,\Np\@cx)} \gdef\@rotate(#1,#2,#3){\PDF{#1 #2 #3 #1 0 0 cm}} \gdef\Rect(#1,#2,#3,#4){\PDF{#1 #2 #3 #4 re}} % ------------------------------------------------------------------------- % \Dash(n) 4 predefined standard dashes (0..3). % ------------------------------------------------------------------------- \gdef\Dash(#1){\def\@c{#1} \ifnum\@c=0 \PDF{[] 0 d} \fi \ifnum\@c=1 \PDF{[0.1 0.1] 0 d} \fi \ifnum\@c=2 \PDF{[0.1 0.1 0.025 0.1] 0 d} \fi \ifnum\@c=3 \PDF{[0.025 0.1] 0 d} \fi} % ------------------------------------------------------------------------- % Move to point and line drawing in affine space. % \Moveto(x1,y1) \Lineto(x1,y1) \Line(x1,y1,x2,y2) % ------------------------------------------------------------------------- \gdef\Moveto(#1,#2){\Dset(\@xx,#1) \Dset(\@xy,#2) \PDF{#1 #2 m}} \gdef\Lineto(#1,#2){\Dset(\@xx,#1) \Dset(\@xy,#2) \PDF{#1 #2 l}} \gdef\Line(#1,#2)(#3,#4){\Moveto(#1,#2) \Lineto(#3,#4)} % ------------------------------------------------------------------------- % Move to point in homogeneous space. % \Rmoveto(x1,y1,z1) % ------------------------------------------------------------------------- \gdef\Rmoveto(#1,#2,#3){\Dset(\@xx,#1) \Dset(\@xy,#2) \Dset(\@xz,#3) \PDF{#1 #2 m}} % ------------------------------------------------------------------------- % Helper macros for all the grid drawings. % ------------------------------------------------------------------------- \gdef\@Putline(#1,#2)(#3,#4)(#5){\put(#1,#2){\line(#3,#4){#5}}} \gdef\@Putvector(#1,#2)(#3,#4)(#5){\put(#1,#2){\vector(#3,#4){#5}}} \gdef\@Puttext(#1,#2)[#3]#4{\put(#1,#2){\makebox(0,0)[#3]{#4}}} % ------------------------------------------------------------------------- % Helper: Draws a graphic dot at point (x,y). % \@Gdot(x,y) % ------------------------------------------------------------------------- \gdef\@Gbox{\setbox\@tbox\hbox{\hskip-\@halfwidth% \vrule\@height\@halfwidth\@depth\@halfwidth\@width\@wholewidth}} \gdef\@Gdot(#1,#2){\@killglue \raise#2\hb@xt@\z@{\kern#1\unhcopy\@tbox\hss}} % ------------------------------------------------------------------------- % Helper: Draws a dashed line with n points per unitlength from current % point to x,y. \@Gline(n)(x,y) % ------------------------------------------------------------------------- \gdef\@Gline(#1)(#2,#3){% \@cm=#1 \@ci=0 \@dx=#2\Ul \@dy=#3\Ul \Div(\@dx,\@cm) \Div(\@dy,\@cm) \Add(\@cm,1) \@Gbox \@whilenum{\@ci<\@cm}\do{% \@@X=\@ci\@dx \@@Y=\@ci\@dy \@Gdot(\@@X,\@@Y) \Add(\@ci,1)}} % ------------------------------------------------------------------------- % Helper: Draws a dashed circle of radius r with 10 points per unitlength. % \@Gcircle(r) % ------------------------------------------------------------------------- \gdef\@Gcircle(#1){% \@cm=#1 \Mul(\@cm,63) \@ci=0 \Dset(\@dx,6.2832) \Div(\@dx,\@cm) \@Gbox \@whilenum{\@ci<\@cm}\do{% \@dy=\@ci\@dx \Cos(\Np\@dy,\@@X) \@@X=#1\@@X \Sin(\Np\@dy,\@@Y) \@@Y=#1\@@Y \@Gdot(\Np\@@X\Ul,\Np\@@Y\Ul) \Add(\@ci,1)}} % ------------------------------------------------------------------------- % Draws a linear grid with n points per unitlength. A grid is drawn if g>0. % Value a may be 0 (no axes), 1 (simple axes), 2 (additional tickmarks) % or 3 (additional values). \Lingrid(n)(g,a)(xmin,max)(ymin,ymax) % ------------------------------------------------------------------------- \gdef\Lingrid(#1)(#2,#3)(#4,#5)(#6,#7){% \end{pdf} \scriptsize \linethickness{\wid} \@cd=#7 \Sub(\@cd,#6) \@cg=\@cd \Mul(\@cg,#1) \@cb=#4 \@cc=#5 \Add(\@cc,1) \ifnum#4=0 \ifnum#3>1 \@Putline(-0.1,0)(1,0)(0.1) \fi \ifnum#3>2 \@Puttext(-0.15,0)[rc]{0} \fi \fi \ifnum#6=0 \ifnum#3>1 \@Putline(0,-0.1)(0,1)(0.1) \fi \ifnum#3>2 \@Puttext(0,-0.15)[ct]{0} \fi \fi \@whilenum{\@cb<\@cc}\do{% \ifnum#2=1 \put(\@cb,#6){\@Gline(\@cg)(0,\@cd)} \fi \ifnum\@cb=0 \else \ifnum#3>1 \@Putline(\@cb,-0.1)(0,1)(0.1) \fi \ifnum#3>2 \@Puttext(\@cb,-0.15)[ct]{\the\@cb} \fi \fi \Add(\@cb,1)} \@cd=#5 \Sub(\@cd,#4) \@cg=\@cd \Mul(\@cg,#1) \@cb=#6 \@cc=#7 \Add(\@cc,1) \@whilenum{\@cb<\@cc}\do{% \ifnum#2=1 \put(#4,\@cb){\@Gline(\@cg)(\@cd,0)} \fi \ifnum\@cb=0 \else \ifnum#3>1 \@Putline(-0.1,\@cb)(1,0)(0.1) \fi \ifnum#3>2 \@Puttext(-0.15,\@cb)[rc]{\the\@cb} \fi \fi \Add(\@cb,1)} \Dset(\@@X,#5) \Dsub(\@@X,#4) \Dadd(\@@X,0.4) \Dset(\@@Y,#7) \Dsub(\@@Y,#6) \Dadd(\@@Y,0.4) \ifnum#3>0 \@Putvector(#4,0)(1,0)(\Np\@@X) \@Putvector(0,#6)(0,1)(\Np\@@Y) \fi \begin{pdf}} % ------------------------------------------------------------------------- % Draws a grid with n points per unitlength. It is horizontal logarithmic % and vertical linear. A grid is drawn if g>0. Value a may be 0 (no axes), % 1 (simple axes), 2 (additional tickmarks) or 3 (additional values). % \Logxgrid(n)(g,a)(xmin,max)(ymin,ymax) % ------------------------------------------------------------------------- \gdef\Logxgrid(#1)(#2,#3)(#4,#5)(#6,#7){% \end{pdf} \scriptsize \linethickness{\wid} \@cd=#7 \Sub(\@cd,#6) \@cg=\@cd \Mul(\@cg,#1) \@cb=1 \@cc=0 \@ca=#4 \ifnum#6=0 \ifnum#3>1 \@Putline(0,-0.1)(0,1)(0.1) \fi \ifnum#3>2 \@Puttext(0,-0.15)[ct]{$10^{\the\@ca}$} \fi \fi \@whilenum{\@ca<#5}\do{\Log(10,\@cb,\@@X) \Dadd(\@@X,\@cc) \Mul(\@@X,5) \ifnum#2=1 \put(\Np\@@X,#6){\@Gline(\@cg)(0,\@cd)} \fi \ifnum\@cb<10 \Add(\@cb,1) \else \@cb=2 \Add(\@cc,1) \Add(\@ca,1) \ifnum#3>1 \@Putline(\Np\@@X,-0.1)(0,1)(0.1) \fi \ifnum#3>2 \@Puttext(\Np\@@X,-0.15)[ct]{$10^{\the\@ca}$} \fi \fi} \@cd=#5 \Sub(\@cd,#4) \Mul(\@cd,5) \@cg=\@cd \Mul(\@cg,#1) \@cb=#6 \@cc=#7 \Add(\@cc,1) \@whilenum{\@cb<\@cc}\do{% \ifnum#2=1 \put(0,\@cb){\@Gline(\@cg)(\@cd,0)} \fi \ifnum#3>1 \@Putline(-0.1,\@cb)(1,0)(0.1) \fi \ifnum#3>2 \@Puttext(-0.15,\@cb)[rc]{\the\@cb} \fi \Add(\@cb,1)} \Dset(\@@X,#5) \Dsub(\@@X,#4) \Mul(\@@X,5) \Dadd(\@@X,0.4) \Dset(\@@Y,#7) \Dsub(\@@Y,#6) \Dadd(\@@Y,0.4) \ifnum#3>0 \@Putvector(-0.1,0)(1,0)(\Np\@@X) \@Putvector(0,#6)(0,1)(\Np\@@Y) \fi \begin{pdf}} % ------------------------------------------------------------------------- % Draws a grid with n points per unitlength. It is horizontal linear and % vertical logarithmic. A grid is drawn if g>0. Value a may be 0 (no axes), % 1 (simple axes), 2 (additional tickmarks) or 3 (additional values). % \Logygrid(n)(g,a)(xmin,max)(ymin,ymax) % ------------------------------------------------------------------------- \gdef\Logygrid(#1)(#2,#3)(#4,#5)(#6,#7){% \end{pdf} \scriptsize \linethickness{\wid} \@cd=#7 \Sub(\@cd,#6) \@cg=\@cd \Mul(\@cg,#1) \@cb=1 \@cc=0 \@ca=#4 \ifnum#6=0 \ifnum#3>1 \@Putline(-0.1,0)(1,0)(0.1) \fi \ifnum#3>2 \@Puttext(-0.15,0)[rc]{$10^{\the\@ca}$} \fi \fi \@whilenum{\@ca<#5}\do{\Log(10,\@cb,\@@Y) \Dadd(\@@Y,\@cc) \Mul(\@@Y,5) \ifnum#2=1 \put(#6,\Np\@@Y){\@Gline(\@cg)(\@cd,0)} \fi \ifnum\@cb<10 \Add(\@cb,1) \else \@cb=2 \Add(\@cc,1) \Add(\@ca,1) \ifnum#3>1 \@Putline(-0.1,\Np\@@Y)(1,0)(0.1) \fi \ifnum#3>2 \@Puttext(-0.15,\Np\@@Y)[rc]{$10^{\the\@ca}$} \fi \fi} \@cd=#5 \Sub(\@cd,#4) \Mul(\@cd,5) \@cg=\@cd \Mul(\@cg,#1) \@cb=#6 \@cc=#7 \Add(\@cc,1) \@whilenum{\@cb<\@cc}\do{% \ifnum#2=1 \put(\@cb,0){\@Gline(\@cg)(0,\@cd)} \fi \ifnum#3>1 \@Putline(\@cb,-0.1)(0,1)(0.1) \fi \ifnum#3>2 \@Puttext(\@cb,-0.15)[ct]{\the\@cb} \fi \Add(\@cb,1)} \Dset(\@@Y,#5) \Dsub(\@@Y,#4) \Mul(\@@Y,5) \Dadd(\@@Y,0.4) \Dset(\@@X,#7) \Dsub(\@@X,#6) \Dadd(\@@X,0.4) \ifnum#3>0 \@Putvector(#6,0)(1,0)(\Np\@@X) \@Putvector(0,-0.1)(0,1)(\Np\@@Y) \fi \begin{pdf}} % ------------------------------------------------------------------------- % Draws a grid with n points per unitlength. It is logarithmic in both % directions. A grid is drawn if g>0. Value a may be 0 (no axes), % 1 (simple axes), 2 (additional tickmarks) or 3 (additional values). % \Logxygrid(n)(g,a)(xmin,max)(ymin,ymax) % ------------------------------------------------------------------------- \gdef\Logxygrid(#1)(#2,#3)(#4,#5)(#6,#7){% \end{pdf} \scriptsize \linethickness{\wid} \@cd=#7 \Sub(\@cd,#6) \Mul(\@cd,5) \@cg=\@cd \Mul(\@cg,#1) \@cb=1 \@cc=0 \@ca=#4 \ifnum#6=0 \ifnum#3>1 \@Putline(0,-0.1)(0,1)(0.1) \fi \ifnum#3>2 \@Puttext(0,-0.15)[ct]{$10^{\the\@ca}$} \fi \fi \@whilenum{\@ca<#5}\do{\Log(10,\@cb,\@@X) \Dadd(\@@X,\@cc) \Mul(\@@X,5) \ifnum#2=1 \put(\Np\@@X,#6){\@Gline(\@cg)(0,\@cd)} \fi \ifnum\@cb<10 \Add(\@cb,1) \else \@cb=2 \Add(\@cc,1) \Add(\@ca,1) \ifnum#3>1 \@Putline(\Np\@@X,-0.1)(0,1)(0.1) \fi \ifnum#3>2 \@Puttext(\Np\@@X,-0.15)[ct]{$10^{\the\@ca}$} \fi \fi} \@cd=#5 \Sub(\@cd,#4) \Mul(\@cd,5) \@cg=\@cd \Mul(\@cg,#1) \@cb=1 \@cc=0 \@ca=#6 \ifnum#6=0 \ifnum#3>1 \@Putline(-0.1,0)(1,0)(0.1) \fi \ifnum#3>2 \@Puttext(-0.15,0)[rc]{$10^{\the\@ca}$} \fi \fi \@whilenum{\@ca<#7}\do{\Log(10,\@cb,\@@Y) \Dadd(\@@Y,\@cc) \Mul(\@@Y,5) \ifnum#2=1 \put(#6,\Np\@@Y){\@Gline(\@cg)(\@cd,0)} \fi \ifnum\@cb<10 \Add(\@cb,1) \else \@cb=2 \Add(\@cc,1) \Add(\@ca,1) \ifnum#3>1 \@Putline(-0.1,\Np\@@Y)(1,0)(0.1) \fi \ifnum#3>2 \@Puttext(-0.15,\Np\@@Y)[rc]{$10^{\the\@ca}$} \fi \fi} \Dset(\@@X,#5) \Dsub(\@@X,#4) \Mul(\@@X,5) \Dadd(\@@X,0.4) \Dset(\@@Y,#7) \Dsub(\@@Y,#6) \Mul(\@@Y,5) \Dadd(\@@Y,0.4) \ifnum#3>0 \@Putvector(-0.1,0)(1,0)(\Np\@@X) \@Putvector(0,-0.1)(0,1)(\Np\@@Y) \fi \begin{pdf}} % ------------------------------------------------------------------------- % Draws a polar grid with 10 points per unitlength and maximum radius r. % If g>0, a grid is drawn. Value a may be 0 (no axes), 1 (simple axes), % 2 (additional tickmarks), 3 (additional values, angles in degree) or % 4 (like 3, but angles in multiples of pi). \Polgrid(g,a)(r) % ------------------------------------------------------------------------- \gdef\Polgrid(#1,#2)(#3){% \end{pdf} \scriptsize \linethickness{\wid} \@ca=0 \@whilenum{\@ca<#3}\do{% \Add(\@ca,1) \ifnum#1>0 \@Gcircle(\@ca) \fi \ifnum#2>1 \ifnum\@ca=0 \else \@Putline(\@ca,-0.1)(0,1)(0.1) \@Putline(-\@ca,-0.1)(0,1)(0.1) \@Putline(-0.1,\@ca)(1,0)(0.1) \@Putline(-0.1,-\@ca)(1,0)(0.1) \ifnum#2>2 \@Puttext(\@ca,-0.15)[tc]{\the\@ca} \fi \fi \fi} \@ca=0 \@cb=0 \@whilenum{\@ca<360}\do{% \@cb=#3 \Mul(\@cb,10) \Rad(\@ca,\@ax) \ifnum#1>0 \Cos(\Np\@ax,\@@X) \Mul(\@@X,#3) \Sin(\Np\@ax,\@@Y) \Mul(\@@Y,#3) \put(0,0){\@Gline(\@cb)(\Np\@@X,\Np\@@Y)} \fi \ifnum#2>2 \Dset(\@@U,#3) \Dadd(\@@U,0.35) \Cos(\Np\@ax,\@@X) \Dmul(\@@X,\@@U) \Sin(\Np\@ax,\@@Y) \Dmul(\@@Y,\@@U) \ifnum#2>3 \@cb=\@ca \Div(\@cb,15) \ifnum\@ca=0 \@Puttext(\Np\@@X,\Np\@@Y)[cc]{0} \else \@cc=\@cb \Mod(\@cc,6) \ifnum\@cc=0 \Div(\@cb,6) \ifnum\@cb=2 \@Puttext(\Np\@@X,\Np\@@Y)[cc]{$\pi$} \else \@Puttext(\Np\@@X,\Np\@@Y)[cc]{$\frac{\the\@cb}{2}\pi$} \fi \else \@Puttext(\Np\@@X,\Np\@@Y)[cc]{$\frac{\the\@cb}{12}\pi$} \fi \fi \else \@Puttext(\Np\@@X,\Np\@@Y)[cc]{$\the\@ca^{\circ}$} \fi \fi \Add(\@ca,15)} \ifnum#2>0 \Dset(\@@X,#3) \Mul(\@@X,2) \@Putline(-#3,0)(1,0)(\Np\@@X) \@Putline(0,-#3)(0,1)(\Np\@@X) \fi \begin{pdf}} % ------------------------------------------------------------------------- % Plots a function with n line segments from x1 to x2. You have to define % a function \Fx with the command: \def\Fx(#1,#2){..}. #1 is the x value % and #2 is the result register. \Fplot(n)(x1,x2) Examples: % \def\Fx(#1,#2){\Sin(#1,#2) \Mul(#2,3) \Dadd(#2,1)} y=3*sin(x)+1 % \def\Fx(#1,#2){\Dset(\x,#1) \Dsub(\x,2) \Exp(\Np\x,#2)} y=exp(x-2) % ------------------------------------------------------------------------- \gdef\Fplot(#1)(#2,#3){% \Dset(\@dx,#3) \Dsub(\@dx,#2) \Div(\@dx,#1) \Dset(\@ux,#2) \Fx(\Np\@ux,\@uy) \Moveto(\Np\@ux,\Np\@uy) \@whiledim{\@ux<#3pt}\do{\Add(\@ux,\@dx) \ifdim\@ux>#3pt \Dset(\@ux,#3) \fi \Fx(\Np\@ux,\@uy) \Lineto(\Np\@ux,\Np\@uy)}} % ------------------------------------------------------------------------- % Plots a parametric function with n line segments for t1 to t2. You have % to define two functions \Tx and \Ty with the commands: \def\Tx(#1,#2){..} % and \def\Ty(#1,#2){..}. Here #1 is the t value and #2 is the result % register. \Tplot(n)(t1,t2) Example: % \def\Tx(#1,#2){\Dset(#2,#1) \Mul(#2,2) \Dsub(#2,1)} x=2*t-1 % \def\Ty(#1,#2){\Dset(\t,#1) #2=\t \Dmul(#2,#2) \Add(#2,\t)} y=t^2+t % ------------------------------------------------------------------------- \gdef\Tplot(#1)(#2,#3){% \Dset(\@dx,#3) \Dsub(\@dx,#2) \Div(\@dx,#1) \Dset(\@@U,#2) \Tx(\Np\@@U,\@ux) \Dset(\@@U,#2) \Ty(\Np\@@U,\@uy) \Moveto(\Np\@ux,\Np\@uy) \@whiledim{\@@U<#3pt}\do{\Add(\@@U,\@dx) \ifdim\@@U>#3pt \Dset(\@@U,#3) \fi \Tx(\Np\@@U,\@ux) \Ty(\Np\@@U,\@uy) \Lineto(\Np\@ux,\Np\@uy)}} % ------------------------------------------------------------------------- % Converts a polar function r=f(a) to parametric cartesian form with: % x=f(a)*cos(a), y=f(a)*sin(a). The result is returned in regs x and y. % \Pxy(a,x,y) % ------------------------------------------------------------------------- \gdef\Pxy(#1,#2,#3){% \Px(#1,#2) #3=#2 \Cos(#1,\@@T) \Dmul(#2,\@@T) \Sin(#1,\@@T) \Dmul(#3,\@@T)} % ------------------------------------------------------------------------- % Plots a polar function with n line segments from a1 to a2. You have to % define a function \Px with the command: \def\Px(#1,#2){..}. #1 is the x % value and #2 is the result register. \Pplot(n)(a1,a2) Examples: % \def\Px(#1,#2){\Dset(\a,#1) #2=2\a \Sin(\Np#2,#2)} r=cos(2a) % \def\Px(#1,#2){\Dset(\Sin(#1,#2) \Dadd(#2,1)} r=1+sin(a) % ------------------------------------------------------------------------- \gdef\Pplot(#1)(#2,#3){% \Dset(\@tx,#2) \Dset(\@ty,#3) \Dmul(\@tx,3.14159pt) \Dmul(\@ty,3.14159pt) \@dx=\@ty \Sub(\@dx,\@tx) \Div(\@dx,#1) \@@U=\@tx \Pxy(\Np\@@U,\@ux,\@uy) \Moveto(\Np\@ux,\Np\@uy) \@whiledim{\@@U<\@ty}\do{\Add(\@@U,\@dx) \ifdim\@@U>\@ty \@@U=\@ty \fi \Pxy(\Np\@@U,\@ux,\@uy) \Lineto(\Np\@ux,\Np\@uy)}} % ------------------------------------------------------------------------- % Calculates the derivative dy/dx of a predefined real function \Fx. % The value is x and the result is stored in register n. \Df(x,n) % ------------------------------------------------------------------------- \gdef\Df(#1,#2){% \Dset(\@dx,#1) \@dy=\@dx \Dadd(\@dy,0.015625) \Dsub(\@dx,0.015625) \Fx(\Np\@dy,#2) \Fx(\Np\@dx,\@dx) \Sub(#2,\@dx) #2=32#2} % ------------------------------------------------------------------------- % Calculates the partial derivative dx/dt of a predefined parameter curve % \Tx. The value is t and the result is stored in register n. \Dtx(t,n) % ------------------------------------------------------------------------- \gdef\Dtx(#1,#2){% \Dset(\@dx,#1) \@dy=\@dx \Dadd(\@dy,0.015625) \Dsub(\@dx,0.015625) \Tx(\Np\@dy,#2) \Tx(\Np\@dx,\@dx) \Sub(#2,\@dx) #2=32#2} % ------------------------------------------------------------------------- % Calculates the partial derivative dy/dt of a predefined parameter curve % \Ty. The value is t and the result is stored in register n. \Dty(t,n) % ------------------------------------------------------------------------- \gdef\Dty(#1,#2){% \Dset(\@dx,#1) \@dy=\@dx \Dadd(\@dy,0.015625) \Dsub(\@dx,0.015625) \Ty(\Np\@dy,#2) \Ty(\Np\@dx,\@dx) \Sub(#2,\@dx) #2=32#2} % ------------------------------------------------------------------------- % Calculates the total derivative dy/dx of a predefined parameter curve % \Ty, \Tx. The value is t and the result is stored in register n. \Dtt(t,n) % ------------------------------------------------------------------------- \gdef\Dtt(#1,#2){% \Dty(#1,#2) \Dtx(#1,\@dz) \Ddiv(#2,\@dz)} % ------------------------------------------------------------------------- % Calculates the partial derivative dx/da of a predefined polar curve \Px. % The value is a and the result is stored in register n. \Dpx(a,n) % ------------------------------------------------------------------------- \gdef\Dpx(#1,#2){% \Dset(\@dx,#1) \@dy=\@dx \Dadd(\@dy,0.015625) \Dsub(\@dx,0.015625) \Px(\Np\@dy,#2) \Cos(\Np\@dy,\@dy) \Dmul(#2,\@dy) \Px(\Np\@dx,\@tx) \Cos(\Np\@dx,\@dx) \Dmul(\@tx,\@dx) \Sub(#2,\@tx) #2=32#2} % ------------------------------------------------------------------------- % Calculates the partial derivative dy/da of a predefined polar curve \Px. % The value is a and the result is stored in register n. \Dpy(a,n) % ------------------------------------------------------------------------- \gdef\Dpy(#1,#2){% \Dset(\@dx,#1) \@dy=\@dx \Dadd(\@dy,0.015625) \Dsub(\@dx,0.015625) \Px(\Np\@dy,#2) \Sin(\Np\@dy,\@dy) \Dmul(#2,\@dy) \Px(\Np\@dx,\@tx) \Sin(\Np\@dx,\@dx) \Dmul(\@tx,\@dx) \Sub(#2,\@tx) #2=32#2} % ------------------------------------------------------------------------- % Calculates the total derivative dy/dx of a predefined polar curve \Px. % The value is a and the result is stored in register n. \Dtp(a,n) % ------------------------------------------------------------------------- \gdef\Dtp(#1,#2){% \Dpy(#1,#2) \Dpx(#1,\@dz) \Ddiv(#2,\@dz)} % ------------------------------------------------------------------------- % Draws a full ellipse with two rational quadratic bezier curves. x,y is % the center, a and b are the diameters, n is the number of segments and c % is the rotation angle in degree. \Ellipse(n)(x,y)(a,b,c) % ------------------------------------------------------------------------- \gdef\Ellipse(#1)(#2,#3)(#4,#5,#6){% \@tb=#1 \Mul(\@tb,3) \Rad(#6,\@sx) \Dset(\@ux,#2) \Dset(\@uy,#3) \Dset(\@vx,#2) \Dset(\@vy,#3) \Dset(\@wx,#2) \Dset(\@wy,#3) \Dset(\@ax,#4) \Dset(\@ay,#5) \Sin(\Np\@sx,\@sy) \Cos(\Np\@sx,\@sx) \@bx=0.866\@ax \@by=0.500\@ay \@cx=\@bx \@cy=\@by \Dmul(\@bx,\@sx)\Dmul(\@by,\@sy) \Dmul(\@cx,\@sy)\Dmul(\@cy,\@sx) \Sub(\@ux,\@bx) \Sub(\@ux,\@by) \Sub(\@uy,\@cx) \Add(\@uy,\@cy) \Add(\@wx,\@bx) \Sub(\@wx,\@by) \Add(\@wy,\@cx) \Add(\@wy,\@cy) \@bx=0.000\@ax \@by=2.000\@ay \@cx=\@bx \@cy=\@by \Dmul(\@bx,\@sx)\Dmul(\@by,\@sy) \Dmul(\@cx,\@sy)\Dmul(\@cy,\@sx) \Add(\@vx,\@bx) \Sub(\@vx,\@by) \Add(\@vy,\@cx) \Add(\@vy,\@cy) \Rmoveto(\Np\@ux,\Np\@uy,2) \Rcurveto(#1)(\Np\@vx,\Np\@vy,1)(\Np\@wx,\Np\@wy,2) \Rcurveto(\@tb)(\Np\@vx,\Np\@vy,-1)(\Np\@ux,\Np\@uy,2)} % ------------------------------------------------------------------------- % Draws a full circle with two rational quadratic Bezier curves. % \Circle(n)(x,y,radius) % ------------------------------------------------------------------------- \gdef\Circle(#1)(#2,#3,#4){% \Set(\@tb,#1) \Mul(\@tb,2) \Dset(\@ux,#2) \Dset(\@uy,#3) \Dset(\@vx,#2) \Dset(\@vy,#3) \Dset(\@wx,#2) \Dset(\@wy,#3) \Dset(\@ax,#4) \Dset(\@ay,#4) \Dset(\@az,#4) \@ax=0.866\@ax \@ay=0.500\@ay \@az=2.000\@az \Sub(\@ux,\@ax) \Add(\@wx,\@ax) \Sub(\@uy,\@ay) \Sub(\@vy,\@az) \Sub(\@wy,\@ay) \Rmoveto(\Np\@ux,\Np\@uy,2) \Rcurveto(#1)(\Np\@vx,\Np\@vy,1)(\Np\@wx,\Np\@wy,2) \Rcurveto(\@tb)(\Np\@vx,\Np\@vy,-1)(\Np\@ux,\Np\@uy,2)} % ------------------------------------------------------------------------- % Draws a rectangle between two points, rotated at point x1,y1 by angle a % in degree. \Rectangle(x1,y1)(x2,y2)(a) % ------------------------------------------------------------------------- \gdef\Rectangle(#1,#2)(#3,#4)(#5){% \Dset(\@cx,#3) \Dset(\@cy,#4) \Dset(\@@U,#5) \@bx=\@cx \Dset(\@by,0) \Dset(\@dx,0) \@dy=\@cy \Rotpoint(#5)(\Np\@bx,\Np\@by)(\@ux,\@uy) \Rotpoint(#5)(\Np\@cx,\Np\@cy)(\@vx,\@vy) \Rotpoint(#5)(\Np\@dx,\Np\@dy)(\@wx,\@wy) \Dadd(\@ux,#1) \Dadd(\@uy,#2) \Dadd(\@vx,#1) \Dadd(\@vy,#2) \Dadd(\@wx,#1) \Dadd(\@wy,#2) \Polygon(#1,#2)(\Np\@ux,\Np\@uy)(\Np\@vx,\Np\@vy)(\Np\@wx,\Np\@wy)(#1,#2)} % ------------------------------------------------------------------------- % Draws a triangle between three points, rotated at point x1,y1 by angle a % in degree. \Triangle(x1,y1)(x2,y2)(x3,y3)(a) % ------------------------------------------------------------------------- \gdef\Triangle(#1,#2)(#3,#4)(#5,#6)(#7){% \Dset(\@bx,#3) \Dsub(\@bx,#1) \Dset(\@by,#4) \Dsub(\@by,#2) \Dset(\@cx,#5) \Dsub(\@cx,#1) \Dset(\@cy,#6) \Dsub(\@cy,#2) \Rotpoint(#7)(\Np\@bx,\Np\@by)(\@ux,\@uy) \Rotpoint(#7)(\Np\@cx,\Np\@cy)(\@vx,\@vy) \Dadd(\@ux,#1) \Dadd(\@uy,#2) \Dadd(\@vx,#1) \Dadd(\@vy,#2) \Polygon(#1,#2)(\Np\@ux,\Np\@uy)(\Np\@vx,\Np\@vy)(#1,#2)} % ------------------------------------------------------------------------- % Draws a equilateral polygon with radius r and n vertices. It is rotated % around the center x,y by an angle a in degree. The first (unrotated) % point is r,0. \Epolygon(n)(x,y)(r,a) % ------------------------------------------------------------------------- \gdef\Epolygon(#1)(#2,#3)(#4,#5){% \Rotpoint(#5)(#4,0)(\@vx,\@vy) \Dadd(\@vx,#2) \Dadd(\@vy,#3) \@ch=0 \Moveto(\Np\@vx,\Np\@vy) \@whilenum{\@ch<#1}\do{\Add(\@ch,1) \Dset(\@ax,6.2832) \Div(\@ax,#1) \Mul(\@ax,\@ch) \Cos(\Np\@ax,\@vx) \Dmul(\@vx,#4pt) \Sin(\Np\@ax,\@vy) \Dmul(\@vy,#4pt) \Rotpoint(#5)(\Np\@vx,\Np\@vy)(\@vx,\@vy) \Dadd(\@vx,#2) \Dadd(\@vy,#3) \Lineto(\Np\@vx,\Np\@vy)}} % ------------------------------------------------------------------------- % Draws a sector of a circle with center xm,ym, radius r, direction a and % angle b in degree with n segments. \Sector(n)(xm,ym)(a,b)(r) % ------------------------------------------------------------------------- \gdef\Sector(#1)(#2,#3)(#4,#5)(#6){% \Dset(\@ax,#4) \Dset(\@bx,#5) \Dset(\@rx,#6) \@ch=0 \Rad(#4,\@sx) \Cos(\Np\@sx,\@sx) \Dmul(\@sx,\@rx) \Rad(#4,\@sy) \Sin(\Np\@sy,\@sy) \Dmul(\@sy,\@rx) \Dadd(\@sx,#2) \Dadd(\@sy,#3) \Line(#2,#3)(\Np\@sx,\Np\@sy) \@whilenum{\@ch<#1}\do{\Add(\@ch,1) \Dset(\@dx,#5) \Div(\@dx,#1) \Mul(\@dx,\@ch) \Dadd(\@dx,#4) \Rad(\Np\@dx,\@sx) \Cos(\Np\@sx,\@sx) \Dmul(\@sx,\@rx) \Rad(\Np\@dx,\@sy) \Sin(\Np\@sy,\@sy) \Dmul(\@sy,\@rx) \Dadd(\@sx,#2) \Dadd(\@sy,#3) \Lineto(\Np\@sx,\Np\@sy)} \Lineto(#2,#3)} % ------------------------------------------------------------------------- % These draw a circular arc (or a circular vector) with center xm,ym, % radius r, direction a and angle b in degree with n segments. Both use % \@Arc. \Arc(n)(xm,ym)(a,b)(r) \Varc(n)(xm,ym)(a,b)(r) % ------------------------------------------------------------------------- \gdef\Arc(#1)(#2,#3)(#4,#5)(#6){\@Arc(#1)(#2,#3)(#4,#5)(#6,0)} \gdef\Varc(#1)(#2,#3)(#4,#5)(#6){\@Arc(#1)(#2,#3)(#4,#5)(#6,1)} % ------------------------------------------------------------------------- % Helper macro that draws a circular arc (t=0) or vector (t=1). % It is called by \Arc and \Varc. \@Arc(n)(xm,ym)(a,b)(r,t) % ------------------------------------------------------------------------- \gdef\@Arc(#1)(#2,#3)(#4,#5)(#6,#7){% \Dset(\@ax,#4) \Dset(\@bx,#5) \Dset(\@rx,#6) \@ch=0 \Rad(#4,\@vx) \Cos(\Np\@vx,\@vx) \Dmul(\@vx,\@rx) \Rad(#4,\@vy) \Sin(\Np\@vy,\@vy) \Dmul(\@vy,\@rx) \Dadd(\@vx,#2) \Dadd(\@vy,#3) \@whilenum{\@ch<#1}\do{\Add(\@ch,1) \@ux=\@vx \@uy=\@vy \Dset(\@dx,#5) \Div(\@dx,#1) \Mul(\@dx,\@ch) \Dadd(\@dx,#4) \Rad(\Np\@dx,\@vx) \Cos(\Np\@vx,\@vx) \Dmul(\@vx,\@rx) \Rad(\Np\@dx,\@vy) \Sin(\Np\@vy,\@vy) \Dmul(\@vy,\@rx) \Dadd(\@vx,#2) \Dadd(\@vy,#3) \ifnum#7=0 \Polygon(\Np\@ux,\Np\@uy)(\Np\@vx,\Np\@vy) \else \ifnum\@ch<#1 \Polygon(\Np\@ux,\Np\@uy)(\Np\@vx,\Np\@vy) \else {\Vpolygon(\Np\@ux,\Np\@uy)(\Np\@vx,\Np\@vy) \Stroke} \fi \fi}} % ------------------------------------------------------------------------- % Draws a circular arc with center xm,ym, radius r, direction a and angle b % with n segments. The incoming direction goes from the current point. The % last point x2, y2 gives the outgoing direcion. Lines from the current % point and to the end point are also drawn. \Arcto(n)(x1,y1)(x2,y2)(r) % ------------------------------------------------------------------------- \gdef\Arcto(#1)(#2,#3)(#4,#5)(#6){% \Dset(\@yx,#2) \Dset(\@yy,#3) \Dset(\@zx,#4) \Dset(\@zy,#5) \Dset(\@rx,#6) \Direc(#2,#3)(\Np\@xx,\Np\@xy)(\@ax) \Direc(#2,#3)(\Np\@zx,\Np\@zy)(\@ay) \Len(\Np\@yx,\Np\@yy)(\Np\@xx,\Np\@xy)(\@dx) \Len(\Np\@yx,\Np\@yy)(\Np\@zx,\Np\@zy)(\@dy) \Len(\Np\@xx,\Np\@xy)(\Np\@zx,\Np\@zy)(\@dz) \Cos(\Np\@ay,\@ex) \Dmul(\@ex,\@dx) \Add(\@ex,\@xx) \Add(\@ex,\@yx) \@ex=0.5\@ex \Sin(\Np\@ay,\@ey) \Dmul(\@ey,\@dx) \Add(\@ey,\@xy) \Add(\@ey,\@yy) \@ey=0.5\@ey \Direc(\Np\@yx,\Np\@yy)(\Np\@ex,\Np\@ey)(\@az) \@cy=2.0\@dx \Dmul(\@cy,\@dy) \Dmul(\@dx,\@dx) \Dmul(\@dy,\@dy) \Dmul(\@dz,\@dz) \Add(\@dx,\@dy) \Sub(\@dx,\@dz) \Ddiv(\@dx,\@cy) \Acos(\Np\@dx,\@cx) \@cy=0.5\@cx \Dset(\@@U,1.5708) \Sub(\@@U,\@cy) \Tan(\Np\@@U,\@dx) \Dmul(\@dx,\@rx) \Cos(\Np\@@U,\@@U) \Cos(\Np\@ax,\@ux) \Dmul(\@ux,\@dx) \Add(\@ux,\@yx) \Sin(\Np\@ax,\@uy) \Dmul(\@uy,\@dx) \Add(\@uy,\@yy) \Cos(\Np\@ay,\@vx) \Dmul(\@vx,\@dx) \Add(\@vx,\@yx) \Sin(\Np\@ay,\@vy) \Dmul(\@vy,\@dx) \Add(\@vy,\@yy) \Polygon(\Np\@xx,\Np\@xy)(\Np\@ux,\Np\@uy) \Stroke \Rcurve(#1)(\Np\@ux,\Np\@uy,1)(#2,#3,\Np\@@U)(\Np\@vx,\Np\@vy,1) \Lineto(#4,#5) \Stroke} % ------------------------------------------------------------------------- % Draws a vector from point x1,y1 to point x2,y2. \Vect(x1,y1)(x2,y2) % ------------------------------------------------------------------------- \gdef\Vect(#1,#2)(#3,#4){% \Dset(\@ux,#1) \Dset(\@uy,#2) \Len(\Np\@ux,\Np\@uy)(#3,#4)(\@tx) \Direc(\Np\@ux,\Np\@uy)(#3,#4)(\@ty) \@cd=0 \Deg(\Np\@ty,\@ty) \@dx=\@tx \Dsub(\@dx,0.20) \Dset(\@dy,0.05) \@ex=\@dx \@ey=-\@dy \Rotpoint(\Np\@ty)(\Np\@dx,\Np\@dy)(\@dx,\@dy) \Rotpoint(\Np\@ty)(\Np\@ex,\Np\@ey)(\@ex,\@ey) \Add(\@dx,\@ux) \Add(\@dy,\@uy) \Add(\@ex,\@ux) \Add(\@ey,\@uy) \Polygon(\Np\@ux,\Np\@uy)(#3,#4)(\Np\@dx,\Np\@dy)(\Np\@ex,\Np\@ey)(#3,#4) \Sfill} % ------------------------------------------------------------------------- % Draws a vector from the current point to point x1,y1. \Vecto(x1,y1) % ------------------------------------------------------------------------- \gdef\Vecto(#1,#2){\Vect(\Np\@xx,\Np\@xy)(#1,#2)} % ------------------------------------------------------------------------- % Computes the function value of a polynom (dregree <= 3) at x and stores % the result in y. \Fpoly(x,y) % ------------------------------------------------------------------------- \gdef\Fpoly(#1,#2){#2=\@ax \Dmul(#2,#1) \Add(#2,\@bx) \Dmul(#2,#1) \Add(#2,\@cx) \Dmul(#2,#1) \Add(#2,\@dx)} % ------------------------------------------------------------------------- % Computes the first derivative of a polynom (degree <= 3) at x and stores % the result in y. \Dpoly(x,y) % ------------------------------------------------------------------------- \gdef\Dpoly(#1,#2){#2=\@ax \Dmul(#2,#1) \Mul(#2,3) \Add(#2,\@bx) \Add(#2,\@bx) \Dmul(#2,#1) \Add(#2,\@cx)} % ------------------------------------------------------------------------- % Draws a polynom y=ax^3+bx^2+cx+d from x1 to x2 with a cubic bezier curve. % All coefficients may be zero. So you can draw lines, parabolas and cubics. % \Polynom(x1,x2)(a,b,c,d) % ------------------------------------------------------------------------- \gdef\Polynom(#1,#2)(#3,#4,#5,#6){% \Dset(\@sx,#1) \Dset(\@vx,#2) \Dset(\@ax,#3) \Dset(\@bx,#4) \Dset(\@cx,#5) \Dset(\@dx,#6) \@zx=\@vx \Sub(\@zx,\@sx) \Div(\@zx,3) \@tx=\@sx \Add(\@tx,\@zx) \@ux=\@vx \Sub(\@ux,\@zx) \Dpoly(\@sx,\@wx) \Dmul(\@wx,\@zx) \Dpoly(\@vx,\@wy) \Dmul(\@wy,\@zx) \Fpoly(\@sx,\@sy) \Fpoly(\@vx,\@vy) \@ty=\@sy \Add(\@ty,\@wx) \@uy=\@vy \Sub(\@uy,\@wy) \Moveto(\Np\@sx,\Np\@sy) \Bezier(\Np\@tx,\Np\@ty,\Np\@ux,\Np\@uy,\Np\@vx,\Np\@vy)} % ------------------------------------------------------------------------- % Draws the tangent of a polynom y=ax^3+bx^2+cx+d at abszissa x from x1 % to x2 and marks the touching point. \Tangent(x)(x1,x2)(a,b,c,d) % ------------------------------------------------------------------------- \gdef\Tangent(#1)(#2,#3)(#4,#5,#6,#7){% \Dset(\@xx,#1) \Dset(\@sx,#2) \Dset(\@tx,#3) \Dset(\@ax,#4) \Dset(\@bx,#5) \Dset(\@cx,#6) \Dset(\@dx,#7) \Fpoly(\@xx,\@xy) \Dpoly(\@xx,\@wx) \@sy=\@wx \@ty=\@wx \Dmul(\@sy,\@sx) \Dmul(\@ty,\@tx) \Add(\@sy,\@xy) \Add(\@ty,\@xy) \Dmul(\@wx,\@xx) \Sub(\@sy,\@wx) \Sub(\@ty,\@wx) \Line(\Np\@sx,\Np\@sy)(\Np\@tx,\Np\@ty) \Stroke \Point(1)(#1,\Np\@xy)} % ------------------------------------------------------------------------- % Draws a sequence of line segments. You have to provide m points % with m=i+1 (i=1,2,..). \Polygon(x1,y1)(x2,y2)...(xm,ym) % ------------------------------------------------------------------------- \gdef\Polygon{\@ifnextchar ({\@polygon}{\@ck=0}} \gdef\@polygon(#1,#2){\@ifnextchar ({\@pdraw(#1,#2)}{\@ck=0}} \gdef\@pdraw(#1,#2)(#3,#4){\ifnum\@ck=0 \@ck=1 \Moveto(#1,#2) \fi \Lineto(#3,#4) \Polygon(#3,#4)} % ------------------------------------------------------------------------- % Draws a sequence of vector segments. You have to provide m points % with m=i+1 (i=1,2,..). \Vpolygon(x1,y1)(x2,y2)...(xm,ym) % ------------------------------------------------------------------------- \gdef\Vpolygon{\@ifnextchar ({\@Vdraw}{\relax}} \gdef\@Vdraw(#1,#2){\@ifnextchar ({\@Vcoord(#1,#2)}{\relax}} \gdef\@Vcoord(#1,#2)(#3,#4){\Vect(#1,#2)(#3,#4) \Vpolygon(#3,#4)} % ------------------------------------------------------------------------- % Draws a sequence of quadratic bezier curves. % You have to provide m points with m=2*i+1 (i=1,2,..). % \Quadratic(x1,y1)(x2,y2)(x3,y3)...(xm,ym) % ------------------------------------------------------------------------- \gdef\Quadratic{\@ifnextchar ({\@Qdraw}{\relax}} \gdef\@Qdraw(#1,#2){\@ifnextchar ({\@Qcoord(#1,#2)}{\relax}} \gdef\@Qcoord(#1,#2)(#3,#4)(#5,#6){% \Dset(\@ax,#1) \Dset(\@ay,#2) \Dset(\@bx,#3) \Dset(\@by,#4) \Dset(\@cx,#5) \Dset(\@cy,#6) \Mul(\@bx,2) \Mul(\@by,2) \Add(\@ax,\@bx)\Div(\@ax,3) \Add(\@ay,\@by)\Div(\@ay,3) \Add(\@cx,\@bx)\Div(\@cx,3) \Add(\@cy,\@by)\Div(\@cy,3) \Moveto(#1,#2) \Bezier(\Np\@ax,\Np\@ay,\Np\@cx,\Np\@cy,#5,#6) \Quadratic(#5,#6)} % ------------------------------------------------------------------------- % Draws a sequence of n cubic bezier curves. % You have to provide m points with m=3*i+1 (i=1,2,..). % \Cubic(x1,y1)(x2,y2)(x3,y3)(x4,y4)...(xm,ym) % ------------------------------------------------------------------------- \gdef\Cubic{\@ifnextchar ({\@Cdraw}{\relax}} \gdef\@Cdraw(#1,#2){\@ifnextchar ({\@Ccoord(#1,#2)}{\relax}} \gdef\@Ccoord(#1,#2)(#3,#4)(#5,#6)(#7,#8){% \Moveto(#1,#2) \Bezier(#3,#4,#5,#6,#7,#8) \Cubic(#7,#8)} % ------------------------------------------------------------------------- % This is the general macro for drawing integral bezier curves. It draws % bezier curves of degree 1..7. The degree depends on the number of % coordinates. If \@ce is zero, the curve is drawn, depending on the % counter \@ci. If \@ce is not zero, the coordinates are read until no % more open cordinates are found. \Curveto needs \Moveto in front to % draw from the current point. % \Curve(n)(x0,y0)..., \Curveto(n)(x1,y1)... % ------------------------------------------------------------------------- \gdef\Curve{\@cg=0\@ce=1\@ifnextchar ({\@Draw}{\@Draw(0)}} \gdef\Curveto{\@cg=0\@ce=0\@ifnextchar ({\@Draw}{\@Draw(0)}} \gdef\@Draw(#1){\@ifnextchar ({\@Coord(#1)}{% \@ci=0 \ifcase\@cf\or\@Acurve\or \@Bcurve\or\@Ccurve\or\@Dcurve\or \@Ecurve\or\@Fcurve\or\@Gcurve\fi}} \gdef\@Coord(#1)(#2,#3){% \ifnum#1=0 \Add(\@cf,1) \Euclid(#2,#3) \else \@cf=0 \@ca=#1 \@cb=\@ca \Add(\@cb,1) \ifnum\@ce=1 \Dset(\@ax,#2)\Dset(\@ay,#3) \Moveto(\Np\@ax,\Np\@ay) \else \Add(\@cf,1) \@ax=\@xx \@ay=\@xy \Dset(\@bx,#2)\Dset(\@by,#3) \fi\fi \Curve(0)} % ------------------------------------------------------------------------- % This sets the points in euclidean (affine) coordinate space % ------------------------------------------------------------------------- \gdef\Euclid(#1,#2){% \ifcase\@cf\or \Dset(\@bx,#1)\Dset(\@by,#2)\or \Dset(\@cx,#1)\Dset(\@cy,#2)\or \Dset(\@dx,#1)\Dset(\@dy,#2)\or \Dset(\@ex,#1)\Dset(\@ey,#2)\or \Dset(\@fx,#1)\Dset(\@fy,#2)\or \Dset(\@gx,#1)\Dset(\@gy,#2)\or \Dset(\@hx,#1)\Dset(\@hy,#2)\fi} % ------------------------------------------------------------------------- % This is the general macro to draw rational bezier curves. It draws % bezier curves of degree 1..7. The degree depends on the number of % coordinates. If \@ce is zero, the curve is drawn, depending on the % counter \@ci. If \@ci is not zero, the coordinates are read until no % more open cordinates are found. \Rcurveto needs \Rmoveto in front to % draw from the current point. % \Rcurve(n)(x0,y0,z0)..., \Rcurveto(n)(x1,y1,z1)... % ------------------------------------------------------------------------- \gdef\Rcurve{\@cg=1\@ce=1\@ifnextchar ({\@Rdraw}{\@Rdraw(0)}} \gdef\Rcurveto{\@cg=1\@ce=0\@ifnextchar ({\@Rdraw}{\@Rdraw(0)}} \gdef\@Rdraw(#1){\@ifnextchar ({\@Rcoord(#1)}{% \@ci=0 \ifcase\@cf\or\@Acurve\or \@Bcurve\or\@Ccurve\or\@Dcurve\or \@Ecurve\or\@Fcurve\or\@Gcurve\fi}} \gdef\@Rcoord(#1)(#2,#3,#4){% \ifnum#1=0 \Add(\@cf,1) \Homogen(#2,#3,#4) \else \@cf=0 \@ca=#1 \@cb=\@ca \Add(\@cb,1) \ifnum\@ce=1 \Dset(\@ax,#2)\Dset(\@ay,#3)\Dset(\@az,#4) \Rmoveto(\Np\@ax,\Np\@ay,\Np\@az) \Dmul(\@ax,\@az)\Dmul(\@ay,\@az) \else \Add(\@cf,1) \@ax=\@xx \@ay=\@xy \@az=\@xz \Dmul(\@ax,\@az)\Dmul(\@ay,\@az) \Dset(\@bx,#2)\Dset(\@by,#3)\Dset(\@bz,#4) \Dmul(\@bx,\@bz)\Dmul(\@by,\@bz) \fi\fi \Rcurve(0)} % ------------------------------------------------------------------------- % For rational bezier curves, this adds a weight component to the points % and multiplies the components by the weights. Now, we can treat the % curve as integral bezier curve with 3 components (homogen coordinates) % px=px*w, py=py*w, pz=w. \Homogen(px,py,w) % ------------------------------------------------------------------------- \gdef\Homogen(#1,#2,#3){% \ifcase\@cf\or \Dset(\@bx,#1)\Dset(\@by,#2)\Dset(\@bz,#3)\Dmul(\@bx,\@bz)\Dmul(\@by,\@bz) \or \Dset(\@cx,#1)\Dset(\@cy,#2)\Dset(\@cz,#3)\Dmul(\@cx,\@cz)\Dmul(\@cy,\@cz) \or \Dset(\@dx,#1)\Dset(\@dy,#2)\Dset(\@dz,#3)\Dmul(\@dx,\@dz)\Dmul(\@dy,\@dz) \or \Dset(\@ex,#1)\Dset(\@ey,#2)\Dset(\@ez,#3)\Dmul(\@ex,\@ez)\Dmul(\@ey,\@ez) \or \Dset(\@fx,#1)\Dset(\@fy,#2)\Dset(\@fz,#3)\Dmul(\@fx,\@fz)\Dmul(\@fy,\@fz) \or \Dset(\@gx,#1)\Dset(\@gy,#2)\Dset(\@gz,#3)\Dmul(\@gx,\@gz)\Dmul(\@gy,\@gz) \or \Dset(\@hx,#1)\Dset(\@hy,#2)\Dset(\@hz,#3)\Dmul(\@hx,\@hz)\Dmul(\@hy,\@hz) \fi} % ------------------------------------------------------------------------- % For rational bezier curves, this projects homogeneous coordinates into % affine space by dividing each component through the interpolated weight % if pz=0 px=py=0 else px=px/pz, py=py/pz. \Affine % ------------------------------------------------------------------------- \gdef\Affine{% \ifdim\@zz=\z@ \Dset(\@zx,0) \Dset(\@zy,0) \else \Ddiv(\@zx,\@zz) \Ddiv(\@zy,\@zz)\fi} % ------------------------------------------------------------------------- % Linear interpolation between two coordinates. We have to take care, not % to change the contents of #1 and #2, because these are fixed bezier % coordinates. The interpolation value is returned in register #3. % b0=a0+i*(a1-a0)/n % ------------------------------------------------------------------------- \gdef\@One(#1,#2,#3){#3=#2 \Sub(#3,#1) \Mul(#3,\@ci) \Div(#3,\@ca) \Add(#3,#1)} % ------------------------------------------------------------------------- % Two degree interpolation between three coordinates. % c0=b0+i*(b1-b0)/n, c1=b1+i*(b2-b1)/n, c=c0+i*(c1-c0)/n % ------------------------------------------------------------------------- \gdef\@Two(#1,#2,#3,#4){% \@One(#1,#2,\@sx) \@One(#2,#3,\@sy) \@One(\@sx,\@sy,#4)} % ------------------------------------------------------------------------- % Three degree interpolation between four coordinates. % d0=c0+i*(c1-c0)/n, d1=c1+i*(c2-c1)/n, d=d0+i*(d1-d0)/n % ------------------------------------------------------------------------- \gdef\@Three(#1,#2,#3,#4,#5){% \@Two(#1,#2,#3,\@tx) \@Two(#2,#3,#4,\@ty) \@One(\@tx,\@ty,#5)} % ------------------------------------------------------------------------- % Four degree interpolation between five coordinates. % e0=d0+i*(d1-d0)/n, e1=d1+i*(d2-d1)/n, e=e0+i*(e1-e0)/n % ------------------------------------------------------------------------- \gdef\@Four(#1,#2,#3,#4,#5,#6){% \@Three(#1,#2,#3,#4,\@ux) \@Three(#2,#3,#4,#5,\@uy) \@One(\@ux,\@uy,#6)} % ------------------------------------------------------------------------- % Five degree interpolation between six coordinates. % f0=e0+i*(e1-e0)/n, f1=e1+i*(e2-e1)/n, f=f0+i*(f1-f0)/n % ------------------------------------------------------------------------- \gdef\@Five(#1,#2,#3,#4,#5,#6,#7){% \@Four(#1,#2,#3,#4,#5,\@vx) \@Four(#2,#3,#4,#5,#6,\@vy) \@One(\@vx,\@vy,#7)} % ------------------------------------------------------------------------- % Six degree interpolation between seven coordinates. % g0=f0+i*(f1-f0)/n, g1=f1+i*(f2-f1)/n, g=g0+i*(g1-g0)/n % ------------------------------------------------------------------------- \gdef\@Six(#1,#2,#3,#4,#5,#6,#7,#8){% \@Five(#1,#2,#3,#4,#5,#6,\@wx) \@Five(#2,#3,#4,#5,#6,#7,\@wy) \@One(\@wx,\@wy,#8)} % ------------------------------------------------------------------------- % Seven degree interpolation between eight coordinates. % h0=g0+i*(g1-g0)/n, h1=g1+i*(g2-g1)/n, h=h0+i*(h1-h0)/n % ------------------------------------------------------------------------- \gdef\@Seven(#1,#2,#3,#4,#5,#6,#7,#8,#9){% \@Six(#1,#2,#3,#4,#5,#6,#7,\@yx) \@Six(#2,#3,#4,#5,#6,#7,#8,\@yy) \@One(\@yx,\@yy,#9)} % ------------------------------------------------------------------------- % Draws a one degree bezier curve (integral or rational). % ------------------------------------------------------------------------- \gdef\@Acurve{% \@whilenum{\@ci<\@cb}\do{% \@One(\@ax,\@bx,\@zx) \@One(\@ay,\@by,\@zy) \ifnum\@cg=1 \@One(\@az,\@bz,\@zz)\Affine\fi \Lineto(\Np\@zx,\Np\@zy) \Add(\@ci,1)}} % ------------------------------------------------------------------------- % Draws a two degree bezier curve (integral or rational). % ------------------------------------------------------------------------- \gdef\@Bcurve{% \@whilenum{\@ci<\@cb}\do{% \@Two(\@ax,\@bx,\@cx,\@zx) \@Two(\@ay,\@by,\@cy,\@zy) \ifnum\@cg=1 \@Two(\@az,\@bz,\@cz,\@zz)\Affine\fi \Lineto(\Np\@zx,\Np\@zy) \Add(\@ci,1)}} % ------------------------------------------------------------------------- % Draws a three degree bezier curve (integral or rational). % ------------------------------------------------------------------------- \gdef\@Ccurve{% \@whilenum{\@ci<\@cb}\do{% \@Three(\@ax,\@bx,\@cx,\@dx,\@zx) \@Three(\@ay,\@by,\@cy,\@dy,\@zy) \ifnum\@cg=1 \@Three(\@az,\@bz,\@cz,\@dz,\@zz)\Affine\fi \Lineto(\Np\@zx,\Np\@zy) \Add(\@ci,1)}} % ------------------------------------------------------------------------- % Draws a four degree bezier curve (integral or rational). % ------------------------------------------------------------------------- \gdef\@Dcurve{% \@whilenum{\@ci<\@cb}\do{% \@Four(\@ax,\@bx,\@cx,\@dx,\@ex,\@zx) \@Four(\@ay,\@by,\@cy,\@dy,\@ey,\@zy) \ifnum\@cg=1 \@Four(\@az,\@bz,\@cz,\@dz,\@ez,\@zz)\Affine\fi \Lineto(\Np\@zx,\Np\@zy) \Add(\@ci,1)}} % ------------------------------------------------------------------------- % Draws a five degree bezier curve (integral or rational). % ------------------------------------------------------------------------- \gdef\@Ecurve{% \@whilenum{\@ci<\@cb}\do{% \@Five(\@ax,\@bx,\@cx,\@dx,\@ex,\@fx,\@zx) \@Five(\@ay,\@by,\@cy,\@dy,\@ey,\@fy,\@zy) \ifnum\@cg=1 \@Five(\@az,\@bz,\@cz,\@dz,\@ez,\@fz,\@zz)\Affine\fi \Lineto(\Np\@zx,\Np\@zy) \Add(\@ci,1)}} % ------------------------------------------------------------------------- % Draws a six degree bezier curve (integral or rational). % ------------------------------------------------------------------------- \gdef\@Fcurve{% \@whilenum{\@ci<\@cb}\do{% \@Six(\@ax,\@bx,\@cx,\@dx,\@ex,\@fx,\@gx,\@zx) \@Six(\@ay,\@by,\@cy,\@dy,\@ey,\@fy,\@gy,\@zy) \ifnum\@cg=1 \@Six(\@az,\@bz,\@cz,\@dz,\@ez,\@fz,\@gz,\@zz)\Affine\fi \Lineto(\Np\@zx,\Np\@zy) \Add(\@ci,1)}} % ------------------------------------------------------------------------- % Draws a seven degree bezier curve (integral or rational). % ------------------------------------------------------------------------- \gdef\@Gcurve{% \@whilenum{\@ci<\@cb}\do{% \@Seven(\@ax,\@bx,\@cx,\@dx,\@ex,\@fx,\@gx,\@hx,\@zx) \@Seven(\@ay,\@by,\@cy,\@dy,\@ey,\@fy,\@gy,\@hy,\@zy) \ifnum\@cg=1 \@Seven(\@az,\@bz,\@cz,\@dz,\@ez,\@fz,\@gz,\@hz,\@zz)\Affine\fi \Lineto(\Np\@zx,\Np\@zy) \Add(\@ci,1)}} % ------------------------------------------------------------------------- \endinput %% End of file `lapdf.sty'.