none
WPFのStaticResourceとDynamicResourceの違い

    質問

  • WPFのStaticResourceとDynamicResourceの違いがどうしても分かりません。どなたかご教授頂けますでしょうか。また、この辺りを学習できるサイトを教えていただけると有難いのですが、いかがでしょうか?
    2014年12月29日 11:40

回答

  • どちらもリソースを参照しますが、リソースが変更された時の挙動に違いがあります。

    StaticResourceでは対象のプロパティに1度だけ設定が行われます。
    DynamicResourceはリソースの内容が変更されたら対象のプロパティも変更されます。

    単純な例としては

    <Window x:Class="WpfApplication1.MainWindow" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Title="MainWindow" Height="350" Width="525">
        <Window.Resources>
            <SolidColorBrush x:Key="testBrush" Color="Red"/>
        </Window.Resources>
        <DockPanel>
            <Button DockPanel.Dock="Top" Content="Test" Click="TestButton_Click" />
            <UniformGrid Columns="2">
                <Grid Background="{StaticResource ResourceKey=testBrush}" Margin="10">
                    <TextBlock Text="StaticResource" />
                </Grid>
    
                <Grid Background="{DynamicResource ResourceKey=testBrush}" Margin="10">
                    <TextBlock Text="DynamicResource" />
                </Grid>
            </UniformGrid>
        </DockPanel>
    </Window>
    C#
    using System.Windows;
    using System.Windows.Media;
    namespace WpfApplication1
    {
        public partial class MainWindow : Window
        {
            public MainWindow()
            {
                InitializeComponent();
            }
    
            private void TestButton_Click(object sender, RoutedEventArgs e)
            {
                this.Resources["testBrush"] = new SolidColorBrush(Colors.Green);
            }
        }
    }
    VB
    Class MainWindow 
        Private Sub TestButton_Click(sender As Object, e As RoutedEventArgs)
            Me.Resources("testBrush") = New SolidColorBrush(Colors.Green)
        End Sub
    End Class
    この例では、最初にGridが生成される時点でのリソースは赤色であるため、どちらも背景色が赤色になります。

    そのあとで、リソースを変更するとDynamicResourceの方だけが変化を検出して緑色になります。
    StaticResourceでは最初に設定された背景色のままになります。

    以上のような違いがあるので、後からリソースが変更されても追従する必要がある場合のみDynamicResourceを使用します。
    必要ではないのにDynamicResoruceを使うと変化の監視をするための処理を無駄に行うことになります。


    個別に明示されていない限りgekkaがフォーラムに投稿したコードにはフォーラム使用条件に基づき「MICROSOFT LIMITED PUBLIC LICENSE」が適用されます。(かなり自由に使ってOK!)

    • 編集済み gekkaMVP 2014年12月29日 12:30
    • 回答の候補に設定 Tak1waMVP, Moderator 2014年12月29日 15:23
    • 回答としてマーク hotz07 2014年12月30日 2:05
    2014年12月29日 12:26

すべての返信

  • どちらもリソースを参照しますが、リソースが変更された時の挙動に違いがあります。

    StaticResourceでは対象のプロパティに1度だけ設定が行われます。
    DynamicResourceはリソースの内容が変更されたら対象のプロパティも変更されます。

    単純な例としては

    <Window x:Class="WpfApplication1.MainWindow" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Title="MainWindow" Height="350" Width="525">
        <Window.Resources>
            <SolidColorBrush x:Key="testBrush" Color="Red"/>
        </Window.Resources>
        <DockPanel>
            <Button DockPanel.Dock="Top" Content="Test" Click="TestButton_Click" />
            <UniformGrid Columns="2">
                <Grid Background="{StaticResource ResourceKey=testBrush}" Margin="10">
                    <TextBlock Text="StaticResource" />
                </Grid>
    
                <Grid Background="{DynamicResource ResourceKey=testBrush}" Margin="10">
                    <TextBlock Text="DynamicResource" />
                </Grid>
            </UniformGrid>
        </DockPanel>
    </Window>
    C#
    using System.Windows;
    using System.Windows.Media;
    namespace WpfApplication1
    {
        public partial class MainWindow : Window
        {
            public MainWindow()
            {
                InitializeComponent();
            }
    
            private void TestButton_Click(object sender, RoutedEventArgs e)
            {
                this.Resources["testBrush"] = new SolidColorBrush(Colors.Green);
            }
        }
    }
    VB
    Class MainWindow 
        Private Sub TestButton_Click(sender As Object, e As RoutedEventArgs)
            Me.Resources("testBrush") = New SolidColorBrush(Colors.Green)
        End Sub
    End Class
    この例では、最初にGridが生成される時点でのリソースは赤色であるため、どちらも背景色が赤色になります。

    そのあとで、リソースを変更するとDynamicResourceの方だけが変化を検出して緑色になります。
    StaticResourceでは最初に設定された背景色のままになります。

    以上のような違いがあるので、後からリソースが変更されても追従する必要がある場合のみDynamicResourceを使用します。
    必要ではないのにDynamicResoruceを使うと変化の監視をするための処理を無駄に行うことになります。


    個別に明示されていない限りgekkaがフォーラムに投稿したコードにはフォーラム使用条件に基づき「MICROSOFT LIMITED PUBLIC LICENSE」が適用されます。(かなり自由に使ってOK!)

    • 編集済み gekkaMVP 2014年12月29日 12:30
    • 回答の候補に設定 Tak1waMVP, Moderator 2014年12月29日 15:23
    • 回答としてマーク hotz07 2014年12月30日 2:05
    2014年12月29日 12:26
  • サイトを探してみましたが、日本語ではあまりないようですね。しかし、以下がわかりやすそうでした。

    WPFのStaticResourceとDynamicResourceの違い
    http://tocsworld.wordpress.com/2014/06/26/wpf%E3%81%AEstaticresource%E3%81%A8dynamicresource%E3%81%AE%E9%81%95%E3%81%84/

    英語だと割とたくさん見つかります。参考までに以下をご紹介しておきます。

    WPF: StaticResource vs. DynamicResource
    http://www.codeproject.com/Articles/393086/WPF-StaticResource-vs-DynamicResource

    WPF StaticResource and DynamicResource Examples and Explanations
    http://www.tuicool.com/articles/JJ3MFvi

    StaticResource, DynamicResource, x:Static – what’s all this about?
    http://khason.net/blog/staticresource-dynamicresource-xstatic-whats-all-this-about/


    ★良い回答には回答済みマークを付けよう! わんくま同盟 MVP - Visual C# http://d.hatena.ne.jp/trapemiya/

    2014年12月29日 12:39
    モデレータ
  • 確かに英語で検索するとたくさんヒットしますね。英語をもう少し勉強してみます。ありがとうございました。
    2014年12月30日 2:09
  • 勉強になりました。ありがとうございました。
    2014年12月30日 2:10