Bezier(n) 1.0 " Bezier "

Name

Bezier - Create and manipulate Bezier curvers.

Table Of Contents

Synopsis

Description

INTRODUCTION

This package provides methods for manipulating Bezier's curves (see Wikipedia for a thorough introduction)

A Bezier curve is represented by an Itcl object and manipulated by various methods. Other than basic methods for basic operations, you can find more elaborated methods for computing the curve lenght, the tangent and the normal vector, and for subdiving the curves in equally spaced segments.

With this package you can represent curves in a n-dimensional space (with optimized code for handling 1D and 2D curves).

COMMANDS

Given a list of control-points (each control-point represented as lists of real-numbers), the ::Bezier::new command returns the (fully qualified) name of a new object representing a Bezier curve. Object is created in the caller's namespace

The Bezier::new command accepts both a list-of-points as well as a sequence-of-points

Bezier::new point ?point ...?

as well as

Bezier::new {point ?point ...?}

All points must have the same dimension.

The following example

set bzObj1 [Bezier::new {0.0 0.0} {0.5 0.7} {2.5 3.6}]

creates a curve made of three 2D control-points.

Note that

set bzObj1 [Bezier::new {1.0 2.0 3.0}]

is a (degenerated) curve made of one 3D key-point {1.0 2.0 3.0}, whilst

set bzObj1 [Bezier::new 1.0 2.0 3.0]

is a curve made of three 1D control-points {1.0} {2.0} {3.0}

METHODS

The following commands are possible for a Bezier-object:

bzObj destroy

destroys the object, including its storage space and associated command.

bzObj spaceDim

returns the dimension of each control-points of the curve (all points in a given curve MUST have the same dimension)

bzObj degree

returns the the curve degree (i.e. the number of control-points less one). Often referred as ?curve's order?

bzObj points

returns the list of control-points

bzObj PZero

returns The Point-Zero (as a list of real numbers) with dimension equal to the curve dimension. e.g if bZobj is a curve of 3D points, [bzObj PZero] returns {0.0 0.0 0.0}

bzObj point i

returns the i-th control-point

bzObj point i point

replaces the i-th control-point with the new point.

Note that you can also use expressions like "end" "end-1" as indexes If i is out of range or new point's dimension is different from the dimension of the other points of the curve, then an error is raised.

bzObj clone

creates a new clone of this curve. The new curve is created in the caller's namespace. It's caller responsability to delete it after use.

bzObj polylength

returns the length of the control-polygon

bzObj baselength

returns the distance between the first and the last control-point

bzObj at t

evaluates B(t) (0.0<=t<=1.0)

B(t) is the parametric form of the Bezier's curve

bzObj derivative

returns a new Bezier's curve of degree n-1. Derivative of a degenerate 0-degree curve is still a 0-degree curve

NOTE: it's caller responsability to delete it after use

bzObj tangent_at t

returns the (normalized) tangent-vector at B(t) (0.0<=t<=1.0)

NOTE: degree-0 curves have no tangent (nor normal); in such cases an arbitrary normalized vector is returned.

bzObj vtangent_at len t

returns a segment (a list of two points) whose length is len, with origin in [bzObj at t] and the same direction of [bzObj tangent_at t].

Difference between tangent_at and vtangent_at:

 set bObj [Bezier::new {1 1} {2 2} {3 1}]
 set tg [$bObj tangent_at 0.5]
 # tg is  the vector {1.0 0.0}
 set vtg [$bObj vtangent_at 2 0.5]
 # vtg is the segment {{2.0 1.5} {4.0 1.5}}  i.e. a segment with origin in {2.0 1.5}, length 2 and direction {1.0 0.0}
bzObj normal_at t

returns the normal-vector at B(t) (0.0<=t<=1.0).

NOTE: meaningful only for 2D curves; in other cases it returns Point-Zero.

bzObj vnormal_at len t

returns a segment (a list of two points) whose length is len, with origin in [bzObj at t] and the same direction of [bzObj normal_at t].

NOTE: meaningful only for 2D curves; in other cases result is Point-Zero.

bzObj split_at t

splits the curve at B(t) (0.0<=t<=1.0) and returns 2 new curves (a list with 2 curves).

It's caller's responsability to delete these 2 curves after use.

NOTE: Algorhythm adapted from Earl Boeber's work: "Computing the arc length of cubic bezier curves"

bzObj length

returns the approximated length of the curve, accordling to the algorhythm by J.Gravesen. Approximation is controlled by the flatnesstolerance parameter (see below)

WARNING: this is a time-consuming computation; your app should cache the result.

bzObj flatnesstolerance
bzObj flatnesstolerance val

gets/sets the flatness tolerance:

if val is positive, it is used as an absolute tolerance, if val is negative, tolerance is related to the polylength, i.e the tolerance is P*abs(flatnesstolerance) where P is polylength

Flatness tolerance cannot be 0.0; it must be > 1e-9

bzObj length_at t

returns the approximated length of the curve from B(0) to B(t) (0.0<=t<=1.0).

If t < 0.0 then [bzObj length_at t] == [bzObj length_at 0.0] == 0.0.

If t > 1.0 then [bzObj length_at t] == is [bzObj length_at 1.0] == [bzObj length].

Properties:
-----------
  [$bzObj length_at 0.0] == 0.0
  [$bzObj length_at 1.0] == [$bzObj length]
  [$bzObj length_at $t0] < [$bzObj length_at $t1]   <==>   $t0 < $t1 
bzObj invlength len

is the inverse of [bzObj length_at t]. Given a len, returns a value t such that [bzObj length_at t] == len.

Properties:
-----------
  [$bzObj length_at [$bzObj invlength [arg len]]] == [arg len]
  [$bzObj invlength [$bzObj length_at [arg t]]] == [arg t]
  [$bzObj invlength 0.0] == 0.0
  [$bzObj invlength [$obj length]] == 1.0
  [$bzObj invlength [arg $len0]] < [$bzObj invlength [arg $len1]]  <==> [arg len0] < [arg len1]
 Degenerated cases:
   If [arg len] < 0  ==>  [$bzObj invlength [arg $len]] == 0.0
   If [arg len] > [$bzObj length]  ==>  [$bzObj invlength [arg $len]] == 1.0
bzObj t_splitUniform dl ?pLen?

] returns a list of t (t is parameter of curve B(t)) subdividing the curve in subcurves of length dL. Optional arameter plen (default is 0.0) is the length of the initial part of the curve to be skipped before the subdivision.

Note that after the subdivision there may remain the last part of the curve, whose length is less than dL. You can get the length of the last part by calling the splitLeftOver method.

Once you get a list of t, then you can get a list of equally spaced points, tangents, normals, by simply calling at, tangent_at, normal_at methods.

bzObj t_splitLeftOver

returns the length of the last part of the curve subdivision after calling the t_splitUniform method.

LIMITATIONS

BUGS, IDEAS, FEEDBACK

See Also

BContour

Keywords

Itcl, math

Category

math