% hodgman-sutherland.inc % * evaluate2d % * evaluate3d % * hodgman-sutherland % x y ... [A B C ... ] = f => Ax + By + ... /evaluate2d { aload pop % x y A B C 5 1 roll % C x y A B 3 2 roll % C x A B y mul % C x A By 3 1 roll % C By x A mul % C By Ax add add } def /evaluate3d { aload pop % x y z A B C D 7 1 roll % D x y z A B C 4 3 roll % D x y A B C z mul % D x y A B Cz 5 1 roll % D Cz x y A B 3 2 roll % D Cz x A B y mul % D Cz x A By 3 1 roll % D Cz By x A mul % D Cz By Ax add add add } def % polygon + affine function f => truncated polygon where f <= 0 /hodgman-sutherland { 8 dict begin /f exch def /p exch def /n p length def f length 3 eq { /evaluate /evaluate2d load def }{ /evaluate /evaluate3d load def } ifelse % P = p[n-1] to start /P p n 1 sub get def /d P length 1 sub def /fP P aload pop f evaluate def [ p { /Q exch def /fQ Q aload pop f evaluate def fP 0 le { fQ 0 le { % P & Q both in % (-, -) == Q }{ % P in, Q out: put R on stack % (-, +) == fP 0 lt { /QP fQ fP sub def [ 0 1 d { /i exch def fQ P i get mul fP Q i get mul sub QP div } for ] } if } ifelse }{ fQ 0 le { % P out, Q in: if fQ< 0 put R Q, otherwise put Q % (+, -) == fQ 0 lt { /QP fQ fP sub def [ 0 1 d { /i exch def fQ P i get mul fP Q i get mul sub QP div } for ] } if Q }{ % else both out % (+, +) == } ifelse } ifelse /P Q def /fP fQ def } forall ] end } def