Accueil > Silverlight > Render Silverlight control to image: WriteableBitmap

Render Silverlight control to image: WriteableBitmap

Il existe un mécanisme très intéressant en silverlight qui permet de rendre un contrôle dans une image: la classe WriteableBitmap. Il est donc possible de créer une image qui sera la représentation graphique d’un ou plusieurs contrôles Xaml. C’est utile pour de la sauvegarde, de l’impression ou même de l’optimisation: imaginez un canvas qui contienne beaucoup de contrôles image superposés. Il sera possible de ne créer et afficher après la création de ces superpositions qu’un seul et unique contrôle image contenant l’image générée par le rendu du canvas et donc de ne pas continuer à gérer un arbre visuel complet devenu inutile.

Pierre Belin a fait un très bon article la dessus avec un sample qui montre comment utiliser l’encodeur PNG de Joe Stegman conjointement avec la classe WriteableBitmap pour sauvegarder le rendu d’un contrôle dans un fichier PNG.

Le point faible de cette classe est qu’elle n’est faite pour rendre en image que les contrôles qui sont VISIBLES à l’écran. Elle se base en fait sur les propriétés ActualWidth et ActualHeight pour définir la taille de l’image finale. Un contrôle non affiché à l’écran a la valeur 0 dans ces propriétés et ne sera donc pas rendu par un WriteableBitmap. Heureusement il existe un moyen de simuler l’affichage à l’écran et de mettre une valeur correcte dans ces propriétés.

A l’affichage d’un contrôle, le runtime silverlight appelle dessus les méthodes: Measure, Arrange et UpdateLayout. Il nous suffit donc d’appeler ces méthodes nous même pour que le runtime pense que notre contrôle est actuellement affiché. Attention cependant, il faut appeler ces méthodes sur tout l’arbre de contrôle à rendre. Voici une méthode récursive qui permet de le faire:

        private void MeasureArrange(UIElement el)
        {
            for (int i = 0; i < VisualTreeHelper.GetChildrenCount(el); i++)
            {
                FrameworkElement child = VisualTreeHelper.GetChild(el, i) as FrameworkElement;
                if (child != null)
                {
                    child.Measure(new Size(el.Width, el.Height));
                    child.Arrange(new Rect(0, 0, el.Width, el.Height));
                    child.UpdateLayout();
 
                    if (VisualTreeHelper.GetChildrenCount(child) != 0)
                        MeasureArrange(child);
                }
            }
            el.Measure(new Size(el.Width, el.Height));
            el.Arrange(new Rect(0, 0, el.Width, el.Height));
            el.UpdateLayout();
        }

Elle utilise VisualTreeHelper qui permet d’itérer dans les noeuds de l’arbre visuel.

Vous pouvez donc maintenant créer une image qui est la représentation visuelle d’un contrôle silverlight existant en mémoire mais non affiché à l’écran. Ça nous servira dans mon prochain article où on aura besoin d’afficher dans la navigateur des contrôles silverlight hors du plugin pour simuler in browser un mécanisme qui n’est implémenté dans silverlight que pour les scenarii OOB. Je laisse le suspense jusqu’à ce que j’aie le temps d’écrire celui là😉

Enjoy…

Étiquettes : ,

Laisser un commentaire

Entrez vos coordonnées ci-dessous ou cliquez sur une icône pour vous connecter:

Logo WordPress.com

Vous commentez à l'aide de votre compte WordPress.com. Déconnexion / Changer )

Image Twitter

Vous commentez à l'aide de votre compte Twitter. Déconnexion / Changer )

Photo Facebook

Vous commentez à l'aide de votre compte Facebook. Déconnexion / Changer )

Photo Google+

Vous commentez à l'aide de votre compte Google+. Déconnexion / Changer )

Connexion à %s

%d blogueurs aiment cette page :