openfl / svg

Provides SVG parsing and rendering for OpenFL and Haxe
MIT License
68 stars 30 forks source link

Parent/child object composition, properties, transforms, alpha, etc #38

Open jcward opened 8 years ago

jcward commented 8 years ago

There are fairly significant problems with parent/child element containment and the inheritance of properties, as illustrated by this example:

<svg id="svg1" viewBox="0 0 256 256" xmlns="http://www.w3.org/2000/svg" width="256" height="256">
  <rect width="256" height="256" style="fill:#FFF" />
  <rect x="10" y="10" width="236" height="40" style="fill:#f00;stroke:#000;stroke-width:20;" opacity="0.5"/>
  <g opacity="0.5" stroke="#000" stroke-width="14" transform="scale(0.33 1)">
    <circle cx="80" cy="150" r="60" fill="#f00"/>
    <circle cx="130" cy="150" r="60" fill="#aa0"/>
    <circle cx="180" cy="150" r="60" fill="#0f0"/>
    <circle cx="230" cy="150" r="60" fill="#0aa"/>
    <circle cx="280" cy="150" r="60" fill="#00f"/>
    <circle cx="330" cy="150" r="60" fill="#a0a"/>
    <rect x="50" y="160" width="300" height="80" fill="#ff4" stroke="#552" opacity="0.5"/>
  </g>
</svg>

Here's the rendering in OpenFL vs eog/gimp/etc: image

As you can see:

  1. In the top box, the opacity should apply to the object as a whole, but it's being applied separately to the stroke and fill. So you can see the overlap between the stroke and fill.
  2. With the set of circles in a group:

    a. again the alpha should be applied to the whole group b. the scaling isn't being applied properly (different x / y scaling) c. the stroke properties should be inherited (issue #32) except where overridden (rectangle)

I haven't looked into the architecture of how SVGs are rendered onto Shapes, but I know in theory how ending fills (or composing Shapes/Sprites) might fix some of these issues.

It may be beyond me, but I'll have a quick look into these issues.

jcward commented 8 years ago

Yes, this will be an extremely difficult set of issues of solve. Specifically, for transforms or alpha on a group (even a rect with a stroke can be considered a group), it is not possible to apply the transform or alpha to the group without composing multiple Shapes / Sprites in a DisplayList. So that means the render(graphics) API cannot achieve proper SVG drawing.

But even if you were to compose a displaylist of Shapes / Sprites, and inherit the properties properly, and supported transforms, I recall that scaling up a Shape causes pixelization (as the Shape is rasterized at it's natural, untransformed size.)

jgranick commented 8 years ago

I think we could look at tossing the render(graphics) API and outputting a DisplayObject instead

As for quality, I think we discussed a solution that might be a suitable compromise between performance and quality, the key is just to get that implemented :wink: