In order to deliver better user experience, it’s common to introduce transitions during view components insertion or removal. San provides basic transition mechanism to facilitate the development of experience-rich web apps.
version
: >= 3.3.0
s-transition Transition controllers can be specified on elements using s-transition directives.
1 <button s-transition ="opacityTransition" > click</button >
The directive value is the corresponding property name of the element’s owner component.
1 2 3 4 5 6 7 8 san.defineComponent ({ template : '<div><button s-transition="opacityTransition">click</button></div>' , opacityTransition : { } });
s-transition directives are typically used with if or for directives.
1 2 <button s-transition ="opacityTransition" s-if ="allowEdit" > Edit</button > <b s-transition ="opacityTransition" s-else > Edit not allow</b >
The transition controller specified by s-transition directive can be a deep property of the owner component.
1 2 3 4 5 6 7 8 9 10 san.defineComponent ({ template : '<div><button s-transition="trans.opacity">click</button></div>' , trans : { opacity : { } } });
Note
: s-transition can be used on concrete elements only. If used on virtual elements, like template , s-transition will have no effect.
Animation Controller Animation controllers are objects that have enter and leave methods.
The signature for both enter and leave methods are: function({HTMLElement}el, {Function}done) . They will be called with the element to be transitioned, and shall call the done() callback when the transition is complete.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 san.defineComponent ({ template : ` <div> <button on-click="toggle">toggle</button> <button s-if="isShow" s-transition="opacityTrans">Hello San!</button> <button s-else s-transition="opacityTrans">Hello ER!</button> </div> ` , toggle : function ( ) { this .data .set ('isShow' , !this .data .get ('isShow' )); }, opacityTrans : { enter : function (el, done ) { var steps = 20 ; var currentStep = 0 ; function goStep ( ) { if (currentStep >= steps) { el.style .opacity = 1 ; done (); return ; } el.style .opacity = 1 / steps * currentStep++; requestAnimationFrame (goStep); } goStep (); }, leave : function (el, done ) { var steps = 20 ; var currentStep = 0 ; function goStep ( ) { if (currentStep >= steps) { el.style .opacity = 0 ; done (); return ; } el.style .opacity = 1 - 1 / steps * currentStep++; requestAnimationFrame (goStep); } goStep (); } } });
Note
:
There’s no transition controllers built in san. They’re left to the developers to implement, by means of:
Using CSS transitions or animations. Call done
on transitionend
or animationend
events.
Using requestAnimationFrame
. Call done
when it’s complete.
Using setTimeout
/ setInterval
in legacy browsers, call done
when it’s complete.
Any way within your imagination.
Animation Controller Creator If the property specified by s-transition directive is a function
, it will be treated as a transition controller creator .
Each time a transition is requested, the transition controller creator gets called and it’s return value is used as the transition controller .
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 san.defineComponent ({ template : ` <div> <button on-click="toggle">toggle</button> <button s-if="isShow" s-transition="opacityTrans">Hello San!</button> <button s-else s-transition="opacityTrans">Hello ER!</button> </div> ` , toggle : function ( ) { this .data .set ('isShow' , !this .data .get ('isShow' )); }, opacityTrans : function ( ) { return { enter : function (el, done ) { var steps = 20 ; var currentStep = 0 ; function goStep ( ) { if (currentStep >= steps) { el.style .opacity = 1 ; done (); return ; } el.style .opacity = 1 / steps * currentStep++; requestAnimationFrame (goStep); } goStep (); }, leave : function (el, done ) { var steps = 20 ; var currentStep = 0 ; function goStep ( ) { if (currentStep >= steps) { el.style .opacity = 0 ; done (); return ; } el.style .opacity = 1 - 1 / steps * currentStep++; requestAnimationFrame (goStep); } goStep (); } } } });
As with the event attributes , transition controller creator s accept arguments.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 san.defineComponent ({ template : ` <div> <button on-click="toggle">toggle</button> <button on-click="toggleTrans">toggle transition</button> <button s-if="isShow" s-transition="opacityTrans(noTransition)">Hello San!</button> <button s-else s-transition="opacityTrans(noTransition)">Hello ER!</button> </div> ` , toggle : function ( ) { this .data .set ('isShow' , !this .data .get ('isShow' )); }, toggleTrans : function ( ) { this .data .set ('noTransition' , !this .data .get ('noTransition' )); }, initData : function ( ) { return { noTransition : false }; }, opacityTrans : function (disabled ) { return { enter : function (el, done ) { if (disabled) { done (); return ; } var steps = 20 ; var currentStep = 0 ; function goStep ( ) { if (currentStep >= steps) { el.style .opacity = 1 ; done (); return ; } el.style .opacity = 1 / steps * currentStep++; requestAnimationFrame (goStep); } goStep (); }, leave : function (el, done ) { if (disabled) { done (); return ; } var steps = 20 ; var currentStep = 0 ; function goStep ( ) { if (currentStep >= steps) { el.style .opacity = 0 ; done (); return ; } el.style .opacity = 1 - 1 / steps * currentStep++; requestAnimationFrame (goStep); } goStep (); } } } });