w3c / svgwg

SVG Working Group specifications
Other
710 stars 133 forks source link

Enhance `<pattern>` to support auto-width or auto-height for pattern tiles with a `viewBox` #342

Open BigBadaboom opened 7 years ago

BigBadaboom commented 7 years ago

Some useful features of CSS background, cannot be reproduced well, or at all, with SVG patterns.

For example this configuration:

background-image: url(/* URL */); 
background-position: 50%;
background-size: auto 100%;
background-repeat: repeat-x;

from this Stack Overflow question

That particular problem could, I think, be solved by changing it so that that unspecified widths and heights should be treated as they are in <svg> if there is a viewBox.

<pattern id="p1" height="1" viewBox="0 0 1 1"
         overflow="visible">
  <image xlink:href="https://static.jsbin.com/images/dave.min.svg"
         width="1" height="1" />
</pattern>

...along with the overflow change requested in bug #129.

This is just an example, but it would be good to go through the background style attributes (background-size, background-repeat etc) and find ways that we can enhance patterns to support all those features.

I could come up with some more concrete proposals if there is some enthusiam for this idea.

AmeliaBR commented 7 years ago

"All features" is pretty broad, so I'm changing this to focus on the particular issue you describe: auto-sizing the pattern tile to match the aspect ratio. Feel free to open separate issues for other missing features.

I think this is useful and probably a reasonable change.

By combining most width and height attributes with the CSS properties of the same name, SVG 2 adds an auto as the default. In most cases, auto is defined to behave the same as the SVG 1.1 default.

However, for <image>, auto is defined to match the normal CSS behavior: auto-size based on aspect ratio or intrinsic size. Although this is technically a "breaking change", it was accepted because it only breaks things that were already broken. In SVG 1.1, if you didn't specify both height and width for an <image>, the image wouldn't be rendered. Now (in browsers that have updated), it is rendered with automatic sizing.

The width and height attributes on <pattern> aren't currently defined as mapping to the CSS properties. However, the arguments for <image> apply equally to <pattern>: currently, if you omit either width or height, the pattern is in error and won't be used. So if we give the attributes a new auto default, we're not breaking anything that isn't already broken.

But there are complications...

First, we then need to define what the auto behavior is in all cases:

And that gets us to the other complication: object bounding-box units are applied as a non-uniform scale. Within that scaled coordinate system, the bounding box is treated as if it always has a 1:1 aspect ratio. The result is then stretched to fit the actual bounding box. So if you're auto-sizing content within an object bounding-box context (aka, the default patternUnits value), it's not going to have the affect you want. We'd need to significantly re-write how bounding box units are interpretted to make it useful.

By the way, for the specific case of using an <image> as a pattern fill, the Fill and Stroke Module has a better solution: skip the pattern, and just reference the image file directly, with CSS-background-inspired sizing properties. But there would still be a use case for aspect-ratio sizing for normal SVG patterns.

fsoder commented 7 years ago

To keep with the "inspiration" (background-*), I guess the default object size would be an analog of the positioning area? To tie in with the Fill and Stroke spec, presumably fill-box and similar would be used to change what area to use. Whether that would apply for both unit types though...

boggydigital commented 6 years ago

Not blocking updated 2.0 CR publication - assigning 2.1 WD milestone