Adobe FLASH Optimisation Manual

Optimisation des performances pour la
plate-forme ADOBE® FLASH®

Informations juridiques

Informations juridiques
Dernière mise à jour le 9/5/2012

Sommaire

Chapitre 1 : Présentation
Principes fondamentaux relatifs à l’exécution du code par le moteur d’exécution . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 1
Perception et réalité en matière de performances . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
Ciblage des optimisations . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
Chapitre 2 : Conservation de mémoire
Objets d’affichage . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5
Types de primitives . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 5
Réutilisation d’objets . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 7
Libération de mémoire . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12
Utilisation des bitmaps . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
Filtres et déchargement dynamique de bitmaps . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 20
Mip-mapping direct . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 21
Utilisation des effets 3D . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 22
Objets de texte et mémoire . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 23
Modèle d’événement et rappels . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 24
iii
Chapitre 3 : Réduction de la charge de l’unité centrale
Améliorations de Flash Player 10.1 liées à l’utilisation de l’unité centrale . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 25
Mode veille . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 27
Figement et libération d’objets . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 28
Evénements activate et deactivate . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 32
Interactions de la souris . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33
Minuteurs et événements ENTER_FRAME . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 34
Interpolations . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 36
Chapitre 4 : Performances d’ActionScript 3.0
Comparaison des classes Vector et Array . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 37
API de dessin . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 38
Capture et propagation d’événement . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 39
Utilisation des pixels . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 41
Expressions régulières . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 42
Optimisations diverses . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 43
Chapitre 5 : Performances de rendu
Options de retraçage . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 49
Contenu hors-scène . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 50
Qualité des clips . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 51
Fusion alpha . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 53
Cadence de l’application . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 54
Mise en cache sous forme de bitmap . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 55
Mise en cache manuelle sous forme de bitmap . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 63
Rendu des objets de texte . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 69
Processeur graphique . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 74
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Sommaire
Opérations asynchrones . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 76
Fenêtres transparentes . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 78
Lissage des formes vectorielles . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 79
Chapitre 6 : Optimisation de l’interaction avec le réseau
Amélioration en vue de l’interaction avec le réseau . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 81
Contenu externe . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 83
Erreurs d’entrée/sortie . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 85
Flash Remoting . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 86
Opérations de réseau superflues . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 88
Chapitre 7 : Utilisation des données multimédias
Vidéo . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 89
StageVideo . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 89
Audio . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 89
Chapitre 8 : Performances de la base de données SQL
Structure d’application visant à améliorer les performances de la base de données . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 91
Optimisation des fichiers de base de données . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 94
Traitement superflu de la base de données à l’exécution . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 94
Syntaxe SQL performante . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 95
Performances des instructions SQL . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 96
iv
Chapitre 9 : Test de performances et déploiement
Test de performances . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 97
Déploiement . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 98
Dernière mise à jour le 9/5/2012

Chapitre 1 : Présentation

Il est possible d’exécuter les applications Adobe® AIR® et Adobe® Flash® sur de nombreuses plates-formes, notamment sur des ordinateurs de bureau, des périphériques mobiles, des tablettes et des téléviseurs. Le présent document s’appuie sur des exemples et des études de cas pour présenter les normes de bonne pratique destinées aux développeurs qui déploient ces applications. Il traite des sujets suivants :
Conservation de mémoire
Réduction de la charge de l’unité centrale
Amélioration des performances d’ActionScript 3.0
Augmentation de la vitesse de rendu
Optimisation de l’interaction avec le réseau
Utilisation de l’audio et de la vidéo
Optimisation des performances de la base de données SQL
Test de performances et déploiement d’applications
1
La plupart des ces optimisations s’appliquent aux applications sur tous les périphériques, qu’il s’agisse du moteur d’exécution d’AIR ou du moteur d’exécution de Flash Player. Ce document décrit également les ajouts et exceptions correspondant à certains périphériques.
Certaines de ces optimisations sont centrées sur les fonctionnalités introduites dans Flash Player 10.1 et AIR 2.5. Néanmoins, la plupart d’entre elles s’appliquent également aux versions précédentes d’AIR et de Flash Player.

Principes fondamentaux relatifs à l’exécution du code par le moteur d’exécution

Pour comprendre comment améliorer les performances d’une application, il est essentiel de comprendre comment le moteur d’exécution de la plate-forme Flash exécute le code. Le moteur d’exécution fonctionne en boucle, certaines actions se produisant sur chaque « image ». On entend ici par image un simple bloc de temps déterminé par la cadence définie pour l’application. Le temps alloué à chaque image correspond directement à la cadence. Si vous spécifiez une cadence de 30 images par seconde, par exemple, le moteur d’exécution s’efforce de faire durer chaque image un trentième de seconde.
Vous définissez la cadence initiale de l’application au moment où vous créez celle-ci. Pour ce faire, vous pouvez utiliser les paramètres correspondants d’Adobe® Flash® Builder™ ou Flash Professional. Libre à vous également de définir la cadence initiale dans le code. Pour définir la cadence d’une application basée uniquement sur ActionScript, appliquez la balise de métadonnées
frameRate dans la balise Application ou WindowedApplication.
[SWF(frameRate="24")] à la classe du document racine. En MXML, définissez l’attribut
Chaque boucle d’image comprend deux phases, divisées en trois parties : les événements, l’événement le rendu.
Dernière mise à jour le 9/5/2012
enterFrame et
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Présentation
La première phase comporte deux parties (les événements et l’événement enterFrame), qui entraînent potentiellement toutes deux l’appel de votre code. Dans la première partie de la première phase, des événements du moteur d’exécution arrivent et sont distribués. Ces événements peuvent représenter la fin ou la progression d’opérations asynchrones telles qu’une réponse à un chargement de données sur un réseau. Ils peuvent également être la conséquence d’une entrée de l’utilisateur. Au fur et à mesure de la distribution des événements, le moteur d’exécution exécute le code dans des écouteurs que vous avez enregistrés. En l’absence d’événements, le moteur d’exécution attend, sans agir, la fin de cette phase d’exécution. Il n’accélère jamais la cadence par manque d’activité. Si des événements se produisent dans d’autres parties du cycle d’exécution, le moteur d’exécution les place en file d’attente et les distribue sur l’image suivante.
2
La deuxième partie de la première phase correspond à l’événement
enterFrame. Cet événement se distingue des autres
en ce qu’il est toujours distribué une fois par image.
Une fois tous les événements distribués, la phase de rendu de la boucle d’image commence. A ce stade, le moteur d’exécution calcule l’état de tous les éléments visibles à l’écran et les dessine. Le processus peut alors recommencer, à l’instar d’un coureur qui fait des circuits dans un stade.
Remarque : dans le cas des événements comprenant la propriété immédiat plutôt que d’attendre la phase de rendu. Evitez toutefois d’utiliser
updateAfterEvent, il est possible d’imposer un rendu
updateAfterEvent si elle entraîne
fréquemment des problèmes de performances.
Il est plus facile d’imaginer que la durée des deux phases de la boucle d’image est identique. Dans ce cas, une moitié de chaque boucle est dévolue à l’exécution des gestionnaires d’événements et du code d’application, tandis que la seconde moitié est consacrée au rendu. La réalité est néanmoins souvent toute autre. Il arrive que le code d’application utilise plus de la moitié du temps disponible dans l’image, étirant ainsi le créneau qui lui est alloué et réduisant celui du rendu. Dans d’autres cas, notamment lorsque le contenu visuel est complexe (filtres et modes de fondu, par exemple), c’est le rendu qui exige plus de la moitié du temps. La durée des phases étant variable, on dit souvent de la boucle d’image qu’elle est « élastique ».
Si les opérations combinées de la boucle d’image (exécution du code et rendu) durent trop longtemps, le moteur d’exécution ne peut pas assurer une cadence uniforme. L’image s’étend au-delà du temps qui lui est alloué, retardant ainsi le déclenchement de l’image suivante. Si, par exemple, une boucle d’image dépasse un trentième de seconde, le moteur d’exécution ne peut pas mettre l’écran à jour à 30 images par seconde. Le ralentissement de la cadence se traduit par une détérioration de l’expérience de l’utilisateur. Au mieux, l’animation est saccadée ; au pire, l’application se bloque et la fenêtre est vide.
Pour plus de détails sur l’exécution du code par le moteur d’exécution de la plate-forme Flash et le modèle de rendu, voir les ressources suivantes :
Flash Player Mental Model - The Elastic Racetrack (article de Ted Patrick, disponible en anglais uniquement)
Asynchronous ActionScript Execution (article de Trevor McCauley, disponible en anglais uniquement)
Optimizing Adobe AIR for code execution, memory & rendering à l’adresse
http://www.adobe.com/go/learn_fp_air_perf_tv_fr (Enregistrement vidéo de la présentation de Sean Christmann
lors de la conférence MAX, disponible en anglais uniquement)
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Présentation

Perception et réalité en matière de performances

Les utilisateurs de votre application sont les ultimes juges de ses performances. Les développeurs peuvent mesurer les performances d’une application en terme de la durée d’exécution de certaines opérations ou du nombre d’occurrences d’objet créées. Ces mesures ne présentent cependant aucun intérêt pour l’utilisateur. Celui-ci mesure parfois les performances selon d’autres critères. Par exemple, l’application s’exécute-t-elle rapidement et sans saccades ? Réagit­elle rapidement aux entrées ? A-t-elle un impact négatif sur les performances du système ? Pour tester les performances perçues, posez-vous les questions suivantes :
Les animations sont-elles fluides ou saccadées ?
Le contenu vidéo est-il fluide ou saccadé ?
Les clips audio s’exécutent-ils en continu ou contiennent-ils des interruptions ?
La fenêtre scintille-t-elle ou se vide-t-elle pendant les opérations de longue durée ?
Y a-t-il un décalage entre le moment où vous effectuez une saisie et l’affichage du texte ?
Si vous cliquez sur un élément, la réponse est-elle instantanée ou un délai se produit-il ?
Le ventilateur de l’unité centrale fait-il plus de bruit lorsque l’application s’exécute ?
Sur un ordinateur portable ou un périphérique mobile, la batterie se décharge-t-elle rapidement lors de l’exécution
de l’application ?
Les autres applications réagissent-elles plus lentement lorsque l’application s’exécute ?
3
Il est important de faire la distinction entre perception et réalité, car vous ne procéderez pas nécessairement de même pour optimiser les performances perçues ou pour accélérer au maximum les performances. Veillez à ce que l’application n’exécute jamais de tels volumes de code que le moteur d’exécution se trouve dans l’impossibilité de mettre à jour l’écran et de recueillir les entrées de l’utilisateur à fréquence régulière. Pour parvenir à cet équilibre, il est parfois nécessaire de diviser une tâche de programme en plusieurs parties, entre lesquelles le moteur d’exécution pourra mettre l’écran à jour (voir « Performances de rendu » à la page 49 pour plus de détails).
Les astuces et techniques décrites ci-après visent à vous permettre d’optimiser l’exécution du code lui-même et les performances perçues par l’utilisateur.

Ciblage des optimisations

Certaines améliorations des performances ne font pas de différence notoire pour l’utilisateur. Il est important de bien cibler les optimisations sur les zones problématiques de l’application concernée. Certaines techniques d’optimisation sont bonnes à mettre en pratique dans tous les cas. Pour d’autres, ce sont les exigences de l’application et la base d’utilisateurs visée qui en déterminent l’utilité. Il est vrai, par exemple, que les applications sont plus performantes si vous éliminez toute animation ou vidéo, de même que les filtres graphiques et les effets. Ce sont cependant ses fonctionnalités multimédias et graphiques qui sont l’une des raisons d’utiliser la plate-forme Flash pour créer des applications riches et expressives. Déterminez si le niveau de complexité souhaité est adapté aux performances caractéristiques des machines et périphériques sur lesquelles l’application s’exécutera.
Suivez ce conseil courant : « Ne cherchez pas à optimiser les performances trop tôt. » Certaines optimisations nécessitent de programmer du code peu lisible ou plus rigide. Il est alors plus difficile d’assurer la maintenance de ce code une fois qu’il est optimisé. Dans ce cas, il est souvent préférable d’attendre pour déterminer si les performances d’une portion spécifique du code sont médiocres avant de décider de son optimisation.
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Présentation
L’amélioration des performances exige souvent des compromis. En théorie, la réduction de la quantité de mémoire consommée par une application se traduit par une accélération de la vitesse d’exécution d’une tâche par l’application. En pratique, ce type d’amélioration n’est pas toujours possible. Imaginons que l’application se bloque pendant une opération. Pour résoudre ce problème, il est souvent nécessaire de répartir des tâches sur plusieurs images. Cette division se soldera, selon toute probabilité, par un ralentissement global du processus. Il se peut toutefois que l’utilisateur ne remarque pas le temps supplémentaire, car l’application continue de répondre à ses entrées et ne se bloque pas.
Pour identifier les éléments à optimiser et déterminer l’utilité des optimisations, il est essentiel d’effectuer des tests de performances. Vous trouverez des techniques et des conseils à ce sujet à la section « Test de performances et
déploiement » à la page 97.
Pour plus d’informations sur la façon de déterminer les parties d’une application qu’il serait judicieux d’optimiser, voir les ressources suivantes :
Performance-tuning apps for AIR à l’adresse http://www.adobe.com/go/learn_fp_goldman_tv_fr (Enregistrement
vidéo de la présentation d’Oliver Goldman lors de la conférence MAX. Disponible en anglais uniquement)
Performance-tuning Adobe AIR applications à l’adresse http://www.adobe.com/go/learn_fp_air_perf_devnet_fr
(Article d’Oliver Goldman, fondé sur la présentation, sur Adobe Developer Connection. Disponible en anglais uniquement.)
4
Dernière mise à jour le 9/5/2012

Chapitre 2 : Conservation de mémoire

Lors du développement d’applications, y compris les applications de bureau, il est toujours important de conserver la mémoire. Les périphériques mobiles sont toutefois particulièrement gourmands en mémoire et il est souhaitable de limiter la quantité de mémoire que consomme une application.

Objets d’affichage

Sélectionnez un objet d’affichage approprié.
ActionScript 3.0 propose un grand nombre d’objets d’affichage. Une des plus simples techniques d’optimisation visant à limiter la consommation de mémoire consiste à choisir le type approprié d’objet d’affichage. Pour créer des formes simples qui ne sont pas interactives, utilisez les objets Shape. Pour créer des objets interactifs ne nécessitant pas de scénario, faites appel aux objets Spirite. Pour une animation s’appuyant sur un scénario, recourez aux objets MovieClip. Choisissez toujours le type d’objet le plus performant pour l’application.
5
Le code suivant indique la quantité de mémoire utilisée par différents objets d’affichage :
trace(getSize(new Shape())); // output: 236
trace(getSize(new Sprite())); // output: 412
trace(getSize(new MovieClip())); // output: 440
La méthode getSize() indique la quantité de mémoire, exprimée en nombre d’octets, que consomme un objet. Vous pouvez constater que l’utilisation de plusieurs objets MovieClip, plutôt que des objets Shape simples, peut gaspiller de la mémoire si les fonctionnalités d’un objet MovieClip ne sont pas nécessaires.

Types de primitives

La méthode getSize() permet de tester les performances du code et de déterminer l’objet le plus adapté à la tâche concernée.
Tous les types de primitives, à l’exception de String, requièrent 4 à 8 octets de mémoire. Aucun type spécifique de primitive ne permet d’optimiser l’utilisation de la mémoire :
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
// Primitive types var a:Number; trace(getSize(a)); // output: 8
var b:int; trace(getSize(b)); // output: 4
var c:uint; trace(getSize(c)); // output: 4
var d:Boolean; trace(getSize(d)); // output: 4
var e:String; trace(getSize(e)); // output: 4
Si vous n’attribuez pas de valeur à une primitive Number, qui représente une valeur 64 bits, la machine virtuelle ActionScript (AVM) lui alloue 8 octets. Tous les autres types de primitives sont stockés dans 4 octets.
6
// Primitive types var a:Number = 8; trace(getSize(a)); // output: 4
a = Number.MAX_VALUE; trace(getSize(a)); // output: 8
Le comportement du type String est différent. La quantité d’espace de stockage alloué est fonction de la longueur de la chaîne :
var name:String; trace(getSize(name)); // output: 4
name = ""; trace(getSize(name)); // output: 24
name = "Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and scrambled it to make a type specimen book. It has survived not only five centuries, but also the leap into electronic typesetting, remaining essentially unchanged. It was popularized in the 1960s with the release of Letraset sheets containing Lorem Ipsum passages, and more recently with desktop publishing software like Aldus PageMaker including versions of Lorem Ipsum."; trace(getSize(name)); // output: 1172
La méthode getSize() permet de tester les performances du code et de déterminer l’objet le plus adapté à la tâche concernée.
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire

Réutilisation d’objets

Réutilisez des objets, si possible, au lieu de les recréer.
Une autre technique simple d’optimisation de la mémoire consiste à réutiliser les objets pour éviter, dans la mesure possible, de les recréer. N’utilisez pas le code suivant dans une boucle, par exemple :
const MAX_NUM:int = 18; const COLOR:uint = 0xCCCCCC;
var area:Rectangle;
for (var:int = 0; i < MAX_NUM; i++) { // Do not use the following code area = new Rectangle(i,0,1,10); myBitmapData.fillRect(area,COLOR); }
Le fait de recréer l’objet Rectangle dans chaque itération de la boucle utilise plus de mémoire et est une procédure plus lente, car un objet est créé à chaque itération. Procédez plutôt comme suit :
7
const MAX_NUM:int = 18; const COLOR:uint = 0xCCCCCC;
// Create the rectangle outside the loop var area:Rectangle = new Rectangle(0,0,1,10);
for (var:int = 0; i < MAX_NUM; i++) { area.x = i; myBitmapData.fillRect(area,COLOR); }
L’exemple précédent reposait sur un objet dont l’impact sur la mémoire était relativement faible. L’exemple suivant montre comment conserver encore plus de mémoire en réutilisant un objet BitmapData. Le code ci-dessous, qui crée un effet de mosaïque, gaspille de la mémoire :
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
var myImage:BitmapData; var myContainer:Bitmap; const MAX_NUM:int = 300;
for (var i:int = 0; i< MAX_NUM; i++) {
// Create a 20 x 20 pixel bitmap, non-transparent myImage = new BitmapData(20,20,false,0xF0D062);
// Create a container for each BitmapData instance myContainer = new Bitmap(myImage);
// Add it to the display list addChild(myContainer);
// Place each container myContainer.x = (myContainer.width + 8) * Math.round(i % 20); myContainer.y = (myContainer.height + 8) * int(i / 20);
}
Remarque : lorsque vous utilisez des valeurs positives, il est beaucoup plus rapide d’associer la valeur arrondie à int que d’utiliser la méthode
Math.floor().
8
L’image suivante illustre le résultat de l’effet de mosaïque sur le bitmap :
Effet de mosaïque résultant
Une version optimisée crée une occurrence unique de BitmapData référencée par plusieurs occurrences de Bitmap et donne le même résultat :
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
// Create a single 20 x 20 pixel bitmap, non-transparent var myImage:BitmapData = new BitmapData(20,20,false,0xF0D062); var myContainer:Bitmap; const MAX_NUM:int = 300;
for (var i:int = 0; i< MAX_NUM; i++) {
// Create a container referencing the BitmapData instance myContainer = new Bitmap(myImage);
// Add it to the display list addChild(myContainer);
// Place each container myContainer.x = (myContainer.width + 8) * Math.round(i % 20); myContainer.y = (myContainer.height + 8) * int(i / 20);
}
Cette technique conserve environ 700 Ko de mémoire, ce qui est considérable sur un périphérique mobile standard. Les propriétés de Bitmap permettent de manipuler tout conteneur de bitmap sans incidence sur l’occurrence de BitmapData originale :
// Create a single 20 x 20 pixel bitmap, non-transparent var myImage:BitmapData = new BitmapData(20,20,false,0xF0D062); var myContainer:Bitmap; const MAX_NUM:int = 300;
for (var i:int = 0; i< MAX_NUM; i++) {
// Create a container referencing the BitmapData instance myContainer = new Bitmap(myImage);
// Add it to the DisplayList addChild(myContainer);
// Place each container myContainer.x = (myContainer.width + 8) * Math.round(i % 20); myContainer.y = (myContainer.height + 8) * int(i / 20);
// Set a specific rotation, alpha, and depth myContainer.rotation = Math.random()*360; myContainer.alpha = Math.random(); myContainer.scaleX = myContainer.scaleY = Math.random();
}
9
L’image suivante illustre le résultat de l’effet des transformations du bitmap :
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
10
Résultat des transformations du bitmap
Voir aussi
« Mise en cache sous forme de bitmap » à la page 55

Pool d’objets

Faites appel à la technique de pool d’objets, dans la mesure du possible.
Le pool d’objets, qui consiste à réutiliser des objets à terme, est une autre technique d’optimisation importante. Vous créez un nombre défini d’objets lors de l’initialisation de l’application et les enregistrez dans un pool, tel qu’un objet Array ou Vector. Lorsque vous en avez terminé avec un objet, vous le désactivez pour éviter qu’il ne consomme des ressources de l’unité centrale et vous supprimez toutes les références mutuelles. Vous ne définissez toutefois pas les références sur de lui faire réintégrer le pool et de l’en extraire lorsque vous avez besoin d’un nouvel objet.
Lorsque vous réutilisez des objets, il n’est pas autant nécessaire de les instancier, processus gourmand en ressources. Elle limite également le déclenchement du nettoyeur de mémoire, qui est susceptible de ralentir l’application. Le code suivant illustre la technique de pool d’objets :
null, ce qui rendrait l’objet éligible pour le processus de nettoyage de la mémoire. Vous vous contentez
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
package {
import flash.display.Sprite;
public final class SpritePool {
private static var MAX_VALUE:uint; private static var GROWTH_VALUE:uint; private static var counter:uint; private static var pool:Vector.<Sprite>; private static var currentSprite:Sprite;
public static function initialize( maxPoolSize:uint, growthValue:uint ):void {
MAX_VALUE = maxPoolSize; GROWTH_VALUE = growthValue; counter = maxPoolSize;
var i:uint = maxPoolSize;
pool = new Vector.<Sprite>(MAX_VALUE); while( --i > -1 )
pool[i] = new Sprite();
}
public static function getSprite():Sprite {
if ( counter > 0 )
return currentSprite = pool[--counter];
var i:uint = GROWTH_VALUE; while( --i > -1 )
pool.unshift ( new Sprite() ); counter = GROWTH_VALUE; return getSprite();
}
public static function disposeSprite(disposedSprite:Sprite):void {
pool[counter++] = disposedSprite;
}
}
}
11
La classe SpritePool crée un pool de nouveaux objets lors de l’initialisation de l’application. La méthode getSprite() renvoie des occurrences de ces objets tandis que la méthode
disposeSprite() les libère. Le code autorise l’expansion
du pool une fois celui-ci entièrement consommé. Il est également possible de créer un pool de taille fixe, qui une fois épuisé, interdit l’allocation de nouveaux objets. Evitez si possible de créer des objets dans des boucles. Pour plus d’informations, voir « Libération de mémoire » à la page 12. Dans le code suivant, la classe SpritePool extrait de nouvelles occurrences :
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
const MAX_SPRITES:uint = 100; const GROWTH_VALUE:uint = MAX_SPRITES >> 1; const MAX_NUM:uint = 10;
SpritePool.initialize ( MAX_SPRITES, GROWTH_VALUE );
var currentSprite:Sprite; var container:Sprite = SpritePool.getSprite();
addChild ( container );
for ( var i:int = 0; i< MAX_NUM; i++ ) {
for ( var j:int = 0; j< MAX_NUM; j++ ) {
currentSprite = SpritePool.getSprite(); currentSprite.graphics.beginFill ( 0x990000 ); currentSprite.graphics.drawCircle ( 10, 10, 10 ); currentSprite.x = j * (currentSprite.width + 5); currentSprite.y = i * (currentSprite.width + 5); container.addChild ( currentSprite );
}
}
12
Le code suivant supprime tous les objets de la liste d’affichage lorsque l’utilisateur clique sur la souris et les réutilise ultérieurement à d’autres fins :
stage.addEventListener ( MouseEvent.CLICK, removeDots );
function removeDots ( e:MouseEvent ):void {
while (container.numChildren > 0 )
SpritePool.disposeSprite (container.removeChildAt(0) as Sprite );
}
Remarque : le vecteur de pool fait toujours référence aux objets Sprite. Si vous souhaitez définitivement supprimer l’objet de la mémoire, appliquez la méthode
dispose() à la classe SpritePool : elle efface toutes les références restantes.

Libération de mémoire

Supprimez toutes les références aux objets pour activer le déclenchement du nettoyage de la mémoire.
Il est impossible de démarrer directement le nettoyeur de mémoire dans la version commerciale de Flash Player. Pour être certain qu’un objet est collecté par le nettoyeur, supprimez toutes ses références. Rappelez-vous que l’opérateur
delete d’ActionScript 1.0 et 2.0 se comporte différemment dans ActionScript 3.0. Il permet uniquement de
supprimer des propriétés dynamiques sur un objet dynamique.
Remarque : vous pouvez appeler directement le nettoyeur de mémoire dans Adobe® AIR® et dans la version de débogage de Flash Player.
Le code suivant, par exemple, définit une référence Sprite sur
Dernière mise à jour le 9/5/2012
null :
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
var mySprite:Sprite = new Sprite();
// Set the reference to null, so that the garbage collector removes // it from memory mySprite = null;
Un objet défini sur null n’est pas nécessairement supprimé de la mémoire. Il arrive que le nettoyeur de mémoire ne s’exécute pas si la quantité de mémoire disponible est considérée comme suffisante. Le nettoyage de la mémoire est un processus imprévisible. L’affectation de mémoire, et non la suppression d’objets, déclenche le nettoyage de la mémoire. Lorsqu’il s’exécute, il détecte des graphes d’objets qui n’ont pas encore été nettoyés. Il détecte les objets inactifs dans ces graphes en identifiant les objets qui se font référence mais que l’application n’utilise plus, et les supprime.
Dans une application de grande taille, ce processus, qui est susceptible de solliciter fortement l’unité centrale, peut affecter les performances et entraîner un ralentissement notable de l’application. Réutilisez autant que possible les objets pour essayer de réduire le nombre d’exécutions du nettoyeur de mémoire. Définissez également les références sur null, le cas échéant, afin que le nettoyeur consacre moins de temps de traitement à rechercher les objets. Vous pourriez envisager le nettoyage de la mémoire comme une assurance : gérez donc la durée de vie des objets de manière explicite et systématique, dans la mesure du possible.
Remarque : définir une référence à un objet d’affichage sur null ne garantit pas le figement de l’objet. L’objet continue de consommer les ressources de l’unité centrale jusqu’à ce qu’il soit nettoyé. Veillez à désactiver votre objet avant de définir sa référence sur
null.
13
Vous pouvez lancer le nettoyeur de mémoire à l’aide de la méthode
System.gc(), que proposent Adobe AIR et la
version de débogage de Flash Player. Le profileur livré avec Adobe® Flash® Builder™ permet de lancer manuellement le nettoyeur de mémoire. L’exécution de ce dernier permet de vérifier le comportement de l’application et de déterminer si les objets sont correctement supprimés de la mémoire.
Remarque : tout objet servant d’écouteur d’événements peut être référencé par un autre objet. Dans ce cas, supprimez les écouteurs d’événements à l’aide de la méthode
removeEventListener() avant de définir les références sur null.
Il est heureusement possible de réduire instantanément la quantité de mémoire utilisée par les bitmaps. La classe BitmapData, par exemple, possède une méthode de 1,8 Mo. La mémoire utilisée actuellement atteint 1,8 Mo et la propriété
dispose(). L’exemple qui suit crée une occurrence de BitmapData
System.totalMemory renvoie une valeur
inférieure :
trace(System.totalMemory / 1024); // output: 43100
// Create a BitmapData instance var image:BitmapData = new BitmapData(800, 600);
trace(System.totalMemory / 1024); // output: 44964
L’occurrence de BitmapData est ensuite manuellement supprimée de la mémoire, qui est à nouveau vérifiée :
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
trace(System.totalMemory / 1024); // output: 43100
// Create a BitmapData instance var image:BitmapData = new BitmapData(800, 600);
trace(System.totalMemory / 1024); // output: 44964
image.dispose(); image = null;
trace(System.totalMemory / 1024); // output: 43084
Bien que la méthode dispose() supprime les pixels de la mémoire, il est néanmoins nécessaire de définir la référence
null pour la libérer totalement. Appelez systématiquement la méthode dispose() et définissez la référence sur
sur
null lorsque vous n’avez plus besoin d’un objet BitmapData afin de libérer immédiatement la mémoire.
14
Remarque : la classe System de Flash Player 10.1 et d’AIR 1.5.2 comporte une nouvelle méthode,
disposeXML(). Cette
méthode vous permet de mettre immédiatement un objet XML à la disposition du nettoyeur de mémoire, en transmettant l’arborescence XML en tant que paramètre.
Voir aussi
« Figement et libération d’objets » à la page 28

Utilisation des bitmaps

L’utilisation de vecteurs et non de bitmaps est un bon moyen d’économiser de la mémoire. Cependant, les vecteurs sollicitent beaucoup l’unité centrale et le processeur graphique, particulièrement s’ils sont nombreux. Les bitmaps, quant à eux, permettent d’optimiser le rendu, car le moteur d’exécution nécessite moins de ressources de traitement pour dessiner des pixels à l’écran que pour effectuer le rendu du contenu des vecteurs.
Voir aussi
« Mise en cache manuelle sous forme de bitmap » à la page 63

Sous-échantillonnage des bitmaps

Pour assurer une meilleure utilisation de la mémoire, les images opaques de 32 bits sont réduites en images de 16 bits lorsque Flash Player détecte un écran 16 bits. Ce sous-échantillonnage nécessite la moitié des ressources de mémoire et le rendu des images est plus rapide. Cette fonction est uniquement disponible dans Flash Player 10.1 pour Windows Mobile.
Remarque : avant Flash Player 10.1, tous les pixels créés en mémoire étaient stockés dans 32 bits (4 octets). Un simple logo de 300 x 300 pixels exigeait 350 Ko de mémoire (300*300*4/1024). Grâce à ce nouveau comportement, le même logo opaque requiert uniquement 175 Ko. Si le logo est transparent, il n’est pas sous-échantillonné à 16 bits et sa taille en mémoire ne change pas. Cette fonction s’applique uniquement aux bitmaps intégrés ou aux images chargées à l’exécution (PNG, GIF, JPG).
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
Sur les périphériques mobiles, il est parfois difficile de faire la différence entre le rendu d’une image en 16 bits ou en 32 bits. Sur une image simple ne comportant que quelques couleurs, aucune différence n’est détectable. Même sur une image plus complexe, les différences sont peu notables. Une certaine dégradation des couleurs peut cependant se produire lorsque l’utilisateur effectue un zoom avant sur l’image, et un dégradé de 16 bits est moins régulier que la version 32 bits.

Référence unique à BitmapData

Il est important d’optimiser l’utilisation de la classe BitmapData en réutilisant les occurrences autant que faire se peut. Flash Player 10.1 et AIR 2.5 proposent une nouvelle fonction de référence unique à BitmapData sur toutes les plates­formes. Lors de la création d’occurrences de BitmapData à partir d’une image intégrée, une version unique du bitmap est utilisée pour toutes ces occurrences. Si le bitmap est modifié par la suite, un bitmap qui lui est propre lui est attribué en mémoire. L’image intégrée peut provenir de la bibliothèque ou d’une balise [Embed].
Remarque : cette nouvelle fonction présente également des avantages pour le contenu existant, car Flash Player 10.1 et AIR 2.5 réutilisent automatiquement les bitmaps.
Lors de l’instanciation d’une image intégrée, un bitmap associé est créé en mémoire. Préalablement à Flash Player 10.1 et AIR 2.5, à chaque occurrence était attribué son propre bitmap en mémoire, comme illustré ci-dessous :
Mémoire Affiché
15
Bitmap source
Bitmap source
Bitmaps en mémoire avant Flash Player 10.1 et AIR 2.5
Occurrence du logo
Occurrence du logo
Dans Flash Player 10.1 et AIR 2.5, lors de la création de plusieurs occurrences d’une même image, une version unique du bitmap est utilisée pour toutes les occurrences de BitmapData. Ce concept est illustré ci-dessous :
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
16
Mémoire
Bitmap source
Affiché
Occurrence du logo
Occurrence du logo
Bitmaps en mémoire dans Flash Player 10.1 et AIR 2.5
Cette technique réduit considérablement la quantité de mémoire que nécessite une application utilisant de nombreux bitmaps. Le code suivant crée plusieurs occurrences du symbole
const MAX_NUM:int = 18;
var star:BitmapData; var bitmap:Bitmap;
for (var i:int = 0; i<MAX_NUM; i++) { for (var j:int = 0; j<MAX_NUM; j++) { star = new Star(0,0); bitmap = new Bitmap(star); bitmap.x = j * star.width; bitmap.y = i * star.height; addChild(bitmap) } }
Star :
La figure suivante illustre le résultat du code :
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
Résultat du code utilisé pour créer plusieurs occurrences du symbole
17
Avec Flash Player 10, par exemple, l’animation ci-dessus utilise environ 1 008 Ko de mémoire. Avec Flash Player 10.1, l’animation utilise seulement 4 Ko, que l’application soit installée sur un ordinateur de bureau ou sur un périphérique mobile.
Le code suivant modifie une seule occurrence de BitmapData :
const MAX_NUM:int = 18;
var star:BitmapData; var bitmap:Bitmap;
for (var i:int = 0; i<MAX_NUM; i++) { for (var j:int = 0; j<MAX_NUM; j++) { star = new Star(0,0); bitmap = new Bitmap(star); bitmap.x = j * star.width; bitmap.y = i * star.height; addChild(bitmap) } }
var ref:Bitmap = getChildAt(0) as Bitmap;
ref.bitmapData.pixelDissolve(ref.bitmapData, ref.bitmapData.rect, new Point(0,0),Math.random()*200,Math.random()*200, 0x990000);
La figure suivante illustre le résultat de la modification d’une seule occurrence de Star :
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
Résultat de la modification d’une occurrence unique
18
En interne, le moteur d’exécution attribue et crée automatiquement un bitmap en mémoire pour gérer les modifications au niveau des pixels. L’appel d’une méthode de la classe BitmapData entraîne la modification des pixels et la création d’une occurrence en mémoire, et aucune autre occurrence n’est mise à jour. La figure suivante illustre ce concept :
Mémoire Affiché
Occurrence du logo
Bitmap source
Occurrence du logo
setPixel()
Bitmap source
Occurrence du logo
Résultat en mémoire de la modification d’un bitmap unique
Si une étoile est modifiée, une nouvelle copie est créée dans la mémoire. L’animation résultante utilise environ 8 Ko de mémoire dans Flash Player 10.1 et AIR 2.5.
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
Dans l’exemple précédent, chaque bitmap peut être transformé individuellement. Pour créer uniquement l’effet de mosaïque, la méthode
var container:Sprite = new Sprite();
var source:BitmapData = new Star(0,0);
// Fill the surface with the source BitmapData container.graphics.beginBitmapFill(source); container.graphics.drawRect(0,0,stage.stageWidth,stage.stageHeight);
addChild(container);
beginBitmapFill() est la plus adaptée :
Cette technique donne le même résultat et une seule occurrence de BitmapData est créée. Pour imprimer une rotation permanente aux étoiles, plutôt que d’accéder à chaque occurrence de Star, utilisez un objet Matrix pivotant sur chaque image et transmettez-le à la méthode
var container:Sprite = new Sprite();
container.addEventListener(Event.ENTER_FRAME, rotate);
var source:BitmapData = new Star(0,0); var matrix:Matrix = new Matrix();
addChild(container);
var angle:Number = .01;
function rotate(e:Event):void { // Rotate the stars matrix.rotate(angle);
// Clear the content
container.graphics.clear();
// Fill the surface with the source BitmapData container.graphics.beginBitmapFill(source,matrix,true,true); container.graphics.drawRect(0,0,stage.stageWidth,stage.stageHeight); }
beginBitmapFill() :
19
Il est ainsi inutile de recourir à une boucle ActionScript pour créer l’effet. Le moteur d’exécution effectue toutes les opérations en interne. La figure suivante illustre le résultat de la transformation des étoiles :
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
Résultat de la rotation des étoiles
20
La mise à jour de l’objet BitmapData source original est automatiquement répercutée sur son utilisation à un autre emplacement sur la scène. Cette technique peut se révéler très performante. Elle ne permet pas cependant de mettre individuellement à l’échelle chaque étoile, comme dans l’exemple précédent.
Remarque : lors de l’utilisation de plusieurs occurrences d’une même image, le dessin varie selon qu’une classe est associée au bitmap original en mémoire. Si aucune classe n’est associée au bitmap, les images sont dessinées en tant qu’objets Shape avec des remplissages de bitmap.

Filtres et déchargement dynamique de bitmaps

Evitez les filtres, y compris ceux traités par le biais de Pixel Bender.
Utilisez un minimum d’effets tels que les filtres, y compris ceux traités sur les périphériques mobiles par le biais de Pixel Bender. Lors de l’application d’un filtre à un objet d’affichage, le moteur d’exécution crée deux bitmaps en mémoire, chacun de la taille de l’objet d’affichage. Le premier est une version pixellisée de l’objet d’affichage et sert à créer le second, auquel le filtre est appliqué :
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
Mémoire Aché
Version du bitmap non ltrée
Résultat
Version du bitmap ltrée
Deux bitmaps en mémoire lors de l’application d’un filtre
Lors de la modification de l’une des propriétés d’un filtre, les deux bitmaps sont mis à jour en mémoire pour créer le bitmap résultant. Ce processus sollicite l’unité centrale et les deux bitmaps peuvent nécessiter beaucoup de mémoire.
21
Flash Player 10.1 et AIR 2.5 proposent un nouveau comportement de filtrage sur toutes les plates-formes. Si le filtre n’est pas modifié sous 30 secondes, ou s’il est masqué ou hors écran, la mémoire utilisée par le bitmap non filtré est libérée.
Cette fonction économise donc la moitié de la mémoire exigée par un filtre sur toutes les plates-formes. Considérez par exemple un objet de texte auquel est appliqué un filtre de flou. Le texte en question est purement décoratif et ne subit aucune modification. Après 30 secondes, le bitmap non filtré est libéré de la mémoire. Il se produit le même résultat si le texte est masqué pendant 30 secondes ou est hors écran. Lors de la modification de l’une des propriétés du filtre, le bitmap non filtré en mémoire est recréé. Cette fonction s’appelle déchargement dynamique de bitmap. Même avec ces optimisations, utilisez les filtres avec précaution. Leur modification sollicite énormément l’unité centrale ou le processeur graphique.
Il est recommandé de créer des bitmaps dans un outil de création, tel qu’Adobe® Photoshop®, pour émuler les filtres, si possible. Evitez l’utilisation de bitmaps dynamiques créés à l’exécution dans ActionScript. L’utilisation de bitmaps créés en externe permet au moteur d’exécution de réduire la charge de l’unité centrale ou du processeur graphique, surtout si les propriétés du filtre ne changent pas à terme. Si possible, créez les effets requis sur un bitmap dans un outil de création. Vous pouvez ensuite afficher ce bitmap dans le moteur d’exécution sans le traiter, ce qui est beaucoup plus rapide.

Mip-mapping direct

Utilisez le mip-mapping pour mettre à l’échelle les images volumineuses, si besoin est.
Flash Player 10.1 et AIR 2.5 proposent, sur toutes les plates-formes, une autre nouvelle fonction liée au mip-mapping. Flash Player 9 et AIR 1.0 offraient une fonction de mip-mapping qui permettait d’améliorer la qualité et les performances des bitmaps sous-échantillonnés.
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
Remarque : le mip-mapping s’applique uniquement aux images chargées dynamiquement ou aux bitmaps intégrés ; il ne s’applique pas aux objets d’affichage filtrés ou mis en cache. Il est uniquement traité si la largeur et la hauteur du bitmap sont des nombres pairs. Si la hauteur ou la largeur est un nombre impair, le mip-mapping s’arrête. Ainsi, il est possible d’appliquer un mip-mapping à une image de 250 x 250 pour la réduire à 125 x 125 au maximum. Dans ce cas, en effet, l’une des dimensions au moins est un nombre impair. Les bitmaps dont les dimensions sont des puissances de deux permettent d’obtenir des résultats optimaux. Exemple : 256 x 256, 512 x 512, 1024 x 1024, etc.
Imaginons qu’une image de 1024 x 1024 est chargée et qu’un développeur souhaite la mettre à l’échelle pour créer une vignette dans une galerie. La fonction de mip-mapping effectue correctement le rendu de l’image lors de la mise à l’échelle en utilisant les versions sous-échantillonnées intermédiaires du bitmap en tant que textures. Les versions antérieures du moteur d’exécution créaient des versions sous-échantillonnées intermédiaires du bitmap en mémoire. Si une image de 1024 x 1024 était chargée et affichée à 64 x 64, les anciennes versions du moteur d’exécution créaient un bitmap pour chaque demi-taille ; dans notre exemple, 512 x 512, 256 x 256, 128 x 128 et 64 x 64.
Flash Player 10.1 et AIR 2.5 permettent à présent d’effectuer un mip-mapping direct de la taille originale à la taille de destination. Dans l’exemple précédent, seuls seraient créés le bitmap original de 4 Mo (1024 x 1024) et le bitmap de 16 Ko (64 x 64) auquel un mip-mapping a été appliqué.
La logique de mip-mapping est également compatible avec le déchargement dynamique de bitmap. Si seul le bitmap de 64 x 64 est utilisé, l’original de 4 Mo est vidé de la mémoire. S’il est nécessaire de répéter le mip-mapping, cet original est rechargé. Par ailleurs, si d’autres bitmaps de plusieurs tailles ayant fait l’objet d’un mip-mapping sont nécessaires, la chaîne de mip-mapping intermédiaire est utilisée pour les créer. S’il est nécessaire de créer un bitmap au 1:8, par exemple, les bitmaps au 1:4, 1:2 et 1:1 sont examinés pour déterminer lequel d’entre eux est chargé en mémoire en premier. En l’absence des autres versions, le bitmap original, au 1:1, est chargé à partir de la ressource et utilisé.
22
Le décompresseur JPEG peut effectuer un mip-mapping dans son propre format. Ce mip-mapping direct permet de décompresser directement un bitmap de grande taille vers un format mip-map sans charger intégralement l’image non compressée. La génération du mip-map est considérablement plus rapide. La mémoire exigée par les bitmaps volumineux n’est pas allouée et, donc, libérée. La qualité d’image JPEG est comparable à la technique de mip-mapping générale.
Remarque : évitez une utilisation excessive du mip-mapping. Bien qu’il améliore la qualité des images téléchargées, il n’est pas sans incidence sur la bande passante, la mémoire et la vitesse. Dans certains cas, il est préférable de mettre à l’échelle une version du bitmap dans un outil externe et de l’importer dans votre application. Ne créez pas des bitmaps de grande taille si vous allez les réduire plus tard.

Utilisation des effets 3D

Envisagez de créer manuellement les effets 3D.
Flash Player 10 et AIR 1.5 ont introduit un nouveau moteur 3D, qui permet d’appliquer des transformations de perspective aux objets d’affichage. Vous pouvez appliquer ces transformations à l’aide des propriétés
rotationY ou de la méthode drawTriangles() de la classe Graphics. Vous pouvez aussi définir un effet de
profondeur à l’aide de la propriété
z. Gardez à l’esprit que chaque objet d’affichage auquel une transformation de
perspective est appliquée est pixellisé en tant que bitmap et exige donc plus de mémoire.
La figure suivante illustre l’anticrènelage résultant de la pixellisation lors de l’application d’une transformation de perspective :
rotationX et
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
Anticrènelage résultant de l’application d’une transformation de perspective
23
L’anticrènelage est produit par la pixellisation dynamique sous forme de bitmap du contenu du vecteur. L’anticrènelage est appliqué lors de l’utilisation d’effets 3D dans la version de bureau d’AIR et de Flash Player, et dans la version mobile d’AIR 2.0.1 et d’AIR 2.5. L’anticrènelage n’est toutefois pas appliqué dans la version mobile de Flash Player.
Vous pouvez économiser de la mémoire s’il vous est possible de créer l’effet 3D manuellement sans faire appel à l’API native. Toutefois, les nouvelles fonctions 3D introduites dans Flash Player 10 et AIR 1.5 facilitent le mappage des textures, car les méthodes comme
drawTriangles() gèrent ce processus en natif.
Il vous appartient, en tant que développeur, de décider si les performances de l’effet 3D recherché sont optimisées par un traitement manuel ou via l’API native. Outre les considérations liées à la mémoire, tenez également compte des performances d’exécution et de rendu d’ActionScript.
Dans les applications mobiles d’AIR 2.0.1 et d’AIR 2.5 dans lesquelles vous définissez la propriété c’est le processeur graphique qui se charge des transformations 3D. En revanche, si la propriété
CPU, c’est l’unité centrale (et non le processeur graphique) qui effectue les transformations 3D. Dans les
sur
renderMode sur GPU,
renderMode est définie
applications de Flash Player 10.1, c’est l’unité centrale qui effectue les transformations 3D.
Lorsque l’unité centrale effectue les transformations 3D, tenez compte du fait que l’application d’une transformation 3D à un objet d’affichage nécessite deux bitmaps en mémoire. Un bitmap est nécessaire pour le bitmap source et un autre pour la version à laquelle une transformation de perspective est appliquée. Le comportement des transformations 3D est similaire à celui des filtres. Par conséquent, utilisez les propriétés 3D avec modération lorsque c’est l’unité centrale qui effectue les transformations 3D.

Objets de texte et mémoire

Utilisez Adobe® Flash® Text Engine pour le texte en lecture seule et des objets TextFields pour le texte de saisie.
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Conservation de mémoire
Flash Player 10 et AIR 1.5 ont introduit un nouveau moteur de texte puissant, Adobe Flash Text Engine (FTE), qui permet de conserver la mémoire système. Ce moteur est néanmoins une API de bas niveau qui nécessite une couche ActionScript 3.0 supplémentaire, fournie dans le package flash.text.engine.
Pour le texte en lecture seule, il est préférable d’utiliser Flash Text Engine, qui est peu gourmand en mémoire et offre un meilleur rendu. Les objets TextFields, quant à eux, sont plus adaptés au texte de saisie, car ils nécessitent moins de code ActionScript pour créer des comportements standard tels que la gestion de la saisie et le retour à la ligne.
Voir aussi
« Rendu des objets de texte » à la page 69

Modèle d’événement et rappels

Envisagez d’utiliser de simples rappels plutôt que le modèle d’événement.
Le modèle d’événement d’ActionScript 3.0 est fondé sur le concept de distribution d’objets. Il est orienté objet et optimisé pour la réutilisation du code. La méthode appelle la méthode du gestionnaire d’événement sur chaque objet enregistré. Ce modèle présente cependant un inconvénient : vous risquez en effet de créer un grand nombre d’objets tout au long de la vie de votre application.
dispatchEvent() effectue une boucle dans la liste d’écouteurs et
24
Imaginons que vous devez distribuer un événement à partir du scénario, pour indiquer la fin d’une séquence d’animation. Pour accomplir la notification, vous pouvez distribuer un événement à partir d’une image spécifique du scénario, comme illustré dans le code suivant :
dispatchEvent( new Event ( Event.COMPLETE ) );
La ligne de code suivante permet à la classe Document d’écouter cet événement :
addEventListener( Event.COMPLETE, onAnimationComplete );
Bien que cette technique soit correcte, l’utilisation du modèle d’événement natif peut être plus lente et exiger plus de mémoire qu’une fonction de rappel classique. Il est nécessaire de créer des objets d’événement et de les affecter en mémoire, ce qui ralentit les performances. Lorsque vous écoutez l’événement Event.ENTER_FRAME, par exemple, un objet d’événement est créé sur chaque image pour le gestionnaire d’événement. Les performances des objets d’affichage peuvent être particulièrement lentes, en raison des phases de capture et de propagation, ce qui se traduit par une forte sollicitation des ressources si la liste d’affichage est complexe.
Dernière mise à jour le 9/5/2012

Chapitre 3 : Réduction de la charge de l’unité centrale

En matière d’optimisation, il est également impératif de tenir compte de l’utilisation de l’unité centrale. L’optimisation du traitement par l’unité centrale améliore les performances et, par conséquent, la durée de vie de la batterie des périphériques mobiles.

Améliorations de Flash Player 10.1 liées à l’utilisation de l’unité centrale

Flash Player 10.1 propose deux nouvelles fonctions qui permettent d’économiser la puissance de traitement de l’unité centrale, à savoir la mise en pause et la reprise du contenu SWF lorsque ce dernier sort de l’écran, et la limitation du nombre d’occurrences de Flash Player sur une page.
25

Pause, ralentissement et reprise

Remarque : la fonction de pause, ralentissement et reprise n’est pas disponible sur les applications Adobe® AIR®.
Pour optimiser l’utilisation de l’unité centrale et de la batterie, Flash Player 10.1 propose une nouvelle fonction relative aux occurrences inactives. Cette fonction permet de limiter l’utilisation de l’unité centrale en mettant en pause et en reprenant le fichier SWF lorsque le contenu sort de l’écran et y revient. Grâce à cette fonction, Flash Player libère autant de mémoire que possible en supprimant tout objet pouvant être recréé lorsque la lecture du contenu reprend. Est considéré comme hors écran, tout contenu qui est totalement sorti de l’écran.
Deux cas de figure entraînent la sortie de l’écran du contenu SWF :
L’utilisateur fait défiler la page et le contenu SWF sort de l’écran.
Dans ce cas, tout contenu audio ou vidéo en cours de lecture continue de s’exécuter mais le rendu est interrompu. Si aucun contenu audio ou vidéo n’est en cours de lecture, pour parer à toute mise en pause de la lecture ou de l’exécution d’ActionScript, définissez le paramètre HTML lorsque le contenu SWF est hors écran ou masqué, son rendu est mis en pause, quelle que soit la valeur du paramètre
hasPriority.
L’utilisateur ouvre un onglet dans le navigateur, faisant passer à l’arrière-plan le contenu SWF.
Dans ce cas, quelle que soit la valeur de la balise HTML 8 ips. La lecture audio et vidéo est arrêtée et aucun rendu n’est traité à moins que le contenu SWF ne soit à nouveau visible.
Pour Flash Player 11.2 et les versions ultérieures exécutées sur des navigateurs Windows et Mac, vous pouvez utiliser l’événement ThrottleEvent dans votre application. Flash Player distribue un événement ThrottleEvent lorsqu’il interrompt, ralenti ou reprend la lecture.
hasPriority sur true. Souvenez-vous cependant que,
hasPriority, le contenu SWF est ralenti ou réduit de 2 à
L’événement ThrottleEvent est un événement de diffusion, c’est-à-dire qu’il est distribué par tous les objets EventDispatcher disposant d’un écouteur de cet événement. Pour plus d’informations sur les événements de diffusion, voir la classe DisplayObject.
Dernière mise à jour le 9/5/2012
OPTIMISATION DES PERFORMANCES POUR LA PLATE-FORME ADOBE FLASH
Réduction de la charge de l’unité centrale

Gestion des occurrences

Remarque : la fonction de gestion des occurrences ne s’applique pas aux applications Adobe® AIR®.
26
Utilisez le paramètre HTML
Flash Player 10.1 propose un nouveau paramètre HTML,
<param name="hasPriority" value="true" />
hasPriority pour retarder le chargement des fichiers SWF hors écran.
hasPriority :
Cette fonction limite le nombre d’occurrences de Flash Player démarrées sur une page, ce qui permet de conserver les ressources de l’unité centrale et de la batterie. Il s’agit d’attribuer une priorité spécifique au contenu SWF, de sorte qu’un certain contenu soit prioritaire sur une page. Prenons un exemple simple : un utilisateur explore un site Web dont la page d’index héberge trois fichiers SWF différents. Le premier est entièrement visible, le deuxième l’est partiellement et le dernier est hors écran et ne peut être atteint que par défilement. Les deux premières animations démarrent normalement mais la troisième est différée jusqu’à ce qu’elle devienne visible. C’est le comportement par défaut lorsque le paramètre SWF, même s’il est hors écran, définissez le paramètre paramètre
hasPriority, le rendu d’un fichier SWF qui n’est pas visible pour l’utilisateur est toujours mis en pause.
hasPriority est absent ou défini sur false. Pour s’assurer du démarrage d’un fichier
hasPriority sur true. Toutefois, quelle que soit la valeur du
Remarque : si les ressources de l’unité centrale sont insuffisantes, les occurrences de Flash Player ne démarrent plus automatiquement, même si le paramètre créées par le biais de JavaScript après le chargement de la page ne tiennent pas compte de l’indicateur
hasPriority correspond à true. Les nouvelles occurrences éventuellement
hasPriority. Tout
contenu de 1 x 1 ou 0 x 0 pixel démarre, empêchant le report du lancement des fichiers SWF d’aide si le webmestre omet l’indicateur
hasPriority. Il est cependant toujours possible de démarrer les fichiers SWF en cliquant dessus. Ce
comportement est appelé « cliquer pour lire ».
Le schéma ci-dessous illustre l’effet de la définition du paramètre
zone visible sur le périphérique de l’utilisateur
hasPriority sur différentes valeurs :
SWF
hasPriority déni
sur false ou absent
déni sur false
SWF
hasPriority déni
sur false ou absent
Animation SWF démarrée
Animation SWF non démarrée
Effets de différentes valeurs affectées au paramètre hasPriority
SWF
hasPriority
ou absent
Dernière mise à jour le 9/5/2012
Loading...
+ 72 hidden pages