Bad performance with Canvas and extensive clipping
Jim Graham
james.graham at oracle.com
Fri May 23 21:35:23 UTC 2014
Are you clipping to an arbitrary path in all cases or just a rectangle?
Unfortunately we only offer the arbitrary clip-to-current-path method
that isn't optimized for basic rectangular clipping and it implements
soft clipping.
There is an outstanding tweak that we added faster clipping support for
WebNode and we need to start using it for
Node.setClipNode(non-rectangle) and Canvas, but we haven't implemented
that yet. (https://javafx-jira.kenai.com/browse/RT-30107) It basically
is a direct "render this texture through that other texture as a clip"
operation instead of the current code that runs it through some Blend
effect filters. It would definitely improve your run times, but I'm not
sure how much.
Even more savings could be had for rectangular clips if we provided some
way to communicate them to the GC...
...jim
On 5/23/14 11:47 AM, Tom Schindl wrote:
> Hi,
>
> Maybe as some of you might know I've been working since sometime on SWT
> on JavaFX and to implement direct drawing operations we use JavaFX-Canvas.
>
> I've today tried to run a heavy direct drawing grid implementation and
> it performed very bad because it makes heavy use of clipping.
>
> For a grid I've counted ~1500 clipping operations the library works
> something like this:
>
> boolean activeClip;
> Canvas canvas = new Canvas();
>
> public void setClipping(PathIterator pathIterator) {
> GraphicsContext gc = canvas.getGraphicsContext2D();
> if(activeClip) {
> gc.restore();
> activeClip= false;
> }
>
> if( pathIterator == null ) {
> return;
> }
>
> activeClip = true;
> float coords[] = new float[6];
> gc.save();
> gc.beginPath();
>
> float x = 0;
> float y = 0;
>
>
> gc.moveTo(0, 0);
>
> while( ! pathIterator.isDone() ) {
> switch (pathIterator.currentSegment(coords)) {
> case PathIterator.SEG_CLOSE:
> gc.lineTo(x, y);
> break;
> case PathIterator.SEG_CUBICTO:
> gc.bezierCurveTo(coords[0], coords[1], coords[2], coords[3],
> coords[4], coords[5]);
> break;
> case PathIterator.SEG_LINETO:
> gc.lineTo(coords[0], coords[1]);
> break;
> case PathIterator.SEG_MOVETO:
> gc.moveTo(coords[0], coords[1]);
> x = coords[0];
> y = coords[1];
> break;
> case PathIterator.SEG_QUADTO:
> gc.quadraticCurveTo(coords[0], coords[1], coords[2], coords[3]);
> break;
> default:
> break;
> }
> pathIterator.next();
> }
>
> gc.clip();
> gc.closePath();
> }
>
> Am I doing something ultimately wrong, totally wrong? Has anyone an idea
> how I would work around the problem?
>
> Tom
>
More information about the openjfx-dev
mailing list