使用任意函数(贝塞尔、圆弧等除外)创建形状的矢量图形

使用任意函数(贝塞尔、圆弧等除外)创建形状的矢量图形

是否可以使用乳胶或外部程序创建矢量图形,允许使用或多或少任意函数(除贝塞尔曲线和圆形等标准形状外)来定义形状?

例如,实际上可以使用函数 Y=sin(1/x),而不必使用具有有限步长的分段线性函数。当然,必须评估函数才能在屏幕/打印机上显示,但随后可以根据给定的分辨率调整步长。

如果不可能,那么 PDF/PostScript 规范中是否存在限制阻止了它,或者为什么这是不可能的?

答案1

你可以改变许多通过使用导数计算内部控制点(表示曲线在端点的切向量),将函数转化为分段贝塞尔近似。

Bill Casselmann 的一篇非常好的文章数学插图,第 6 章曲线和第 7 章自动绘制曲线,我将在进一步介绍之前重新阅读这些内容。但实际上,任何实现贝塞尔曲线的系统都可以通过采样和插值来近似其他函数。

下面是一个后记例子。有时需要发明一种对 x/0 的解释,以便使用 进行计算/div{dup 0 eq{pop pop 100000}{div}ifelse}bind def编辑:修改为显示每条曲线的端点。

N=10:
sin(1/x),n=10,带点

数量=100:
sin(1/x),n=100,带点

%!

/circ { % draw a circle at current point, radius: 3*linewidth
    gsave
        currentpoint newpath % cx cy
        currentlinewidth 3 mul % cx cy r
        0 360 % cx cy r ang^ ang$
        arc fill %draw and fill the circle
    grestore
} def

% x0 x1 N  sin1x  -
% approximate sin(1/x) in N segments with piecewise Bezier curves
% N: number of segments,
% x0,x1: endpoints (x- ordinates)
%
/sin1x { 16 dict begin
    {N x1 x0}{exch def}forall   %give names to the arguments
    /f { 1 exch div sin } def   %f(x) = sin(1/x)
    /f' { 1 exch div cos } def  %f'(x) = cos(1/x)
    /h x1 x0 sub N div def      %dx 
    /x x0 def                   %x = x0
    /y x f def                  %y = f(x)
    /s x f' def                 %s = f'(x)
    x y moveto               %place initial point at x0,f(x0)
    N {                         %repeat N times ...
        circ                    %draw circle to show endpoint
        x h 3 div add
        y h 3 div s mul add  % x+(dx/3) y+(dx/3)*s           ctrl pt 1
        /x x h add def          %x = x + dx
        /y x f def              %y = f(x)
        /s x f' def             %s = f'(x)
        x h 3 div sub
        y h 3 div s mul sub  % x+dx-(dx/3) f(x+dx)-(dx/3)*s  ctrl pt 2
        x y                  % x+dx f(x+dx)                  end pt
        curveto                 %draw curve segment, end pt becomes start of next seg
    } repeat
} def

% translate origin to roughly the center of US letter paper
300 400 translate

% scale by 200, but reduce linewidth by same proportion
% ie. scale the *drawing*, not the *image*
1 200 dup dup scale 
div currentlinewidth mul setlinewidth

%x0 x1 N 
-1 1 100 sin1x stroke
showpage

相关内容