Server Notice:


Public Pad Latest text of pad CwdFZELqCn Saved Feb 11, 2013

Meeting 43:
Web animations minutes, 11 February 2013
Present: Shane, Brian, Dmitry, Silvia, Douglas
1. Review agenda for the week
2. Play control
3. Media integration
4. Play control revisited
5. Spec process / which specs to publish
Draft list of topics:
1. Play Control (Monday, 1st - until lunch)
2. Timing (sharing, templating, separate object etc.) (Tuesday morning)
3. Effect templating (Tuesday afternoon)
4. Groups (Wednesday)
5. Media Integration (Monday afternoon, Friday morning)
6. Autoplay behaviour (Wednesday)
7. Spec finalization and cleanup (Wednesday)
  - motion path
  - CSS integration
  - color interpolation
  - prioritization
8. Next F2F
Wednesday 11:30am offsite
Summary of current thinking regarding play control.
There are basically two options:
1) Have a PlayController object that is associated with the root of each tree in the timegraph (basically the interface between the DocumentTimeSource and a TimedItem in the current model).
2) Have play()/pause()/currentTime etc. on each item in the timegraph. Their behaviour varies depending on if they are at the root of the timegraph or not in the same was as HTMLMediaElement:
  viz. setting currentTime throws an exception
        setting playbackRate is ignored
        calling pause() is defined to pause just the element
        calling play() brings the element up to speed with the controller
There seems to be a preference for (1) so we have discussed the specifics of how this might work:
Issue 1: Naming.
Clock might be a more suitable name than PlayController.
Issue 2: What happens when you get the clock for a nested item?
var a = document.createAnimation(...);
var c = a.getClock();
var b = new ParGroup([a]);
c.pause(); // What happens here??
c is a ClockProxy object that tracks the clock associated with a regardless of any reparenting. In effect, it walks up the tree from a and finds the clock at the root and calls pause on it. As a result a.getClock() !== b.getClock() even though the actual clock is the same.
c throws an exception as it is no longer a clock associated with any TimedItem (it gets disocciated when a is attached to b).
c is still a valid clock, so pause() doesn't throw an exception; however c is not attached to anything any more so calling pause() has no effect. Shane calls this failing silently. Brian calls this succeeding but no-one cares.
General preference is for .
Issue 3: What is the behaviour of start(), particularly when called on a child item?
Scenario (i): Calling start() on a child item
var a = document.createAnimation(...);
var b = new ParGroup([a, d]);
a.start(); // what happens here?
remove a from c, start a
fail silently / ignore the developer
throw an Exception
start C
start C @ A
consensus start
We liked consensus start particularly because it mimicks the intended behaviour of HTML MediaController here and its consistent between child items and root items. Both mean, start when everyone attached to this clock is ready to go (and parents delegate for children).
Scenario (ii): Calling start() with a time value on a child item
var a = document.createAnimation(...);
var b = new ParGroup([a, d]);
a.start(4); // what happens here?
The 4 in this case is relative to the document time source. We think.
This also applies to b.start(4).
In this case, the child is saying, Ill be ready from document time 4. Once all children are ready then it starts.
Scenario (iii): Calling start twice
var a = document.createAnimation(...);
In this case the second call to start updates the start time and the behaviour from there falls out of the model.
start() in the first case, simply sets the start time of the clock to the current document time.
Revisiting this model. Some concerns include:
start() seems to do two things. It is actually just setting the start time of the clock, but since the default is the current document time, it has the effect of kick-starting the clock. People will think of it as actually starting playback (i.e.
Its yet to be seen if we actually can move start time to the clock or whether this would produce undesirable results for the animation sandwich.
start() as a convenience method (on TimedItem) needs justification (on the Clock you have an attribute start, so dont need a start() method).
What happens if you call play() when a clock does not have a startTime?
Dependencies between the media timeline and the animation timeline:
Three cases to consider:
* Slaving animations to media controllers
* Slaving media to Web Animations timing groups
* Slaving media controllers to Web Animations timing groups
a) Slaving animations to media controllers:
This could be done possibly by replacing the clock with the media controller. Other approaches possible too.
Use case: Having animations play in sync with video
Not sure we need to support this
b) Slaving media to Web Animations timing groups
This seems like the more useful arrangement.
Would need to define how media works in this case. Possibly we could add a wrapper for HTMLMediaElement that implements the TimedItem interface.
Would need to define:
- Three states of media elements (solo, slaved, wrapped) and how switching between them works (including mapping to syntax)
- How the wrapper works, including:
  - buffering behaviour on timing groups.
  - effect of timing functions (easing functions) applied to a parent of a media element (suggestion that it be an optional requirement to apply this to video)
c) Slaving media controllers to Web Animations timing groups
If there are things that MediaControllers can do which ParGroups cant, this might be an attractive possibility to support.
Discussed mapping to syntax. The arrangement elements in HTML has meaning with regards to layout, so it can be difficult to also arrange them with regards to timing.
One possibility is to put the animation elements in a separate section of the document or even a separate file. Media elements could be referred to using some sort of pointer element, e.g. <mediaRef href="#myVideo">. What happens if you <use> a <mediaRef>? It could be useful to have multiple <mediaRef> elements refer to the same media element,
     <mediaRef href="#productionCompanyLogo">
     <mediaRef href="#mainFeature">
     <mediaRef href="#productionCompanyLogo">
We could, perhaps, just define the behaviour when two <mediaRef> elements refer to the same media element and have overlapping intervals (e.g. first one wins, last one wins, etc.) This could be thought of as just another case of when we have animations that apply to the same element. Some things like merging would be different, but it should be mostly the same.
For HTML, the time dimension is something completely separate to the layout DOM of the page. Right now, the animation timeline could be defined in an SVG and the SVG can reference elements on the Web page to schedule parallel/sequential animation. In future, a new element in the <head> of a HTML page could be considered that would contain the specification of the time behaviour of (elements of) the Web page. The elements would be referenced from such a new element, similar to how <mediaRef> references video elements.
Buffering and blocking:
Buffering seems hard but we can probably build on top of HTMLs definitions with regards to ready state.
One proposal:
Have MediaRefItem as a wrapper for media elements inside the API. This allows media elements to appear more than once in the timing.
On the Clock have block/unblock behaviour. Each child (or just any element anywhere?) can say to the clock, Im blocking or Ive finished blocking. If the clock has one or more children (or things?) that are blocking then it effectively pauses.
This blocking/unblocking is internal to the model, i.e. it is not available in the API, at least not initially.
Children can opt-in to this. That is, a media ref item might decide not to tell the clock when it is buffering. In that case, it will just keep waiting for data and when it has enough data it will catch up to the time of the clock. It never falls out of sync. This might be an attribute, e.g. <mediaRef href="#video" freeSpirit>
SVG 1.2 has syncBehavior = "canSlip" | "locked" | "independent" | "default"
Shanes suggestion: blockingBehaviour="sync" or blockingBehaviour="swim"
Silvias suggestion: blocking="parent" or "all" (bubbles) or "none"
We could possibly go without the version that slips initially. That is, all media refs will block the clock for the first version. In a subsequent version we could add an attribute that defaults to blocking behaviour.
Should we fire events on (un)blocking?
e.g. one event when the clock first blocks, and one when it unblocks
Shane to do the spec text
Revisiting start()
Suggestion that maybe calling animate() also triggers the animation.
   elem.animate({ top: '100px' }, 3);
Doing so means you could possibly move start() to the clock or remove it altogether.
One issue is about the initial state of the animation after creating. There is a difference between an animation created with a start time but paused, and an animation that is created but has no effect. This is because of backwards fill.
Steve feels strongly that definition of an animation hierarchy shouldnt be mixed with play control i.e. that an animation hierarchy should not have a clock by default, and that something like attach() should generate the clock and the start time.
Issues raised:
1. What should we call the clock?
A: Clock
B: AnimationController
(Note that mis-spelling clock can be quite embarrassing)
Brainstorming other ideas: Player? ClockController? TimeMaster? TimeLord? PlayController? AnimationPlayer? WibblyWobblyTimeyWimey? TimeController? Timeline?
2. How should we get ?
A: anim.getClock()
B: anim.attach() [How do you get the clock after this point? Call attach() again? Also, need to define what this does on non-root items]
3. How do we control not-in-play-state vs in-play-state?
A: Clock.startTime is 'null' or not
B: Calling attach() puts it in play-state. TimedItem.detach() or AnimationController.timedItem = null puts it in not-in-play-state
4. How do we start or set start time?
A: Clock.startTime = 4 (or possibly anim.start(4) as a shortcut)
B: anim.attach(4) or AnimationController.startTime = 4
Also, need to revisit return value of getCurrentAnimations or if we want other methods there.
Reasons for splitting the spec into core model + API
Non-scripted UAs (e.g. platform font engines that implement SVG-in-opentype) only need implement the model not the API
Process: move model along faster without being gated on API issues
Redundancy e.g. start time defined in the model, then in the API the startTime attribute refers to the 'start time'
The model specification has no testable surface area
More crossreferencing / spec-jumping
Process risk: may delay or prevent API from being implemented
Reviewing the model in the absence of a review of the API may be detrimental (it limits the possibility of model changes that improve the API when it is reviewed)
Over time the model and API may grow out of sync and this will become an increasing pain to manage.
Next meeting: Tues 12 Feb 9:00 AEDST @ Google Sydney