les performance de rendu sur mobile
Post on 19-Jul-2015
365 Views
Preview:
TRANSCRIPT
Les performances de rendu
Jean-Pierre VincentArchitecte itinérant
Consultant et Formateur Perfs ou JS
@theystolemynick
POURQUOI FAIRE ?
Pour faire plaisir à l’utilisateur (et ton
CA)Temps de réponse :
• < 150 ms : instantané– Le but de toute interface touch
• 150 ms — 1 s : c’est la machine qui bosse– L’utilisateur stresse
• > 10s : bye bye
Animations :
• 60 Fps : fluide et naturel
• < 30 Fps : bye bye
Pour faire plaisir à Dieu
Pour faire des interfaces très réactive
Pour des interactions plus riches
Avoir 60 Fps ou pas
Comment fluidifier ?
$(‘.el1’).animate(
{ left: ‘-=600’
},
{ duration: 350,
easing:
‘bounce’
}
);
$(‘.el2’).animate …
Les ordres de grandeur
60 Hz = 16 ms pour :
• JS– Récupérer la position de l’élément
– Calcul de la nouvelle position
– Appliquer la nouvelle position
• Navigateur– Calculs de Layout
– Paint des zones modifées
– Pousser vers la carte graphique
Les manipulations DOM en JS
• el.offsetLeft …, el.clientLeft…, el. getBoundingClientRect()…
• el.scrollTo(), el.scrollTop, w.innerHeight
• el.getComputedStyle()
• evt.layerX, evt.offsetX
• SVG.getCharNumAtPosition(), SVG.getNumberOfChars()
jQuery.animate() utilise tout cela !
Animation prédictible ? JS quasi inutile
• On trash jQuery.animate
• Pré-calcul des styles
• JS se limite à ajouter / supprimer des classes
El1.addClass(‘disappear-to-left’)
El2.addClass(‘appear-from-right’)
Animation prédictible : transition CSS
.elements {
transition-property : left;
transition-timing-function: cubic-bezier(0,0,0.25,1);
transition-duration : 350 ms;
left: 600px;
}
.appear-from-right {
left: 0;
}
.disappear-to-left {
left: -600px;
}
Transitions CSS
• JS :– Récupérer la position de l’élément
– Calcul de la nouvelle position
– Appliquer la nouvelle position
• Navigateur– Calculs de Layout
– Paint des zones modifées
– Pousser vers la carte graphique
Les propriétés qui coûtent cher
Elles déclenchent Layout + Paint + Composite
• top, left, width, height, float
• font-*, border-*, padding-*, margin-*
• display, visibility
csstriggers.com
Les propriétés qui vont bien
.move-left{
transform: translateX(-600px);
}
.enlarge-your p {
transform : scale(1.3, 0) ;
}
• IE 8 : ms-filters, IE9 : prefix ms-
• IE10, chrome, Fx, OS mobile : standard
CSS transform / opacity
• JS :– Récupérer la position de l’élément
– Calcul de la nouvelle position
– Appliquer la nouvelle position
• Navigateur– Calculs de Layout
– Paint des zones modifées
– Pousser vers la carte graphique
Bonus : forcer le GPU (parfois)
.move-left {
transform:translate3d(-600px, 0, 0);
}
.enlarge-your p {
transform:scale3d(1.3, 0, 0);
}
Transition + translation + GPU = <3
.elements {
transition-property : transform;
transition-timing-function: cubic-bezier(0,0,0.25,1);
transition-duration : 350 ms;
left: 600px;
}
.appear-from-right {
transform: translate3d(-600px, 0px, 0px);
}
.disappear-to-left {
transform: translate3d(-1200px, 0px, 0px);
}
Transition + translation + GPU = <3
• JS :– Récupérer la position de l’élément
– Calcul de la nouvelle position
– Appliquer la nouvelle position
• Navigateur– Calculs de Layout
– Paint des zones modifées
– Pousser vers la carte graphique
60 FPS FTW
LES ANIMATIONS IMPRÉVISIBLES
Et pour les animations imprévisibles ?
• Parallax
• Drag
• Jeux vidéos
• …
Reprenons
• JS :– Récupérer la position de l’élément
– Calcul de la nouvelle position
– Appliquer la nouvelle position
• Navigateur– Calculs de Layout <= optimisé en CSS
– Paint des zones modifées <= optimisé en CSS
– Pousser vers la carte graphique
Récupérer la position : mise en cache
• Plutôt que$(el).on(‘touchmove’, function move() {
// get + set du DOM en boucle : BOOM
this.style.width = (this.offsetWidth + X);
}
• Préférervar width = el.offsetWidth;
$(el).on(‘touchmove’, function move() {
// un set, et même plusieurs d’affilé : SMOOTH
this.style.width = ( width += Y );
}
Reprenons
• JS :– Récupérer la position de l’élément
– Calcul de la nouvelle position
– Appliquer la nouvelle position
• Navigateur– Calculs de Layout
– Paint des zones modifées
– Pousser vers la carte graphique
Quand mettre à jour le DOM ?
// JAMAIS
setInterval( move, 16 );
// MIEUX, mais agressif et imprécis
(function boucle() {
setTimeout( boucle, 16);
move();
}());
// AU TOP
(function boucle() {
requestAnimationFrame(
boucle);
move();
}());
Alléger
var height = el.offsetHeight,
Y = 0;
$(el).on(‘touchmove’, function calculateDelta() {
… // Calcul séparé de Y (delta du doigt)
});
requestAnimationFrame( function move() {
… // check de la nécessité puis Raf(move)
this.style.height = (height += Y);
});
Reprenons
• JS :– Récupérer la position de l’élément
– Calcul de la nouvelle position <= dissocié
– Appliquer la nouvelle position <= optimisé
• Navigateur– Calculs de Layout
– Paint des zones modifées
– Pousser vers la carte graphique
Calculs lourds ?
var IA = new Worker(‘game-ia.js’);
var positions;
IA.addEventListener(‘moves’,function(e){
positions = e.data;
});
(function boucle() {
requestAnimationFrame( boucle );
moveUnits( positions );
})();
Calculs lourds ?
La technique ancestrale du
setTimeout( fn, 0);
Universel, increvable, lisible avec le bon snippet
Reprenons
• JS :
– Récupérer la position de l’élément
– Calcul de la nouvelle position <= dissocié et optimisé
– Appliquer la nouvelle position <= optimisé
• Navigateur
– Calculs de Layout
– Paint des zones modifées
– Pousser vers la carte graphique
DOM : la taille compte
(et la manière dont on s’en sert)
DOM Monster yellowlab.tools
Touche pas (trop) à mon DOM
• Peu de requête DOM
– Mise en cache des résultats en dehors des boucles
• Appliquer en batchs
– $el.addClass(‘error’) plutôt que $el.css
– .innerHTML marche encore !
– Pas d’alternance get / set
Apprends à faire tes sélecteurs
• Natif quand tu peux :$(document.getElementById(‘id’)) VS $(‘#id’)
document.querySelector(‘.item’) VS $(‘.item’).first()
• Limiter l’étendue de la recherche$container.find(‘.item’)
$container.find(‘ > li.item’)
• Déléguer$container.on( ‘click’, ‘li’, function(){} )
MAÎTRISER SES OUTILS
Assez de règles
Profilers — Android & Desktop
Profilers — Firefox & Firefox OS
Profilers — Windows
Profilers natifs — iOS & desktop
Les autres
• Opera : dragonfly
• IE8 : profiling JS
À l’instinct™ :
• iOS < 7
• Navigateur Android
• …
Librairies d’animation CSS 3
• Librairies CSS:– animate.css,
– Effekt.css
• Librairies JS : – D3.js,
– GSAP,
– TweenJS,
– jQuery 4
Conclusion
• JS seul est performant, merci de demander
• Watch your DOM !
• Use the CSS 3 / HTML5 force Luke
Je testerais, tu testeras,nous testerons …
MERCI
Jean-Pierre Vincent
@theystolemynick
Un audit ou une petite formation Perfs ? jp@braincracking.fr
top related