499 votes

Quelle est la différence entre StaticResource et DynamicResource dans WPF ?

Lorsque l'on utilise des ressources telles que des brosses, des modèles et des styles dans WPF, elles peuvent être spécifiées soit comme StaticResources

<Rectangle Fill="{StaticResource MyBrush}" />

ou comme une DynamicResource

<ItemsControl ItemTemplate="{DynamicResource MyItemTemplate}"  />

La plupart du temps (toujours ?), une seule fonctionne et l'autre lève une exception pendant l'exécution. Mais j'aimerais savoir pourquoi :

  • Quelle est la principale différence ? Comme les implications en termes de mémoire ou de performances
  • Y a-t-il des règles dans WPF comme "les brosses sont toujours statiques" et "les modèles sont toujours dynamiques", etc.

I supposez le choix entre statique et dynamique n'est pas aussi arbitraire qu'il y paraît... mais je ne vois pas le schéma.

490voto

Phil Wright Points 11696

A Ressource statique sera résolu et attribué à la propriété pendant le chargement du XAML, qui a lieu avant l'exécution de l'application. Elle ne sera affectée qu'une seule fois et toute modification du dictionnaire des ressources sera ignorée.

A DynamicResource affecte un objet Expression à la propriété pendant le chargement, mais ne recherche pas réellement la ressource avant le moment de l'exécution, lorsque la valeur est demandée à l'objet Expression. Cela reporte la recherche de la ressource jusqu'à ce qu'elle soit nécessaire au moment de l'exécution. Un bon exemple serait une référence directe à une ressource définie plus tard dans le XAML. Un autre exemple est une ressource qui n'existera même pas avant l'exécution. Elle mettra à jour la cible si le dictionnaire de la ressource source est modifié.

126voto

Akshay J Points 1974

J'ai également été confus à leur sujet. Voir cet exemple ci-dessous :

<Window x:Class="WpfApplicationWPF.CommandsWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="CommandsWindow" Height="300" Width="300">

    <StackPanel>
        <Button Name="ButtonNew" 
                Click="ButtonNew_Click" 
                Background="{DynamicResource PinkBrush}">NEW</Button>
        <Image Name="ImageNew" 
               Source="pack://application:,,,/images/winter.jpg"></Image>
    </StackPanel>

    <Window.Background>
        <DynamicResource ResourceKey="PinkBrush"></DynamicResource>
    </Window.Background>

</Window>

Ici, j'ai utilisé une ressource dynamique pour le bouton et la fenêtre et je ne l'ai déclaré nulle part. Au moment de l'exécution, le ResourceDictionary de la hiérarchie sera vérifié. Comme je ne l'ai pas défini, je suppose que la valeur par défaut sera utilisée.

Si j'ajoute le code ci-dessous à l'événement click du bouton, puisqu'ils utilisent DynamicResource, l'arrière-plan sera mis à jour en conséquence.

private void ButtonNew_Click(object sender, RoutedEventArgs e)
{
    this.Resources.Add(  "PinkBrush"
                         ,new SolidColorBrush(SystemColors.DesktopColor)
                       );
}

S'ils avaient utilisé StaticResource :

  • La ressource doit être déclarée dans XAML.
  • Et cela aussi "avant" qu'ils ne soient utilisés.

J'espère avoir dissipé toute confusion.

35voto

Afshin Points 210

StaticResource sera résolu lors de la construction de l'objet.
DynamicResource sera évalué et résolu chaque fois que le contrôle aura besoin de la ressource.

30voto

Les ressources logiques vous permettent de définir des objets en XAML, qui ne font pas partie de l'arbre visuel mais peuvent être utilisés dans votre interface utilisateur. L'un des exemples de ressource logique est le pinceau, qui est utilisé pour fournir un schéma de couleurs. En général, ces objets sont définis comme des ressources, qui sont utilisées par plusieurs éléments des applications.

<Window.Resources>
    <RadialGradientBrush x:Key="myGradientBrush">
        <GradientStop Color="Green" Offset="0"/>
        <GradientStop Color="Blue" Offset="2"/>
    </RadialGradientBrush>
</Window.Resources>

Maintenant, la ressource déclarée ci-dessus peut être utilisée comme ressource statique ou dynamique. Un point à retenir est que, lors de l'utilisation de ressources statiques, elles doivent d'abord être définies dans le code XAML, avant de pouvoir être référencées. Les ressources statiques et dynamiques peuvent être utilisées comme suit :

<Grid Background="{StaticResource myGradientBrush}"></Grid>

ou :

<Grid Background="{DynamicResource myGradientBrush}"></Grid>

La différence entre StaticResource et DynamicResource réside dans la manière dont les ressources sont récupérées par les éléments de référencement. Les StaticResource sont récupérées une seule fois par l'élément de référencement et utilisées pendant toute la durée de vie de la ressource. En revanche, les DynamicResource sont acquises chaque fois que l'objet référencé est utilisé.

En simplifiant, si la propriété de couleur de RadialGradientBrush est changée dans le code en Orange et Rose, alors elle se reflétera sur les éléments seulement quand la ressource est utilisée comme DynamicResource. Voici le code pour changer la ressource dans le code :

RadialGradientBrush radialGradientBrush =
    new RadialGradientBrush(Colors.Orange, Colors.Pink);
this.Resources["myGradientBrush"] = radialGradientBrush;

Le démérite de DynamicResource est qu'il réduit les performances de l'application car les ressources sont récupérées à chaque fois qu'elles sont utilisées. La meilleure pratique consiste à utiliser StaticResource jusqu'à ce qu'il y ait une raison spécifique d'utiliser DynamicResource.

Source :
WPF : StaticResource vs. DynamicResource

17voto

CharithJ Points 15364

Quelle est la principale différence ? Comme les implications en termes de mémoire ou de performances

La différence entre les ressources statiques et dynamiques intervient lorsque l'objet sous-jacent change. Si votre brosse définie dans la collection Ressources a été accédée dans le code et définie sur une instance d'objet différente, Rectangle ne détectera pas ce changement.

Ressources statiques récupérées une fois par l'élément de référencement et utilisées pendant la durée de vie des ressources. Les ressources dynamiques, quant à elles, sont récupérées chaque fois qu'elles sont utilisées.

L'inconvénient des ressources dynamiques est qu'elles ont tendance à diminuer les performances des applications.

Y a-t-il des règles dans WPF comme "les brosses sont toujours statiques" et "les modèles sont toujours dynamiques", etc.

La meilleure pratique consiste à utiliser des ressources statiques, à moins qu'il n'y ait une raison spécifique pour laquelle vous souhaitez modifier dynamiquement une ressource dans le code sous-jacent. Un autre exemple de cas dans lequel vous voudriez ne pas utiliser de ressources dynamiques est celui de l'utilisation des SystemBrushes, SystenFonts et System Parameters.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X