Vue d'ensemble du rendu graphique de WPF

Cette rubrique fournit une vue d’ensemble de la couche visuelle WPF. Il se concentre sur le rôle de la classe pour la Visual prise en charge du rendu dans le modèle WPF.

Rôle de l’objet visuel

La Visual classe est l’abstraction de base à partir de laquelle chaque FrameworkElement objet dérive. Il sert également de point d’entrée pour écrire de nouveaux contrôles dans WPF, et de nombreuses façons peuvent être considérés comme le handle de fenêtre (HWND) dans le modèle d’application Win32.

L’objet Visual est un objet WPF principal, dont le rôle principal est de fournir la prise en charge du rendu. Les contrôles d’interface utilisateur, tels que Button et TextBox, dérivent de la Visual classe et l’utilisent pour conserver leurs données de rendu. L’objet Visual prend en charge les éléments suivants :

  • Affichage de sortie : rendu du contenu de dessin sérialisé persistant d’un objet visuel.

  • Transformations : exécution de transformations sur un objet visuel.

  • Détourage : prise en charge de la zone de détourage d’un objet visuel.

  • Test des résultats : détermination si une coordonnée ou une géométrie est contenue dans les limites d’un objet visuel.

  • Calculs de rectangle englobant : détermination du rectangle englobant d’un objet visuel.

Toutefois, l’objet Visual n’inclut pas la prise en charge des fonctionnalités non de rendu, telles que :

  • Gestion des événements

  • Disposition

  • Styles

  • Liaison de données

  • Globalisation

Visual est exposé en tant que classe abstraite publique à partir de laquelle les classes enfants doivent être dérivées. L’illustration suivante montre la hiérarchie des objets visuels exposés dans WPF.

Diagram of classes derived from the Visual object

Classe DrawingVisual

Il DrawingVisual s’agit d’une classe de dessin légère utilisée pour afficher des formes, des images ou du texte. Cette classe est considérée comme légère, car elle n’offre pas de dispositions ni d’options de gestion des événements, ce qui améliore ses performances d’exécution. C’est pour cette raison que les dessins sont idéaux pour les arrière-plans et les images clipart. Vous DrawingVisual pouvez l’utiliser pour créer un objet visuel personnalisé. Pour plus d’informations, consultez Utilisation d’objets DrawingVisual.

Classe Viewport3DVisual

Il Viewport3DVisual fournit un pont entre 2D Visual et Visual3D objets. La Visual3D classe est la classe de base pour tous les éléments visuels 3D. Vous Viewport3DVisual devez définir une Camera valeur et une Viewport valeur. La caméra vous permet d’afficher la scène. La fenêtre d’affichage détermine où la projection est mappée sur la surface 2D. Pour plus d’informations sur la 3D dans WPF, consultez Vue d’ensemble des graphiques 3D.

Classe ContainerVisual

La ContainerVisual classe est utilisée comme conteneur pour une collection d’objets Visual . La DrawingVisual classe dérive de la ContainerVisual classe, ce qui lui permet de contenir une collection d’objets visuels.

Dessin de contenu dans des objets visuels

Un Visual objet stocke ses données de rendu sous la forme d’une liste d’instructions graphiques vectorielles. Chaque élément de la liste d’instructions représente un ensemble de bas niveau de données graphiques et des ressources associées dans un format sérialisé. Quatre types de données de rendu différents peuvent du contenu de dessin.

Type de contenu de dessin Description
Graphismes vectoriels Représente les données graphiques vectorielles, ainsi que toutes les informations et Pen les informations associéesBrush.
Image Représente une image dans une région définie par un Rect.
Glyphe Représente un dessin qui affiche un GlyphRun, qui est une séquence de glyphes à partir d’une ressource de police spécifiée. Il s’agit de la représentation du texte.
Vidéo Représente un dessin qui rend de la vidéo.

Vous DrawingContext pouvez remplir un Visual contenu visuel. Lorsque vous utilisez les commandes de dessin d’un DrawingContext objet, vous stockez en fait un ensemble de données de rendu qui seront ultérieurement utilisées par le système graphique ; vous ne dessinez pas sur l’écran en temps réel.

Lorsque vous créez un contrôle WPF, tel qu’un Buttoncontrôle, le contrôle génère implicitement des données de rendu pour le dessin lui-même. Par exemple, la définition de la Content propriété du Button contrôle entraîne le stockage d’une représentation de rendu d’un glyphe.

A Visual décrit son contenu en tant qu’un ou plusieurs Drawing objets contenus dans un DrawingGroup. Il DrawingGroup décrit également les masques d’opacité, les transformations, les effets bitmap et d’autres opérations appliquées à son contenu. DrawingGrouples opérations sont appliquées dans l’ordre suivant lorsque le contenu est rendu : OpacityMask, , OpacityBitmapEffect, ClipGeometry, , GuidelineSet, puis Transform.

L’illustration suivante montre l’ordre dans lequel DrawingGroup les opérations sont appliquées pendant la séquence de rendu.

DrawingGroup order of operations
Ordre des opérations DrawingGroup

Pour plus d’informations, consultez Vue d’ensemble des objets de dessin.

Contenu de dessin sur la couche visuelle

Vous n’instanciez jamais directement un DrawingContext; vous pouvez cependant acquérir un contexte de dessin à partir de certaines méthodes, telles que DrawingGroup.Open et DrawingVisual.RenderOpen. L’exemple suivant récupère un objet DrawingContext à partir d’un DrawingVisual et l’utilise pour dessiner un rectangle.

// Create a DrawingVisual that contains a rectangle.
private DrawingVisual CreateDrawingVisualRectangle()
{
    DrawingVisual drawingVisual = new DrawingVisual();

    // Retrieve the DrawingContext in order to create new drawing content.
    DrawingContext drawingContext = drawingVisual.RenderOpen();

    // Create a rectangle and draw it in the DrawingContext.
    Rect rect = new Rect(new System.Windows.Point(160, 100), new System.Windows.Size(320, 80));
    drawingContext.DrawRectangle(System.Windows.Media.Brushes.LightBlue, (System.Windows.Media.Pen)null, rect);

    // Persist the drawing content.
    drawingContext.Close();

    return drawingVisual;
}
' Create a DrawingVisual that contains a rectangle.
Private Function CreateDrawingVisualRectangle() As DrawingVisual
    Dim drawingVisual As New DrawingVisual()

    ' Retrieve the DrawingContext in order to create new drawing content.
    Dim drawingContext As DrawingContext = drawingVisual.RenderOpen()

    ' Create a rectangle and draw it in the DrawingContext.
    Dim rect As New Rect(New Point(160, 100), New Size(320, 80))
    drawingContext.DrawRectangle(Brushes.LightBlue, CType(Nothing, Pen), rect)

    ' Persist the drawing content.
    drawingContext.Close()

    Return drawingVisual
End Function

Énumération du contenu de dessin sur la couche visuelle

En plus de leurs autres utilisations, Drawing les objets fournissent également un modèle objet pour énumérer le contenu d’un Visual.

Remarque

Lorsque vous énumérez le contenu du visuel, vous récupérez des Drawing objets, et non la représentation sous-jacente des données de rendu en tant que liste d’instructions graphiques vectorielles.

L’exemple suivant utilise la GetDrawing méthode pour récupérer la DrawingGroup valeur d’un Visual et l’énumérer.

public void RetrieveDrawing(Visual v)
{
    DrawingGroup drawingGroup = VisualTreeHelper.GetDrawing(v);
    EnumDrawingGroup(drawingGroup);
}

// Enumerate the drawings in the DrawingGroup.
public void EnumDrawingGroup(DrawingGroup drawingGroup)
{
    DrawingCollection dc = drawingGroup.Children;

    // Enumerate the drawings in the DrawingCollection.
    foreach (Drawing drawing in dc)
    {
        // If the drawing is a DrawingGroup, call the function recursively.
        if (drawing is DrawingGroup group)
        {
            EnumDrawingGroup(group);
        }
        else if (drawing is GeometryDrawing)
        {
            // Perform action based on drawing type.
        }
        else if (drawing is ImageDrawing)
        {
            // Perform action based on drawing type.
        }
        else if (drawing is GlyphRunDrawing)
        {
            // Perform action based on drawing type.
        }
        else if (drawing is VideoDrawing)
        {
            // Perform action based on drawing type.
        }
    }
}

Comment les objets visuels sont utilisés pour générer des contrôles

La plupart des objets de WPF sont composés d’autres objets visuels, ce qui signifie qu’ils peuvent contenir des hiérarchies variables d’objets descendants. La plupart des éléments d’interface utilisateur dans WPF, tels que les contrôles, sont composés de plusieurs objets visuels, représentant différents types d’éléments de rendu. Par exemple, le Button contrôle peut contenir un certain nombre d’autres objets, notamment ClassicBorderDecorator, ContentPresenteret TextBlock.

Le code suivant montre un Button contrôle défini dans le balisage.

<Button Click="OnClick">OK</Button>

Si vous deviez énumérer les objets visuels qui composent le contrôle par défaut Button , vous trouverez la hiérarchie des objets visuels illustrés ci-dessous :

Diagram of visual tree hierarchy

Le Button contrôle contient un ClassicBorderDecorator élément qui, à son tour, contient un ContentPresenter élément. L’élément ClassicBorderDecorator est responsable du dessin d’une bordure et d’un arrière-plan pour le Button. L’élément ContentPresenter est responsable de l’affichage du contenu du Button. Dans ce cas, étant donné que vous affichez du texte, l’élément ContentPresenter contient un TextBlock élément. Le fait que le contrôle utilise un ContentPresenter moyen que le Button contenu peut être représenté par d’autres éléments, tels qu’une Image ou une géométrie, tel qu’un EllipseGeometry.

Modèles de contrôle

La clé de l’expansion d’un contrôle dans une hiérarchie de contrôles est la ControlTemplate. Un modèle de contrôle spécifie la hiérarchie d’objets visuels par défaut d’un contrôle. Lorsque vous référencez explicitement un contrôle, vous référencez implicitement sa hiérarchie d’objets visuels. Vous pouvez remplacer les valeurs par défaut d’un modèle de contrôle afin de créer une apparence visuelle personnalisée pour un contrôle. Par exemple, vous pouvez modifier la valeur de couleur d’arrière-plan du Button contrôle afin qu’il utilise une valeur de couleur de dégradé linéaire au lieu d’une valeur de couleur unie. Pour plus d’informations, consultez Styles et modèles de bouton.

Un élément d’interface utilisateur, tel qu’un Button contrôle, contient plusieurs listes d’instructions graphiques vectorielles qui décrivent toute la définition de rendu d’un contrôle. Le code suivant montre un Button contrôle défini dans le balisage.

<Button Click="OnClick">
  <Image Source="images\greenlight.jpg"></Image>
</Button>

Si vous deviez énumérer les objets visuels et les listes d’instructions graphiques vectorielles qui composent le Button contrôle, vous trouverez la hiérarchie des objets illustrés ci-dessous :

Diagram of visual tree and rendering data

Le Button contrôle contient un ClassicBorderDecorator élément qui, à son tour, contient un ContentPresenter élément. L’élément ClassicBorderDecorator est chargé de dessiner tous les éléments graphiques discrets qui composent la bordure et l’arrière-plan d’un bouton. L’élément ContentPresenter est responsable de l’affichage du contenu du Button. Dans ce cas, étant donné que vous affichez une image, l’élément ContentPresenter contient un Image élément.

Prenez note des différents points suivants sur la hiérarchie d’objets visuels et les listes d’instructions de graphismes vectoriels :

  • L’ordre de la hiérarchie représente l’ordre de rendu des informations de dessin. À partir de l’élément visuel racine, les éléments enfants sont parcourus de gauche à droite et de haut en bas. Si un élément comporte des éléments enfants, ils sont parcourus avant les frères de l’élément.

  • Les éléments de nœud non feuille dans la hiérarchie, tels que ContentPresenterles éléments enfants, sont utilisés pour contenir des éléments enfants , ils ne contiennent pas de listes d’instructions.

  • Si un élément visuel contient une liste d’instructions de graphismes vectoriels et des enfants visuels, la liste d’instructions de l’élément visuel parent est rendue avant les dessins des objets enfants visuels.

  • Les éléments dans la liste d’instructions de graphismes vectoriels sont rendus de gauche à droite.

Arborescence d'éléments visuels

L’arborescence d’éléments visuels contient tous les éléments visuels utilisés dans l’interface utilisateur d’une application. Étant donné qu’un élément visuel contient des informations de dessin persistantes, vous pouvez considérer l’arborescence d’éléments visuels comme un graphique de scène contenant toutes les informations de rendu nécessaires pour composer la sortie vers le périphérique d’affichage. Cette arborescence est l’accumulation de tous les éléments visuels créés directement par l’application, que ce soit dans le code ou dans la balise. L’arborescence d’éléments visuels contient également tous les éléments visuels créés par l’expansion du modèle d’éléments comme les contrôles et les objets de données.

Le code suivant montre un StackPanel élément défini dans le balisage.

<StackPanel>
  <Label>User name:</Label>
  <TextBox />
  <Button Click="OnClick">OK</Button>
</StackPanel>

Si vous deviez énumérer les objets visuels qui composent l’élément StackPanel dans l’exemple de balisage, vous trouverez la hiérarchie des objets visuels illustrés ci-dessous :

Diagram of visual tree hierarchy of a StackPanel control.

Ordre de rendu

L’arborescence visuelle détermine l’ordre de rendu des objets visuels et de dessin WPF. L’ordre de parcours démarre avec l’objet visuel racine qui est le nœud supérieur de l’arborescence d’éléments visuels. Les enfants de l’objet visuel racine sont ensuite parcourus de gauche à droite. Si un objet visuel comporte des enfants, ses enfants sont parcourus avant les frères de l’objet visuel. Cela signifie que le contenu d’un objet visuel enfant est rendu avant le contenu de l’objet visuel.

Diagram of the visual tree rendering order

Objet visuel racine

L’objet visuel racine est le premier élément d’une hiérarchie d’arborescence d’éléments visuels. Dans la plupart des applications, la classe de base du visuel racine est soit WindowNavigationWindow. Toutefois, si vous hébergiez des objets visuels dans une application Win32, l’objet visuel racine serait le premier objet visuel hébergé dans la fenêtre Win32. Pour plus d’informations, consultez Didacticiel : hébergement d’objets visuels dans une application Win32.

Relation à l’arborescence logique

L’arborescence logique dans WPF représente les éléments d’une application au moment de l’exécution. Même si vous ne manipulez pas directement cette arborescence, cette vue de l’application est utile pour comprendre l’héritage de propriété et le routage d’événement. Contrairement à l’arborescence visuelle, l’arborescence logique peut représenter des objets de données non visuels, tels que ListItem. Dans de nombreux cas, l’arborescence logique est très étroitement liée aux définitions de balise d’une application. Le code suivant montre un DockPanel élément défini dans le balisage.

<DockPanel>
  <ListBox>
    <ListBoxItem>Dog</ListBoxItem>
    <ListBoxItem>Cat</ListBoxItem>
    <ListBoxItem>Fish</ListBoxItem>
  </ListBox>
  <Button Click="OnClick">OK</Button>
</DockPanel>

Si vous deviez énumérer les objets logiques qui composent l’élément DockPanel dans l’exemple de balisage, vous trouverez la hiérarchie des objets logiques illustrés ci-dessous :

Tree diagram
Diagramme de l’arborescence logique

L’arborescence d’éléments visuels et l’arborescence logique sont synchronisées avec l’ensemble actuel d’éléments d’application, reflétant tout ajout, suppression ou modification d’éléments. Toutefois, les arborescences présentent différentes vues de l’application. Contrairement à l’arborescence visuelle, l’arborescence logique ne développe pas l’élément d’un ContentPresenter contrôle. Cela signifie qu’il n’existe pas de correspondance directe entre une arborescence logique et une arborescence d’éléments visuels pour le même ensemble d’objets. En fait, l’appel de la méthode de GetChildren l’objet LogicalTreeHelper et de la méthode de GetChild l’objet VisualTreeHelper à l’aide du même élément qu’un paramètre génère des résultats différents.

Pour plus d’informations sur l’arborescence logique, consultez Arborescences dans WPF.

Affichage de l’arborescence d’éléments visuels avec XamlPad

L’outil WPF, XamlPad, offre une option permettant d’afficher et d’explorer l’arborescence visuelle qui correspond au contenu XAML actuellement défini. Cliquez sur le bouton Show Visual Tree (Afficher l’arborescence d’éléments visuels) de la barre de menus pour afficher l’arborescence d’éléments visuels. L’exemple suivant illustre l’expansion du contenu XAML en nœuds d’arborescence visuelle dans le panneau Explorateur d’arborescences visuelles de XamlPad :

Visual Tree Explorer panel in XamlPad

Notez comment les contrôles et Button les Labelcontrôles TextBoxaffichent chacune une hiérarchie d’objets visuels distincte dans le panneau Explorateur d’arborescences visuelles de XamlPad. Cela est dû au fait que les contrôles WPF ont une ControlTemplate arborescence visuelle de ce contrôle. Lorsque vous référencez explicitement un contrôle, vous référencez implicitement sa hiérarchie d’objets visuels.

Profilage des performances visuelles

WPF fournit une suite d’outils de profilage des performances qui vous permettent d’analyser le comportement d’exécution de votre application et de déterminer les types d’optimisations des performances que vous pouvez appliquer. L’outil Profileur Visual fournit une vue graphique détaillée des données de performances en mappant directement à l’arborescence d’éléments visuels de l’application. Dans cette capture d’écran, la section Utilisation du processeur du Profileur visuel vous donne une répartition précise de l’utilisation des services WPF, tels que le rendu et la disposition.

Visual Profiler display output
Sortie du Générateur de profils Visual

Comportement de rendu d’objet visuel

WPF introduit plusieurs fonctionnalités qui affectent le comportement de rendu des objets visuels : graphiques en mode conservé, graphiques vectoriels et graphiques indépendants de l’appareil.

Graphiques en mode retenu

Une des clés pour comprendre le rôle de l’objet visuel est de comprendre la différence entre les systèmes graphiques en mode exécution et en mode retenu. Une application Win32 standard basée sur GDI ou GDI+ utilise un système graphique en mode exécution. Cela signifie que l’application est responsable de la mise à jour la partie de la zone client qui est invalidée en raison d’une action telle que le redimensionnement d’une fenêtre ou de la modification de l’apparence visuelle d’un objet.

Diagram of Win32 rendering sequence

En revanche, WPF utilise un système en mode conservé. Cela signifie que les objets d’application ayant une apparence visuelle définissent un ensemble de données de dessin sérialisées. Une fois que les données de dessin sont définies, le système est ensuite responsable de répondre à toutes les demandes de mise à jour pour le rendu des objets d’application. Même au moment de l’exécution, vous pouvez modifier ou créer des objets d’application en vous appuyant toujours sur le système pour répondre aux demandes de dessin. La puissance d’un système graphique en mode retenu est telle que les informations de dessin restent dans un état sérialisé par l’application, mais la responsabilité du rendu est laissée au système. Le diagramme suivant montre comment l’application s’appuie sur WPF pour répondre aux demandes de peinture.

Diagram of WPF rendering sequence

Nouveau dessin intelligent

L’un des principaux avantages de l’utilisation de graphiques en mode conservé est que WPF peut optimiser efficacement ce qui doit être redessiné dans l’application. Même si vous avez une scène complexe avec différents niveaux d’opacité, vous ne devez généralement pas écrire du code spécial pour optimiser le nouveau dessin. Comparez cela avec la programmation Win32 dans laquelle vous pouvez consacrer beaucoup de temps à optimiser votre application en réduisant la quantité de nouveau dessin dans la région de mise à jour. Consultez Nouveau dessin dans la région de mise à jour pour obtenir un exemple du type de complexité impliquée dans l’optimisation du nouveau dessin dans les applications Win32.

Graphismes vectoriels

WPF utilise des graphiques vectoriels comme format de données de rendu. Les graphiques vectoriels, qui incluent les SVG (Scalable Vector Graphics), les métafichiers Windows (.wmf) et les polices TrueType, stockent les données de rendu et les transmettent sous forme de liste d’instructions qui décrivent comment recréer une image à l’aide de primitives graphiques. Par exemple, les polices TrueType sont des polices vectorielles qui décrivent un ensemble de lignes, de courbes et de commandes, plutôt qu’un tableau de pixels. L’un des principaux avantages des graphismes vectoriels est la possibilité de mettre à l’échelle à toute taille et résolution.

Contrairement aux graphismes vectoriels, les graphiques bitmap stockent les données de rendu sous forme de représentation pixel par pixel d’une image, prérendue pour une résolution spécifique. L’une des principales différences entre les formats de graphiques bitmap et de graphismes vectoriels est la fidélité à l’image source d’origine. Par exemple, lorsque la taille d’une image source est modifiée, les systèmes de graphiques bitmap étirent l’image, tandis que les systèmes de graphismes vectoriels mettent l’image à l’échelle, restant ainsi fidèle à l’image.

L’illustration suivante montre une image source qui a été redimensionnée à 300 %. Remarquez les distorsions qui apparaissent lorsque l’image source est étirée dans une image graphique bitmap plutôt que mise à l’échelle dans une image de graphisme vectoriel.

Differences between raster and vector graphics

Le balisage suivant montre deux Path éléments définis. Le deuxième élément utilise un ScaleTransform pour redimensionner les instructions de dessin du premier élément de 300 %. Notez que les instructions de dessin dans les Path éléments restent inchangées.

<Path
  Data="M10,100 C 60,0 100,200 150,100 z"
  Fill="{StaticResource linearGradientBackground}"
  Stroke="Black"
  StrokeThickness="2" />

<Path
  Data="M10,100 C 60,0 100,200 150,100 z"
  Fill="{StaticResource linearGradientBackground}"
  Stroke="Black"
  StrokeThickness="2" >
  <Path.RenderTransform>
    <ScaleTransform ScaleX="3.0" ScaleY="3.0" />
  </Path.RenderTransform>
</Path>

À propos des graphiques indépendants de la résolution et du périphérique

Deux facteurs système déterminent la taille du texte et des graphiques sur votre écran : la résolution et les points par pouce (PPP). La résolution décrit le nombre de pixels qui apparaissent sur l’écran. Plus la résolution est élevée, plus les pixels sont petits, générant ainsi des graphiques et du texte plus petits. Un graphique affiché sur un écran défini sur 1024 x 768 apparaîtra beaucoup plus petit lorsque la résolution est définie sur 1600 x 1200.

L’autre paramètre système, PPP, décrit la taille d’un pouce d’écran en pixels. La plupart des systèmes Windows ont un PPP de 96, ce qui signifie qu’un pouce d’écran est de 96 pixels. L’augmentation du paramètre PPP rend le pouce d’écran plus grand ; la réduction du paramètre PPP rend le pouce d’écran plus petit. Cela signifie qu’un pouce d’écran n’a pas la même taille qu’un pouce réel ; dans la plupart des systèmes, ceci n’est probablement pas le cas. Lorsque vous augmentez le paramètre PPP, les graphiques et le texte reconnaissant la résolution sont plus volumineux car vous avez augmenté la taille du pouce d’écran. L’augmentation du paramètre PPP peut rendre du texte plus facile à lire, notamment à des hautes résolutions.

Toutes les applications ne reconnaissent pas la résolution : certaines utilisent les pixels matériels comme unité de mesure principale ; la modification du paramètre PPP système n’a aucun effet sur ces applications. Beaucoup d’autres applications utilisent des unités reconnaissant la résolution pour décrire les tailles de police, mais utilisent des pixels pour décrire tout le reste. La définition du paramètre PPP sur une valeur trop basse ou trop élevée peut entraîner des problèmes de disposition pour ces applications, car le texte des applications évolue avec le paramètre PPP du système, mais pas l’interface utilisateur des applications. Ce problème a été éliminé pour les applications développées à l’aide de WPF.

WPF prend en charge la mise à l’échelle automatique à l’aide du pixel indépendant de l’appareil comme unité de mesure principale, au lieu de pixels matériels ; Les graphiques et le texte sont mis à l’échelle correctement sans aucun travail supplémentaire du développeur d’applications. L’illustration suivante montre un exemple de la façon dont le texte et les graphiques WPF apparaissent à différents paramètres DPI.

Graphics and text at different DPI settings
Graphique et texte avec différents paramètres PPP

Classe VisualTreeHelper

La VisualTreeHelper classe est une classe d’assistance statique qui fournit des fonctionnalités de bas niveau pour la programmation au niveau de l’objet visuel, ce qui est utile dans des scénarios très spécifiques, tels que le développement de contrôles personnalisés hautes performances. Dans la plupart des cas, les objets d’infrastructure WPF de niveau supérieur, tels que Canvas et TextBlock, offrent une plus grande flexibilité et facilité d’utilisation.

Test des résultats

La VisualTreeHelper classe fournit des méthodes pour le test d’accès sur les objets visuels lorsque la prise en charge des tests de positionnement par défaut ne répond pas à vos besoins. Vous pouvez utiliser les HitTest méthodes de la VisualTreeHelper classe pour déterminer si une valeur de coordonnée de géométrie ou de point se trouve dans la limite d’un objet donné, telle qu’un contrôle ou un élément graphique. Par exemple, vous pouvez utiliser le test des résultats pour déterminer si un clic de souris dans le rectangle englobant d’un objet se trouve dans la géométrie d’un cercle. Vous pouvez également choisir de substituer l’implémentation par défaut du test des résultats pour effectuer vos propres calculs de test des résultats personnalisés.

Pour plus d’informations sur le test des résultats, consultez Test des résultats dans la couche visuelle.

Énumération de l’arborescence d’éléments visuels

La VisualTreeHelper classe fournit des fonctionnalités permettant d’énumérer les membres d’une arborescence visuelle. Pour récupérer un parent, appelez la GetParent méthode. Pour récupérer un enfant ou un descendant direct d’un objet visuel, appelez la GetChild méthode. Cette méthode retourne un enfant Visual du parent à l’index spécifié.

L’exemple suivant montre comment énumérer tous les descendants d’un objet visuel, qui est une technique utile si vous voulez sérialiser toutes les informations de rendu d’une hiérarchie d’objets visuels.

// Enumerate all the descendants of the visual object.
static public void EnumVisual(Visual myVisual)
{
    for (int i = 0; i < VisualTreeHelper.GetChildrenCount(myVisual); i++)
    {
        // Retrieve child visual at specified index value.
        Visual childVisual = (Visual)VisualTreeHelper.GetChild(myVisual, i);

        // Do processing of the child visual object.

        // Enumerate children of the child visual object.
        EnumVisual(childVisual);
    }
}
' Enumerate all the descendants of the visual object.
Public Shared Sub EnumVisual(ByVal myVisual As Visual)
    For i As Integer = 0 To VisualTreeHelper.GetChildrenCount(myVisual) - 1
        ' Retrieve child visual at specified index value.
        Dim childVisual As Visual = CType(VisualTreeHelper.GetChild(myVisual, i), Visual)

        ' Do processing of the child visual object.

        ' Enumerate children of the child visual object.
        EnumVisual(childVisual)
    Next i
End Sub

Dans la plupart des cas, l’arborescence logique est une représentation plus utile des éléments dans une application WPF. Même si vous ne modifiez pas directement l’arborescence logique, cette vue de l’application est utile pour comprendre l’héritage de propriété et le routage d’événement. Contrairement à l’arborescence visuelle, l’arborescence logique peut représenter des objets de données non visuels, tels que ListItem. Pour plus d’informations sur l’arborescence logique, consultez Arborescences dans WPF.

La VisualTreeHelper classe fournit des méthodes pour renvoyer le rectangle englobant des objets visuels. Vous pouvez retourner le rectangle englobant d’un objet visuel en appelant GetContentBounds. Vous pouvez retourner le rectangle englobant de tous les descendants d’un objet visuel, y compris l’objet visuel lui-même, en appelant GetDescendantBounds. Le code suivant montre comment vous pourriez calculer le rectangle englobant d’un objet visuel et de tous ses descendants.

// Return the bounding rectangle of the parent visual object and all of its descendants.
Rect rectBounds = VisualTreeHelper.GetDescendantBounds(parentVisual);
' Return the bounding rectangle of the parent visual object and all of its descendants.
Dim rectBounds As Rect = VisualTreeHelper.GetDescendantBounds(parentVisual)

Voir aussi