| java.lang.Object org.openlaszlo.iv.flash.util.GeomHelper
GeomHelper | public class GeomHelper (Code) | | Geometric helper: AffineTransform, Rectangle and related stuff.
author: Dmitry Skavish |
Method Summary | |
public static Point2D[] | CubicToQudratricBezier(Point2D p0, Point2D p1, Point2D p2, Point2D p3) Converts qubic bezier to quadratic one with some approximation
Used the following algorithm by Jens Alfke:
James Smith writes:
Can anyone show me a way to convert a Bezier cubic curve to a quadratic spline?
Is this a trivial conversion?
Can this conversion (if possible) be done to produce an identical curve from the Bezier to the spline?
The answer is it's not trivial, and it will necessarily be an approximation
(since you're going from 3rd order to 2nd order). | public static Rectangle2D | add(Rectangle2D dst, Rectangle2D src) | public static Rectangle2D | calcBounds(AffineTransform m, Rectangle2D src, Rectangle2D dst) | public static Rectangle2D | calcBounds(AffineTransform m, Rectangle2D src) | public static AffineTransform | concatenate(AffineTransform m1, AffineTransform m2) | public static Point2D | cubicBezier(Point2D p0, Point2D p1, Point2D p2, Point2D p3, double t) | public static AffineTransform | deRotateMatrix(AffineTransform m) | public static AffineTransform | deScaleMatrix(AffineTransform m) | public static double | getDist(Rectangle2D r) | public static double | getDist(double[] r) | public static double | getDist(double[] r, int offset) | public static Point2D | getIntersectionPoint(Point2D a0, Point2D a1, Point2D b0, Point2D b1) | public static double[] | getMatrixScale(AffineTransform m) | public static int | getSize(Rectangle2D r) | public static Rectangle2D | getTransformedSize(AffineTransform m, Rectangle2D r) Transforms specified rect using specified matrix and
returns rectangle which has width and height as of transformed one. | public static Rectangle2D | newRectangle() | public static Rectangle2D | newRectangle(int x, int y, int w, int h) | public static Rectangle2D | newRectangle(double x, double y, double w, double h) | public static Point2D | quadraticBezier(Point2D p0, Point2D p1, Point2D p2, double t) |
CubicToQudratricBezier | public static Point2D[] CubicToQudratricBezier(Point2D p0, Point2D p1, Point2D p2, Point2D p3)(Code) | | Converts qubic bezier to quadratic one with some approximation
Used the following algorithm by Jens Alfke:
James Smith writes:
Can anyone show me a way to convert a Bezier cubic curve to a quadratic spline?
Is this a trivial conversion?
Can this conversion (if possible) be done to produce an identical curve from the Bezier to the spline?
The answer is it's not trivial, and it will necessarily be an approximation
(since you're going from 3rd order to 2nd order). The usual technique is recursive subdivision:
- Create a quadric that tries to approximate your cubic.
- Apply some metric to see how close an approximation it is.
- If it's not close enough, break the cubic in half at the midpoint and recurse on each half.
Call the Bezier curve ABCD, where A and D are the endpoints and B and C the control points.
For step (1) I found the intersection of AB and CD (call it E) and used AED as the quadric.
This is about your only option because the curve at A has to be parallel to AE, and at D has
to be parallel to ED. In step (2), I used as my metric the distance from the midpoint of the
quadric to the midpoint of the Bezier. The midpoint of the quadric is, if I remember correctly,
halfway between the midpoint of AE and the midpoint of ED. The midpoint of the Bezier involves
computing a few more midpoints; it's a standard construction that you should be able to find in a text.
This worked well enough but tended to produce more quadrics than was optimal. (In general there
were 2-3 times as many quadrics as Beziers. But the quadrics are faster to render, so it balances out.)
I know some people at Apple with more mathematical savvy than I have had worked on this a bit and
had interesting techniques where they didn't always break the Bezier in the middle, and were sometimes
able to merge pieces of adjacent Beziers into the same quadrics. This produced much more efficient
results. To my knowlege their results haven't been published anywhere; but they probably ought to be
now that the ship of QuickDraw GX is imminent. (If you have GX, you might look at the "cubic library",
which apparently does some or all of this stuff. It does describe cubics in quadric form, but I'm not
sure it does all the optimizations I've described in this paragraph...)
Parameters: p0 - 1-st control point of cubic bezier Parameters: p1 - 2-st control point of cubic bezier Parameters: p2 - 3-st control point of cubic bezier Parameters: p3 - 4-st control point of cubic bezier array of qudratic bezier. each curve consists of three control points (Point2D) |
add | public static Rectangle2D add(Rectangle2D dst, Rectangle2D src)(Code) | | Adds one specified rectangle to another
Parameters: dst - destination rectangle (can be null) Parameters: src - rectangle which is going to be added to destination one (can be null) destination rectangle |
calcBounds | public static Rectangle2D calcBounds(AffineTransform m, Rectangle2D src, Rectangle2D dst)(Code) | | Transforms specified rectangle and return its bounds
Parameters: m - matrix which is used to transform the rectangle Parameters: src - rectangle which is transformed Parameters: dst - destination rectangle which is used to hold the bounds destination rectangle |
calcBounds | public static Rectangle2D calcBounds(AffineTransform m, Rectangle2D src)(Code) | | Transforms specified rectangle and return its bounds
Parameters: m - matrix which is used to transform the rectangle Parameters: src - rectangle which is transformed new rectangle which is used to hold the bounds |
cubicBezier | public static Point2D cubicBezier(Point2D p0, Point2D p1, Point2D p2, Point2D p3, double t)(Code) | | Cubic Bezier interpolation
B(t) = P0*(1-t)^3 + P1*3*t*(1-t)^2 + P2*3*t^2*(1-t) + P3*t^3
Parameters: p0 - first control point Parameters: p1 - second control point Parameters: p2 - third control point Parameters: p3 - fourth control point Parameters: t - parameter from 0 to 1 point on the curve corresponding given parameter |
deRotateMatrix | public static AffineTransform deRotateMatrix(AffineTransform m)(Code) | | Discard 'rotate' of the matrix
retrieve scale and transform of the matrix and create new one from them
Parameters: m - matrix to discard rotate from, this matrix is modified same matrix but without rotate |
deScaleMatrix | public static AffineTransform deScaleMatrix(AffineTransform m)(Code) | | Discard 'scale' of the matrix
retrieve scale of the matrix and create new one which is descale
of the first and then multiply them in right order
Parameters: m - matrix to discard scale from, this matrix is modified same matrix but scale is 1 |
getDist | public static double getDist(Rectangle2D r)(Code) | | Return distance between two points defined by the Rect
Parameters: r - rectangle which defines two points distance |
getDist | public static double getDist(double[] r)(Code) | | Return distance between two points defined by array
Parameters: r - 4 elements array which hold the points (x0,y0), (x1,y1) distance between two points |
getDist | public static double getDist(double[] r, int offset)(Code) | | Return distance between two points defined by array
Parameters: r - array which hold the points (x0,y0), (x1,y1) Parameters: offset - offset in the array distance between two points |
getIntersectionPoint | public static Point2D getIntersectionPoint(Point2D a0, Point2D a1, Point2D b0, Point2D b1)(Code) | | Computes intersection of two lines
Each line is specified by two points
Parameters: a0 - first point of line A Parameters: a1 - second point of line A Parameters: b0 - first point of line B Parameters: b1 - second point of line B intersection point |
getMatrixScale | public static double[] getMatrixScale(AffineTransform m)(Code) | | Get values inverse to 'scale' of the matrix
retrieve inverse scale of the matrix
Parameters: m - matrix to get inverse scale from array of x and y descale |
getSize | public static int getSize(Rectangle2D r)(Code) | | Returns size of specified rectangle as if it were written to swf file
Parameters: r - specified rectangle size of rectangle in bytes |
getTransformedSize | public static Rectangle2D getTransformedSize(AffineTransform m, Rectangle2D r)(Code) | | Transforms specified rect using specified matrix and
returns rectangle which has width and height as of transformed one.
Parameters: m - specified matrix Parameters: r - specified rectangle rectangle which has width and height as of transformed one. |
newRectangle | public static Rectangle2D newRectangle()(Code) | | Creates new rectangle
empty rectangle (everything zero) |
newRectangle | public static Rectangle2D newRectangle(int x, int y, int w, int h)(Code) | | Creates new rectangle
Parameters: x - x coordinate Parameters: y - y coordinate Parameters: w - width of the rectangle Parameters: h - height of the rectangle new rectangle |
newRectangle | public static Rectangle2D newRectangle(double x, double y, double w, double h)(Code) | | Creates new rectangle
Parameters: x - x coordinate Parameters: y - y coordinate Parameters: w - width of the rectangle Parameters: h - height of the rectangle new rectangle |
quadraticBezier | public static Point2D quadraticBezier(Point2D p0, Point2D p1, Point2D p2, double t)(Code) | | Quadratic Bezier interpolation
B(t) = P0*(1-t)^2 + P1*2*t*(1-t) + P2*t^2
Parameters: p0 - first control point (anchor) Parameters: p1 - second control point (control) Parameters: p2 - third control point (anchor) Parameters: t - parameter from 0 to 1 point on the curve corresponding given parameter |
|
|