F2F/Seattle 2011/Agenda/Animations/Harmonisation

From SVG

Executive summary

The relationship between SMIL Animation in SVG and CSS Animations/Transitions needs to be clearly established in order to guide future development of these specifications. To that end, a brief comparison between the two technologies is provided. Subsequently some concrete suggestions are offered on how we might proceed. Merging the two technologies seems difficult but aligning them may be possible.

Definitions

From this point forward, the following definitions will be used:

SVG Animation = SMIL Animation as used in SVG (!= SMIL Animation != SMIL 3.0)

CSS Animation = CSS Transitions + CSS Animations


SVG Animation x CSS Animation

Animation target

  • CSS: a set of properties on matched elements
  • SVG: one attribute on one element
div {
  animation-name: 'diagonal-slide';
  animation-duration: 5s;
  animation-iteration-count: 10;
}

@keyframes 'diagonal-slide' {
  from {
    left: 0;
    top: 0;
  }
  to {
    left: 100px;
    top: 100px;
  }
}
  
<animate xlink:href="#rect1" attributeName="left" from="0" to="100px" dur="5s" repeatCount="10"/>
<animate xlink:href="#rect1" attributeName="top" from="0" to="100px" dur="5s" repeatCount="10"/>

Summary: Target selection fundamentally different. SVG lacks animation re-use (proposed - for example a selector attribute on the animation elements [1])

Animation values

Combining with underlying value:

  • CSS: always overrides underlying style
  • SVG: can add to or override in various ways (additive="sum", by-animation, to-animation)

Combining with other animations:

  • CSS: only one animation can target a property (proposal to introduce additive property to CSS animations)
  • SVG: can add to or override other animations (additive="sum/replace")—complex rules for determining priorities of competing animations (begin time, doc order, sync dependencies)

Combining with itself:

  • CSS: When an animation repeats it goes back to the start
  • SVG: Either returns to start, or builds on final value (accumulate="sum")

Before/after animation is complete:

  • CSS: determined by animation-fill-mode property which allows extension in both directions (i.e. before the animation started)
  • SVG: determined by fill attribute (fill="freeze" means last value continues to apply, i.e. after only)

Summary: SVG offers a range of features for combining animations together and with the underlying value.

Animation types

  • CSS: Linear/piecewise-constant interpolation
  • SVG: Linear/piecewise-constant interpolation + animation along a path

Some differences:

  • Integers: CSS: use floor, SVG: round
  • Colors: CSS: sRGB, SVG: sRGB / linearRGB (depends on color-interpolation)
  • Paint servers: CSS: gradients with same no. of stops can be interpolated, SVG: no (but you can animate the gradient itself and its <stop>s)

Summary: Interpolation types and methods have some variation.

Interval timing

Animation begin

  • CSS: doc load/style resolution (incl. UI events: :hover, DOM manipulation: setAttribute("class",...))
  • SVG: doc load/events (not just UI)/accesskey/DOM (beginElement)/syncbase/wallclock ☺

Begin delay

  • CSS: transition/animation-delay
  • SVG: All begin times allow an offset to be applied

Terminating an animation

  • CSS: remove from animation-name
  • SVG: end attribute: same sorts of values as begin (a set time/event firing/syncbase etc.)

Restarting

  • CSS: remove from animation-name and re-add
  • SVG: if restart="always" the animation can restart mid-animation if another begin condition is satisfied

Repeating

  • CSS: animation-iteration-count: >= 0.0 | "infinite"
  • SVG: repeatCount: > 0.0 | "indefinite"; repeatDur

Summary: Interval timing is fundamentally different. The CSS timing model is primarily event-based (animations start when the document loads or a style is resolved). The SMIL timing model combines an event-based model with a scheduling model (many intervals can be scheduled in advance).

SMIL has complex (and confusing) rules for establishing intervals, e.g.

  • Zero-duration intervals ok, but not two in a row
  • If there's an end condition and all end times are before the next begin time the animation will not play—acts like a hard clamp
  • Once an interval (other than the first) is started, certain begin/end times are cleared

This is a significant difference.

Timing functions

Keyframing

  • CSS: @keyframes
  • SVG: keyTimes
@keyframes 'wobble' {
  0% {
    left: 100px;
  }
  40% {
    left: 150px;
  }
  60% {
    left: 75px;
  }
  100% {
    left: 100px;
  }
}

<animate attributeName="left" values="100px; 150px; 75px; 100px"
  keyTimes="0; 0.4; 0.6; 1" ... />
 

Timing functions

  • CSS: cubic bezier curve, discrete steps
  • SVG: cubic bezier curve (lacks CSS' keywords ease-in etc.), discrete steps (not as flexible as CSS), paced (even pace of change, especially for motion on a path)
@keyframes 'bounce' {
  from {
    top: 100px;
    animation-timing-function: ease-out;
  }
  25% {
    top: 50px;
    animation-timing-function: ease-in;
  }
  50% {
    top: 100px;
    animation-timing-function: ease-out;
  }
  75% {
    top: 75px;
    animation-timing-function: ease-in;
  }
  to {
    top: 100px;
  }
}
 
<animate attributeName="top" values="100px; 50px; 100px; 75px; 100px"
  calcMode="spline" keyTimes="0; 0.25; 0.5; 0.75; 1"
  keySplines="0 0 0.58 1; 0.42 0 1 1; 0 0 0.58 1; 0.42 0 1 1"/>

Reversing

  • CSS Transitions: Automatic reversing of animation (does ease-in remain ease-in? Discussion threads: [2] and [3])
  • CSS Animations: animation-direction - allows alternating direction on repeat; ease-in becomes ease-out. Otherwise separate animation required.
  • SVG: --

Summary: Timing functions are mostly comparable (with minor differences, CSS lacks 'paced', SVG lacks keywords and some step functions). However, SVG does not allow mixing types of animation functions (e.g. discrete/cubic bezier/paced) within the one animation definition. Also, SVG lacks any reversing functionality.

DOM functions

DOM interfaces

  • CSS:
    • Per-animation: pause/unpause, query pause/play state (animation-play-state—may be dropped?)
  • SVG:
    • Per-animation: start/stop animation (beginElement(At)/endElement(At)), query start time, current time, duration (interface SVGAnimationElement)
    • Per-document: pause/unpause, get/set current time (i.e. seeking, interface SVGSVGElement)

Events

  • CSS Transitions: TransitionEvent (type: transitionend). Context info: propertyName, elapsedTime
  • CSS Animations: AnimationEvent (type: animationstart/animationend/animationiteration). Context info: animationName[, elapsedTime]
  • SVG: TimeEvent (type: beginEvent/endEvent/repeatEvent). Context info: repeat iteration.

Manipulating timing

  • CSS: Interfaces for manipulating keyframe rules
  • SVG: Standard DOM interfaces (plus above-mentioned animation-specific methods)

Summary: DOM interfaces are fairly different. SVG lacks per-animation pause control but otherwise offers more control. The difference in event names is unfortunate.

DOM modifications

  • CSS: The values used for the keyframes and animation properties are snapshotted at the time the animation starts.
  • SVG: Not specified. (Dynamic changes allowed?)

Other fundamental differences

Approach to script

  • CSS: assumes script is possible—e.g. restarting requires script
  • SVG: tries to remain declarative. A significant use case for SVG animation is SVG assets (SVG backgrounds, fonts, cursors, favicons, <img> etc.) where script is not available

Harmonisation

Danger of creating a confusing platform of overlapping techologies that are subtlely different and incompatible.

Possible approaches

  1. Drop SVG Animation altogether and extend CSS Animations
  2. Merge the two into one master Web Animations spec with two syntaxes: CSS and XML
  3. Leave them as two separate technologies but make them play well together
    • Assign clear roles to each so web developers can easily judge when to use which
    • Make overlapping areas overlap properly (e.g. align syntax, interpolation rules)
    • Where either technology is suitable make them interchangeable

(The following analysis was helped hugely by Cameron's notes: http://www.w3.org/Graphics/SVG/WG/wiki/Talk:F2F/Auckland_2011/CSS_Animation)

Option 1: Drop SVG Animation altogether and extend CSS Animations

Following are some of the features that SVG currently offers that CSS does not. We needn't necessarily import all of them into CSS but this gives some idea of the scale of the task if we want to provide roughly equivalent functionality.

  • Combining with the underlying value: e.g. applying supplemental transformations to an element that already has a transform applied.
    • Also includes special types of animation like to-animation and by-animation
  • Combining independent animations of the same property: e.g. a 'swell' animation and 'spin' animation applying at once.
  • Animation along a path
    • Including "paced" animation which is most useful in this context
  • Begin/End in response to arbitrary events, other animations, etc.
  • End/Restart without script
  • Scheduled timing (e.g. begin="2s; 5s")
    • Adding this to CSS means determining if and when animations can automatically restart (SVG has restart="never|whenNotActive|always")
  • Synchronisation between animations
    • Means defining what sort of cyclic references are permitted and how they should be broken
  • Cumulative repeats
  • Fill behaviour (i.e. continuing to affect animated value after animation has finished)
  • Document-level pause control
  • Document-level seeking

Option 2: Merge the two into one master Web Animations spec with two syntaxes

Based on the above analysis, I think there are fundamental differences that make merging difficult. It would likely involve dropping compatibility with one technology or the other. (If we drop compatibility with SVG then it's basically Option 1.)

UPDATE: On further consideration, I'm not sure it's impossible. It will probably involve some backwards-incompatibility but it's possible that such incompatibility is only minor.

Option 3: Make SVG Animation and CSS Animation play well together

Assign clear roles to each so web developers know when to use each

  • For example, CSS Animation as a simplified SVG Animation. Ensure the functionality of CSS Animation is a subset of SVG Animation
    • → if you find yourself hitting the wall with CSS, time to consider SVG
    • Means adding to SVG anything missing that's in CSS: e.g. reversing, re-usable animations
  • Are there other ways of separating their roles?

Make overlapping areas overlap properly

Align syntax
  • Add CSS' transition/animation-timing-function keywords to SVG
    • Also involves allowing mixing timing functions within the one animation (currently only one calcMode per animation)
  • Rename / alias events? Standardise on which one? TimeEvent vs AnimationEvent? beginEvent vs animationstart?
Make interpolation consistent
  • Integer rounding
  • Color space interpolation—ok to leave CSS as just sRGB? Add HSL to SVG?
    • CSS Transitions needs to specify if interpolation is in premultiplied space or non-premultiplied and SVG should do likewise if it ever does RGBA colors.
  • In future, SVG's <animate> should be able to target a transform list (obsoleting <animateTransform> on the way) and should try to align with the animation definitions in CSS Transforms for this.
  • Cameron also notes that we it would be good to have definitions for how all CSS properties animate even if they're not interpolatable, e.g. fallback to discrete animation. [4]

Where either technology is suitable make them interchangeable

CSS animating SVG — Allow CSS to animate SVG attributes too?
SVG animating CSS
  • Allow SVG animation to target non-SVG content?
    • May be necessary if we decide that CSS Animation is a subset of SVG Animation
    • Might mean adding further definitions for what addition means for various CSS types?
Allow SVG animations to be used as an animation-name
Synchronisation between the two?
  • Allow CSS Animation names to appear in SVG syncbase timing specifications?
  • The other direction (triggering CSS Animations from SVG) should already be possible in a limited fashion: Use a <set> animation to change a class attribute. However, this won't give proper behaviour in the case of a seek.