Re: Gradient syntax proposal

On Sat, Aug 15, 2009 at 2:15 AM, Andrew
Fedoniouk<news@terrainformatica.com> wrote:
> Tab Atkins Jr. wrote:
>>
>> On Fri, Aug 14, 2009 at 8:02 PM, Andrew
>> Fedoniouk<news@terrainformatica.com> wrote:
>>>
>>> Tab Atkins Jr. wrote:
>>>>
>>>> On Fri, Aug 14, 2009 at 6:06 PM, Andrew
>>>> Fedoniouk<news@terrainformatica.com> wrote:
>>>>
>>>>> What if that element has background-image (real one) too?
>>>>>
>>>> Exactly the same as you would if you specified two backgrounds that
>>>> were both url()s.
>>>>
>>>> background: url(),url();
>>>> is *exactly the same* as
>>>> background: url(),linear-gradient();
>>>> in terms of how to treat it.
>>>>
>>> That is not the answer on my question.
>>>
>>> How would you remove gradient if element has gradient and background
>>> image
>>> with (e.g. no-repeat)?
>>
>> I'd do the exact same thing as I would if I had two background images
>> and I wanted to reset it to only one.
>
> So you have no solution. This multiple background thing does not allow to
> address components independently and this is bad per se. But this another
> story of course.

Indeed it is a different story.  I'd be glad to drop it - you can
bring it up in a separate discussion.

> Ok, let's assume that linear-gradient() is such an url.
> I would like to know
>
> 1) how it supposed to interact with background-position, background-origin,
> background-repeat and so on.

Exactly the same way as an SVG image without intrinsic dimensions.

> 2) what attribute exactly that linear-gradient() is value of?
>   You use background:linear-gradient() but what about
>   background-image:linear-gradient(), will it work?
>   If yes will it drop/nullify other background-*** attributes?

Yes.  Because it defines an image.  This isn't some special hack into
the background: syntax.  It's just a new way of specifying an image,
where previously we could only do so with url().

>>
>>> I suspect that you will propose something nice as this:
>>>
>>>  background: url(??????),none;
>>
>> Nah, just "background: url(...)".  I mean, you *could* put "none" in
>> there, but that's kind of unnecessary.  Setting background
>> automatically resets everything.
>
> I do not understand this, sorry.
> Hmm, I suspect I've defined initially the task clear enough...

Nah, I understood you.  You're just asking for something impossible.
CSS simply can't selectively cut out a single background-image while
leaving the others undisturbed.  Similarly, it can't add or remove a
single font from a font-family list.  It's a fundamental limitation of
the language currently, unrelated to gradients.

>> But if, for some reason, you still don't know it (say it's a
>> dynamically generated url and can change unpredictably), then you're
>> sort of screwed, exactly like you would be if you had two background
>> images and wanted to just remove one.  That's just one of the
>> limitations of CSS.
>>
>>> In short: gradients shall be uniquely addressable. solid-color() and
>>> linear-gradient() are mutually exclusive
>>> as they define value of the same thing.
>>
>> I'm still not sure how you're justifying gradients being the same as
>> colors.  They're not, in any way, as I, Brad, and several others in
>> other circumstances have said.  They're an image.
>
> Probably we are coming from different backgrounds. In all systems I know
> that use gradients there is a concept of so called brush. Brush can be
> solid (single color) or it can be gradient brush.
>
> For example in <canvas> fillStyle attribute accepts either solid brushes
> (just a color) or CanvasGradient.
>
> Here are brushes in GDI+: SolidBrush, HatchBrush, TextureBrush,
> LinearGradientBrush, and PathGradientBrush
> http://msdn.microsoft.com/en-us/library/cwka53ef.aspx
>
> In SVG you have
> <rect style="fill:rgb(0,0,255)"> or
> <rect style="fill:url(#orange_red)"> where #orange_red is a name
> of some <linearGradient> brush.
>
> As you see fill can accept either one value.
> http://www.w3.org/TR/SVG/painting.html#FillProperties
>
> Main characteristic of the brush - it fills given figure in full.
> Setting one drawing brush discards another.
> background-image in CSS is not a brush because of existence of
> background-repeat attribute.
> The only attribute that corresponds to the brush in CSS is background-color.
>
> Quod erat demonstrandum.

Sorry, not quite QED.  Let's talk SVG.  The fill and stroke properties
accept a *paint-server*.  Colors are indeed paint-servers, as are
gradients.  But so are *patterns*, which are just SVG images.
*Anything* in SVG can potentially be a paint-server, and used to fill
a shape.  Most drawing programs use the term 'brush' to refer to this
same concept, and they too can usually accept an image as a brush (it
just gets tiled infinitely).

Are you now going to argue that we should allow "color: url(myimage)"?
 If your argument is correct, then we should.

>>> That is why I am insisting that gradients are such colors (color
>>> fill/distribution functions to be precise).
>>
>> Even if two things are mutually exclusive, that does not mean they are
>> the same thing.
>
> As I said solid-color(), linear-gradient(), fractal-plasma(), etc. are
> all kinds of the same entity - the brush used for filling shapes.
>
> If you know any image editor you should know what I mean.
> E.g. in Xara you can fill figure by solid color or gradient.
>
> I simply don't understand where your idea about
> gradient-is-such-an-image comes from. That against any common practice and
> sense.

Answered this up above.  I've been using drawing programs that allow
images as brushes since I was in elementary school (some Mac program -
CoolPix or something?  I don't quite recall the name).

>>> As I said, there are many cases when you will want to have gradients on
>>> boxes other than background box of the element.
>>> Think about these cases:
>>>
>>> background-color: linear-gradient(top to bottom / yellow, blue);
>>
>> background: linear-gradient(top to bottom / yellow, blue);
>>
>>> border-top-color: yellow;
>>> border-left-color: linear-gradient(top to bottom / yellow, blue);
>>> border-right-color: linear-gradient(top to bottom / yellow, blue);
>>> border-bottom-color: blue;
>>
>> border-image: linear-gradient(top / yellow, blue) / ...; (though,
>> Brad's proposed syntax doesn't *quite* work here - I need to be able
>> to slice based on distance from each side, rather than distance from
>> the top/left of the image.)
>>
>>> column-rule-color: linear-gradient(top to bottom / yellow, blue);
>>
>> All right, you can't do this yet.  However, since column-rule is
>> basically just "borders, but between columns instead", we would be
>> within our right to ask for a column-rule-image that worked similarly,
>> so we could put fancy curlicues between our columns and such.
>>
>> Yes, you can justify using a gradient in the place of a color in
>> certain, specific circumstances.  But you really can't ever do it in a
>> reasonably general way, and that makes it useless.  It's much better
>> to find out what you're *really* doing with the image, and lay out a
>> general way to use it for any image.
>>
>> For example, in your code it sort of makes sense to use a vertical
>> gradient for column-rule-color.  But how do you treat a horizontal
>> gradient, or a diagonal one?  And what about radial-gradient()?  I
>> don't think there are good answers to these that aren't arbitrary.
>>
>
> Here is an example for you
> http://www.terrainformatica.com/w3/border-gradients.png
> that use horizontal and vertical gradients in borders.
> Quite useful, isn't it? I know many cases for radial gradients
> on borders too.
>
> I think it makes significantly more sense than that
> ugly border-style:outset that no-one is using 'cause as many UAs
> as many ways how to draw this.

Eh, I use border-style:outset and inset.  They get drawn a little
differently between UAs, but they're an easy way to make something
look like a button.

In the example you gave, though, you're trying to *hack* an outset
border effect using a gradient and (presumably) border-style:solid.
Those sorts of things are acceptable for 'generic' solutions, but CSS
is meant to be human-writable and easy to understand.  If you want an
outset border you should specify an outset border, and if it's not
pretty enough we should get it fixed so it is!

~TJ

Received on Saturday, 15 August 2009 17:08:27 UTC