- From: Brian Birtles <bbirtles@mozilla.com>
- Date: Thu, 26 Nov 2015 11:39:07 +0900
- To: "public-fx@w3.org" <public-fx@w3.org>
- Cc: "www-style@w3.org" <www-style@w3.org>
Hi, Web Animations defines Animatable.getAnimations() (where Animatable is implemented by Element and a forthcoming PseudoElement interface) and I think we've agreed to add Document.getAnimations() as well.[1] I've found two problems with the first method which I'm going to call Element.getAnimations() for now since PseudoElement doesn't exist yet. PROBLEM 1. Element.getAnimations() doesn't work on a subtree Recently I was working on a presentation where I wanted to use script to restart all the animations in a particular slide, represented by a <section> element. What I really wanted to do was something like: section.getAnimations().forEach(anim => anim.currentTime = 0); However, Element.getAnimations() doesn't return animations from its descendants (unlike querySelectorAll, getElementById, etc.). To further complicate things, Document.getAnimations() *does* return animations from its desendants (or will, once it is specced). PROBLEM 2. getAnimations() relies too much on the order in which animations are returned Whenever you see code using getAnimations(), it almost always looks like this: var anim = elem.getAnimations()[0]; That's really brittle. If some style is added that causes a transition to fire on elem, you may end up getting the wrong result. Of course, you can go through all the animations returned from getAnimations() and test their animationName/transitionProperty attributes and make sure you get the right object, but most people won't bother. PROPOSAL: Add some options to getAnimations() At a minimum, I think we need: * transitionProperty - used to filter by 'transitionProperty' which is only set on CSS transitions * animationName - used to filter by 'animationName' which is only set on CSS animations * id - used to filter by 'id' which may be set on script-generated animations * subtree - true means to fetch animations from descendents too (based on the Mutation Observer API) It's not obvious to me what the default value of subtree should be. I'd say 'false' except that would prevent using the same options object on Document.getAnimations(). Perhaps true? Given that most people will use this on leaf nodes anyway, maybe that would be ok? It's also not clear if we should only inspect the transitionProperty on CSSTransition objects, or if script-generated objects that define their own transitionProperty should be considered too. I guess they should. Likewise for animationName and CSS Animations. Some usage patterns are bogus, e.g. passing subtree:false to Document.getAnimations() or specifying both transitionProperty and animationName (except in rare cases where script added these properties), but maybe that's ok. Example usage: // Get the animation I just added elem.style.animation = 'move 3s'; var anim = elem.getAnimations({ animationName: 'move' })[0]; // Get all transform transitions in this section section.classList.add('move-in'); var transitions = section.getAnimations({ transitionProperty: 'transform' }); As you can see in the first example, we still have the '[0]' thing there. It's more safe now since we're only dealing with CSS Animations named 'move', but you could still get the wrong result and it's also a bit of an eyesore and pain to type. I wonder if it's worth following the querySelector/querySelectorAll pattern and having a pair of functions: getAnimation/getAnimations? In the singular, if there were multiple matches on the same element you'd return the one with the highest composite order[2] since that's most likely to be the one that you want. If you had multiple matches within a subtree, I'm not sure: tree order or composite order. Possible future extensions: * Parameters to get only CSS transition or only CSS animations? * Parameters to get all animations that affect certain properties? e.g. all animations that affect either the 'opacity' property or 'visibility' property. These can be easily implemented using Array.filter() so there's no urgency for these. What do you think? Brian [1] https://lists.w3.org/Archives/Public/public-fx/2015JulSep/0073.html [2] http://w3c.github.io/web-animations/#the-effect-stack
Received on Thursday, 26 November 2015 02:39:47 UTC