Re: [css-masking] 'mask' with resource and image references (was: [css4-images] support for SVG Paint Servers without element())

On Nov 7, 2012, at 2:16 PM, Tab Atkins Jr. <jackalmage@gmail.com> wrote:

> On Wed, Nov 7, 2012 at 1:43 PM, Dirk Schulze <dschulze@adobe.com> wrote:
>> On Nov 7, 2012, at 1:32 PM, Tab Atkins Jr. <jackalmage@gmail.com> wrote:
>>> On Wed, Nov 7, 2012 at 1:26 PM, Dirk Schulze <dschulze@adobe.com> wrote:
>>>> On Nov 7, 2012, at 1:08 PM, Tab Atkins Jr. <jackalmage@gmail.com> wrote:
>>>>> On Wed, Nov 7, 2012 at 12:45 PM, Dirk Schulze <dschulze@adobe.com> wrote:
>>>>>> On Nov 7, 2012, at 10:43 AM, Tab Atkins Jr. <jackalmage@gmail.com> wrote:
>>>>>>> So, 'mask-image' needs to have its grammar revised to take this into
>>>>>>> account, so that it can take mask references as well.
>>>>>> 
>>>>>> This would be the consequence, but wouldn't help IMO.
>>>>>> 
>>>>>> mask-image: url(image#frag);
>>>>>> 
>>>>>> It would be unclear until the processing, if this is an SVG resource or an image. However, the syntax would be valid in both cases. The problem for WebKit is, that we already assume that this will be an CSS Image and already start creating an CSSImage resource. This is incompatible with an SVG resource (because of various reasons roc already mentioned). That's why this is not an option for WebKit right now.
>>>>> 
>>>>> Let's be precise here.  It's unclear at parse time whether you're
>>>>> pointing at a <mask> element or some other paint server element like
>>>>> <linearGradient>.
>>>> 
>>>> I think you mix up some things. I am not talking about paint servers at all. I am just talking about the <mask> element for reference.
>>> 
>>> ...I know?  My point is that url(image#frag) might also point at a
>>> paint server, which is an <image>.  But it won't ever be interpreted
>>> as an image file, like an SVG Stack.
>> 
>> Well, for 'mask' I would follow CSS4 Images. If you want to use paint servers, use element().
> 
> Okay, I am very confused.  I don't know if you misunderstand the rule
> we've come up with, or would like an exception for this property, or
> what.
> 
> I'll lay out my understanding as simply as possible, and you can tell
> me what you disagree with.
> 
> If you see "mask: url(...);", there are a priori three possiblities:
> 
> 1. The url might be intending to point to an SVG <mask> element in the
> indicated file.
> 2. The url might be intending to point to an SVG paint server element
> in the indicated file.
> 3. The url might be intending to use the indicated file as an image.
> 
> 1 needs to be distinguished from 2&3, because we treat <mask> and
> <image> values differently.  If we want to have different syntax for
> <mask> and for <image>, we need to distinguish them at parse time.  If
> we're cool with keeping the same syntax (but possibly ignoring things
> that are misplaced, like how 'transition-propery' ignores unknown
> properties), we can do this distinguishing late, after having parsed
> the file and figured out which one it is.  (Because it relies on a url
> resolving, we shouldn't distinguish the cases until used-value time.
> Computed values aren't supposed to depend on url resolution.)
> 
> 1&2 need to be distinguished from 3, because loading an SVG file as an
> image and loading it as an external resource go down very different
> code paths in major browsers, and the decision about which code path
> to take should be done as early as possible, ideally at parse time.
> 
> Roc's original proposal mutated into a simplified proposal given by
> Steve Zilles and fantasai, where we can tell at parse time whether to
> attempt to load a file as an image or as an external resource based on
> the presence/absence of a hash.  For most properties that can take
> url() <image>, url() is always loaded as an image file, regardless.
> For a handful of SVG properties, if the url has a hash, it'll be
> loaded as an external resource; otherwise, loaded as an image.

Looks like a good summary of the discussion on the other threat. I agree with it. As a note: there are SVG fragments which still imply an image. #viewbox is one of them.

> 
> 'mask-image' is in that latter set.  So, when you encounter
> "mask-image: url(image#frag);", we can tell at parse time that we
> should load "image#frag" as an external resource, rather than as an
> image.  This happens *regardless of the file's eventual type" - if it
> ends up being a PNG (which can't provide an external resource), then
> too bad, it's just an invalid reference.

This is a very specific detail. In WebKit does not care about the fragment at all for CSS Image values (one reason WebKit does not support Media Fragments on CSS Images yet IIRC).
Just from the name of the property, WebKit decides to treat a URL as CSS Image or a resource (like <mask>). This is the case for every single property and works very well so far. 'background', 'border' would always be CSS Images (independent of the fragment), which fulfills the agreement. 'fill', 'stroke' and 'clip-path' treat URL as resource, always (independent of the fragment). This fulfills the agreement as well. 
Since 'mask-image' uses the exactly same parsing step as 'background-image', URLs are treated as CSS Images, always. This is why 'mask-image' would be special. The same problem could occur on 'fill' and 'stroke' if SVG2 fully supports CSS image values for these properties.

> 
> 
>>>>> You *do* know, at parse time, that it won't be
>>>>> loading the SVG as an image, because 'mask' is on the list of
>>>>> properties that default frag-urls to being a resource reference rather
>>>>> than an image.
>>>> 
>>>> You do not know that it actually is an SVG file at all. This is what I described in a previous mail:
>>> 
>>> That doesn't matter.  The rule that we're switching to says that, *at
>>> parse time*, a value like "url(image#frag)" will be an external
>>> resource reference, *not* an image file.  You don't need to know what
>>> type of file it is to make this distinction.  It just tells you which
>>> code path to go down.
>> 
>> This would be a mayor difference to current behavior. See below.
> 
> Only theoretically, so far.  *If* people are commonly writing
> -webkit-mask-image with SVG Stacks, or PNGs with useless fragments,
> then it's a problem, because the behavior I outlined above would be a
> change (and would make the mask stop working).
> 
> However, I doubt both of those.  We apparently have decent evidence
> that most usage of SVG Stacks is in HTML (<img>, <iframe>, etc.), not
> CSS, so heavy use of them in -webkit-mask-image seems unlikely.  I
> also doubt that useless fragments are commonly used on bitmap images,
> in any property, so that shouldn't be much of a problem either.
> 
> Given this, it should be okay to make this minor behavior change.

I agree that the fragment is useless on PNGs or any other rasterized image with the exception of Media Fragments. But at least the behavior is consistent across all browsers. It feels bogus to specify something that runs against all implementations.

Greetings,
Dirk

> 
> 
>>>> ""
>>>> And even the fragment itself is not a good identifier, url(image.png#frag) will be an image as well. And the file ending itself can not be trusted. The file doesn't need to have a file ending at all. Therefore, the fragment alone can not be used to clarify if it is a resource or an image. That is what I meant in the mail before. The CSS Parser would need extra information about the file then just the URL.
>>>> ""
>>>> 
>>>> You would need to check the URL itself (e.g check mime type) and can't just rely on the parsing output. That is actually my point.
>>> 
>>> No, not according to the rule we've come up with.  You can tell,
>>> before you attempt to load the url, that it will be a resource
>>> reference of some kind, not an image.
>>> 
>>> The resource might end up being a CSS <image> type (if you're pointing
>>> at a paint server), but that's a different story.
>> 
>> This has nothing to do with the rule we come up. "image.png", "image.png#frag" and even "image#frag" can be PNG images, in which case the fragment doesn't matter at all. You can't make decisions depending on fragments on these files. These are no "resources" in the sense of SVG. These are images where CORS doesn't apply. You can not just say that they are resources now if they have fragments and stop displaying images. As roc said, if Gecko treats something as resource, it doesn't download it at all. Currently Gecko does for images.
> 
> As I have described above, that's fine.  This is only a problem if
> there are large numbers of stylesheets writing things like
> "-webkit-mask-image: url(foo.png#uselesshash);", which I doubt.
> Assuming that it's okay to break whatever tiny fraction of people
> might be doing this, then the effect of that code, once we define
> everything properly, will just be an invalid reference.  The 'mask'
> property will by syntactically valid, but won't do anything because it
> couldn't resolve the file as an external resource, same as if you
> write "background-image: url(foo.html);".
> 
> ~TJ

Received on Wednesday, 7 November 2012 22:53:12 UTC