W3C home > Mailing lists > Public > www-style@w3.org > July 2018

[CSSWG] Minutes Sydney F2F 2018-07-04 Part II: Images L3 [css-images]

From: Dael Jackson <daelcss@gmail.com>
Date: Tue, 24 Jul 2018 19:08:35 -0400
Message-ID: <CADhPm3v4WqjD7KQz5_uE9jtUHOtBjj1rq1MQiZGrpRFnEtq9EQ@mail.gmail.com>
To: www-style@w3.org
  These are the official CSSWG minutes.
  Unless you're correcting the minutes,
 Please respond by starting a new thread
   with an appropriate subject line.

Images L3

  - RESOLVED: cross-fade() takes one or more arguments, each has an
              optional percentages (Issue #2852)
  - RESOLVED: At computed value time, simplify directly nested
              cross-fade()s into a single cross-fade() (Issue #2852)
  - RESOLVED: At computed value time we collapse same <image> values
              in cross-fade()s and adding their percentages (Issue
  - RESOLVED: Gradient interpolation is moved to Images L4
  - RESOLVED: cross-fade() is moved to Images L4


Agenda: https://wiki.csswg.org/planning/sydney-2018#schedule

Scribe: heycam

Images Level 3
  github: https://github.com/w3c/csswg-drafts/issues/2852

  leaverou: We were trying to define interpolation between crossfades
            more reasonably with fantasai yesterday
  leaverou: When we're interpolating two cross fades with same images
            in a different order, A B , then B A
  leaverou: it ends up creating a cross fade of the cross fade
  leaverou: This comes up a lot, this interpolation happens when
            you're reversing a transition
  leaverou: so fantasai suggested when adding a rule, when the images
            is the same and the order is different, we flip the order
            and change the percentages to account for it
  leaverou: So 100% minus what it was
  leaverou: Is that OK? Since it's CR we should check
  fantasai: The use case for getting this to work simply is that when
            you're doing transitions between one image and another,
            when you interrupt that transition, you're half way between
  fantasai: so you want to interpolate between a crossfade and a start
  fantasai: Your computed value gets more and more complex

  dbaron: Is this the only interpolation type that has this problem?
  emilio: I suspect it can happen with transform as well
  dbaron: Yes
  birtles: With calc
  ericwilligers: With transform didn't we define ...
  TabAtkins: The interpolate() function
  dbaron: So transform can do the same thing with interpolate()
          nesting in the same way
  fantasai: We should probably do the same thing for transform then

  ericwilligers: Does interpolate() make cross-fade() redundant?
  leaverou: It only helps you get the intermediate values
  fantasai: There are use cases for cross-fade() where the author
            explicitly wants to fade between two things
  fantasai: and there are different ways of interpolating images,
            cross fade is only one of them
  fantasai: The proposed resolution is that interpolating cross-fade()
            or the interpolate() function, where the end point and
            start point have opposite order of arguments, you swap the
            order, so you don't nest the interpolating function
  xidorn: Shouldn't we just merge things when one side is crossfade A
          to B, and the other side is A or B?
  fantasai: That's the next question
  dbaron: What stage is this happening?
  fantasai: Computed value?
  dbaron: So part of the process of computing the value of a nested
          cross fade is to un-nest
  fantasai: No, when you're computing the mid point for
  dbaron: So you're changing the interpolation rules
  fantasai: Yes

  Rossen: Does that sounds reasonable to people?
  dbaron: Yes, if you make it consistently apply to other places where
          this problem comes up
  TabAtkins: Yes
  Rossen: Any objections to this? Do we need to add a note for the
          general interpolate function to be added as well?

  birtles: I misunderstood
  birtles: I thought this was just about computed value simplification
           of nested cross-fade
  ericwilligers: [writes examples on white board]
  birtles: I'm just wondering why we're adding rules to interpolation.
           Would the alternative be to say this is how nested
           crossfades are simplified at computed value time?
  birtles: Then you don't need to do anything particular for
  fantasai: We could do that
  leaverou: I'd be fine with that

  dino: cross-fade(A, B, 50%) is not the same as cross-fade(B, A, 50%)
  dino: It's 50% of src-overing the second on top of the first
  fantasai: And with transparency?
  dino: You can tell the difference between B over A 50% and A over B
        50%, yes
  ericwilligers: Would you advocate nested cross-fades()?
  dino: I'd advocate not interpolating
  fantasai: I don't think that's a good solution
  dino: If we're going to do it, then nested cross-fade(), maybe
  leaverou: Nested cross-fades() should be supported anyway
  dino: So, yes, nested cross-fades() would be my preferred solution
  leaverou: I think it's Safari and Chrome at the moment
  birtles: pre-fork, so one implementation

  TabAtkins: dino your point before about A B 50% and B A 50% being
             different is wrong, since it's a dissolve
  TabAtkins: Dissolve op rather than src-over op
  TabAtkins: since that's the correct way to fade between two images
             with potential transparencies

  Rossen: Do we need a whiteboarding breakout for this?
  leaverou: If reversing the order does produce the same image, what's
            the argument against it
  leaverou: If nobody has any then why do we need to break out

  <TabAtkins> idea is that cross-fade(foo 10%, bar 50%, baz) is
              eventually allowed
  <TabAtkins> by implication, `baz` gets 40%
  <fantasai> https://drafts.csswg.org/css-images-3/#cross-fade-function

  TabAtkins: Only options are (a) do nothing, allowing nesting, (b)
             accept these rules for interpolation simplification, or
             (c) accept these rules for computed value simplification
             and allow interpolation to fall out
  emilio: Why (c)?
  leaverou: Then it also allows us to simplify computed values returned
  emilio: I thought the point was nested cross fade is hard
  TabAtkins: It's not that it's hard, but in common cases, like
             repeatedly interrupting a transition, it results in a
             large stack of nested cross-fade()s
  TabAtkins: when you could simplify it down
  emilio: The difference between (b) and (c) is not observable
  TabAtkins: Yes it is
  emilio: I think I prefer (b)
  <TabAtkins> Note that if we *do* finally do the "any number of
              images" extension, then we can simplify *all* nested
              cross-fades, in all situations.

  leaverou: [shows demo of a transition between background images;
             it cross-fades smoothly into the transition and back out
             if the transition completes, but not if it's interrupted ]

  emilio: If you want to simplify what you interpolate, to avoid
          growing stacks of cross-fades(), you do it there
  emilio: but you also need to do it at computed values
  emilio: because the author might have specified a nested cross-fade()
  fantasai: The interpolated intermediate value must be a computed
  leaverou: If I'm understanding emilio correctly, you don't want to
            create this thing if you're going to simplify it anyway
  leaverou: If you're already going to simplify serialization of a
            specified (and computed) value
  emilio: It complicates the code
  birtles: I wonder if you're going to need to simplify it first
           anyway, in order to interpolate potentially nested inputs
           that you get
  ericwilligers: Yes
  birtles: Also will need to do it for addition, assuming that makes

  leaverou: Ideally it would be nice if cross-fade() accepted any
            number of arguments, and flatten them down to a single
  ericwilligers: Then you've got more permutations
  leaverou: If you could collapse the tree down to a flat cross fade
            list of values, it's simpler to apply
  TabAtkins: Since dissolve commutes, you can collapse all cross fades
  dino: Plus commutes, dissolve doesn't
  dino: What I got wrong is I'm src-overing not plusing
  TabAtkins: Plusing an appropriate dissolved image commutes, such
             that you can take nested cross fades and flatten it to a
             list of images that plus together
  leaverou: Should we just do that, allow cross-fade() to take a list
            of arguments?
  birtles: I think it's nicer from an authoring point of view too
  <birtles> that is, parsing the result of getComputedStyle is easier
            if you don't need to handle nested cross-fade functions

  leaverou: Another issue, if you're interpolating between A and
            cross-fade(A, ...), with the current rules you'll get a
            nested cross-fade()
  leaverou: We could define that the A gets promoted to 100%
            cross-fade, and just interpolate percentage
  <leaverou> https://github.com/w3c/csswg-drafts/issues/2853

  fantasai: I think the proposal for this one is you get a single
            cross-fade() with A and B with arguments and the
            appropriate percentage
  leaverou: We can, but if we're collapsing trees of cross-fade()s,
            it's less important
  fantasai: Collapsing trees is different from merging
  TabAtkins: Depends how we collapse
  dino: [looking at the issue] wouldn't it be x is between 0 and p,
        not p and 100?
  leaverou: You're interpolating between full A and the cross-fade
  leaverou: you want it to start at 100

  dbaron: I think we should try to resolve both at the same time
  dbaron: where the simplification happens, turning into multi arg
          cross-fade(), applies to both
  myles: The proposal is change the behavior because it makes it
         easier to compute?
  leaverou: This way you wouldn't need to interpolate to make a new
            cross-fade() at all
  myles: There is a difference between having a tree of cross fades
         and not having a tree
  TabAtkins: Nobody has trees yet
  TabAtkins: We're trying to avoid that now
  TabAtkins: Overall proposal is, avoid all trees of cross-fades, in
             all situations, by making it accept more than two
             arguments, just dissolve and plus throughout those
  TabAtkins: and make nested cross-fade() invalid, and make
             interpolations between them build the appropriate
             multi-arg value

  [fantasai explains that interpolating cross-fade(x% A, B) and
      cross-fade(y% A, B) results in cross-fade(z% A, B), not a tree
      of cross-fades()s]
  <fantasai> this issue about treating interpolation of A &
             cross-fade(y% A, B) and cross-fade(100% A, B) &
             cross-fade(y% A, B) the same way

  [whiteboard discussion of particular interpolations]
  leaverou: I still think nested cross-fades() should be valid, since
            they could come from variables
  myles: If the goal is to avoid avoiding trees, by making a list that
         has all the nodes of the tree, I don't see why that's better
  TabAtkins: You don't need to generate all the intermediate images
  myles: Is there a behavior change?
  TabAtkins: No
  myles: Then we should just say "as if", a browser optimization
  myles: so we're talking about computed values
  florian: Do we disallow in specified value?

  TabAtkins: Before we decide on that, let's look at the core thing
  TabAtkins: multi-arg cross-fade(), does it sound reasonable
  dino: And you must provide %s up to the last one?
  dino: allowed to go over 100%?
  TabAtkins: Yes [for first], and no.
  TabAtkins: If the percentages add up to over a 100%, you sum them
             and normalize to 100%
  TabAtkins: then the last one gets zero
  myles: Every time gets a percentage
  TabAtkins: Except the last
  TabAtkins: Last one gets what's left over
  dino: Complete error if you did (A 10%, B, C)?
  TabAtkins: syntax error
  myles: Is the purpose of this that humans will write this? or just
         to make the getCS output smaller?
  TabAtkins: So clearly we want this for interpolation
  heycam: Simplifying trees down to one level is same as flat list
  heycam: Want to collapse list to minimum number of items
  TabAtkins: If the goal is to avoid explosion...
  myles: If this is for humans to use, it's useful
  ericwilligers: Negative %s allowed?
  TabAtkins: no, individual %s above 100% should be invalid
  TabAtkins: But we can't syntactically restrict the sum

  birtles: I'm not 100% sure about the normalization part
  birtles: the syntax I like
  ericwilligers: Not sure about normalization when you have
                 interpolations between lists
  birtles: I was thinking, once the bucket's full, the overflow could
           be dropped
  myles: Should make it possible for the last one to have a %
  florian: To use them as 'fr's?
  leaverou: Right now, cross-fade() percentage is optional
  leaverou: probably it should retain this
  leaverou: Right now (A, B), the 50% is implied
  leaverou: (A 20%, B, C) should make sense
  shans: Distribute the rest
  leaverou: Yes
  myles: Allow the last percentage to be specified, then just weight
  fantasai: If you have (A 20%, C 20%, C 20%)
  fantasai: you could simply add transparent black to take the slack
  florian: Rather than normalizing to 100%?
  fantasai: If you're under
  shans: One problem with different behaviours on either side of 100%
         gets you non-linearities, bad for animation
  ericwilligers: like opacity:1

  TabAtkins: The suggest grammar is, cross-fade() takes one or more
             args, each has an optional %
  TabAtkins: We'll work out what missing %s mean
  Rossen: Any objections to that?

  RESOLVED: cross-fade() takes one or more args, each has an optional %

  leaverou: Next, collapsing trees of cross-fade()s
  leaverou: It's much easier to define interpolation that way
  leaverou: for authors reading it back
  leaverou: Don't know why we wouldn't collapse it down, especially
            given it's commutative
  emilio: Can we disallow nested cross-fade() in specified values?
  TabAtkins: No for the same reason you allow nested calc()s
  leaverou: For variables

  dbaron: Two other points
  dbaron: There are going to be other image-ish functions
  dbaron: cross-fade() one of these other functions containing a
          cross-fade() will be a reasonable thing
  dbaron: I think the other piece is that I think one of the things
          that results from disallowing it, everyone has to go and
          implement that, then later we'll allow it, which is more work
  dbaron: so we should just allow it now
  TabAtkins: Agreed
  TabAtkins: Specified values should allow it. Interpolated values
             collapse to a single value
  TabAtkins: Interpolated values, don't care?
  leaverou: I would collapse
  birtles: Collapse
  fantasai: I think so
  florian: Both kinds of smooshing down, flattening tree, and merging
           items in the list?
  leaverou: They are separate issues but I support both
  myles: So it's not just a simple substitution, there are formulas to
         calculate the percentages
  TabAtkins: Yes. It's just multiplication tho

  RESOLVED: At computed value time, simplify directly nested
            cross-fade()s into a single cross-fade()

  xidorn: That means the flattened value is the canonical form of that
  TabAtkins: Yes
  leaverou: Now dropping duplicated images
  TabAtkins: If you have multiple args which are the same image
  TabAtkins: should the canonical form automatically collapse those
             together and add their percentage
  leaverou: Do we have an algorithm for same image?
  fantasai: The computed value of the <url> is the absolute URL,
            so can just compare those.
  Rossen: The reason for simplifying is avoiding growth of the values
  leaverou: We should not only combine the duplicates but also sort
  fantasai: I think we need to simplify this, to avoid growing lists
  fantasai: We can do it very simply
  emilio: How do you define sorting images?
  myles: If you didn't want this, didn't want to collapse --
         internally you want to
  heycam: Are the cases where we want avoid this?
  fantasai: I don't think so
  fantasai: It's going to be the same when you collapse it all down
  fantasai: Notion of equality we want is "computed values are the
  frremy: With gradients, with px and %s ....
  fantasai: That's not computed value
  fantasai: That's used value

  RESOLVED: At computed value time we collapse same <image> values in
            cross-fade()s and adding their percentages

  leaverou: Sorting
  fantasai: You don't want computed value of cross-fade() where you
            randomly swap the order
  fantasai: re-sort into the target order and go from there?
  fantasai: So don't sort the computed value
  fantasai: but when interpolating, you re-sort the start point into
            the end point order
  fantasai: Order for interpolations falls out of cross-fade(start,
            end) and flattening
  myles: That's cool then CSS doesn't have to define order
  myles: so no sorting occurs, for interpolation it falls out of the
         simplification process
  <TabAtkins> When interpolating between A and B, you just
              cross-fade(A,B) then collapse; whatever that results in
              is the answer.

Deferring gradient interpolation to L4

  Rossen: Anyone objecting to deferring gradient interpolation to L4,
          to move L3 quicker?

  RESOLVED: Gradient interpolation is moved to Images L4

  fantasai: We should clarify the spec to say we do abrupt transitions
  fantasai: (and not cross-fade)
  leaverou: People can still wrap in cross-fade to force interpolation
            by cross-fade?
  TabAtkins: fantasai: Yes

Deferring cross-fade() to L4?

  Rossen: Nobody implements it
  Rossen: Images L3 is in a good shape
  TabAtkins: Let's do that

  RESOLVED: cross-fade() is moved to Images L4

  <leaverou> https://drafts.csswg.org/issues?spec=css-images-3&doc=cr-2012
  <leaverou> Gamma issue:

<br type="lunch" until="1:36pm">
Received on Tuesday, 24 July 2018 23:09:31 UTC

This archive was generated by hypermail 2.4.0 : Friday, 25 March 2022 10:09:11 UTC