{"id":328,"date":"2012-03-11T00:28:23","date_gmt":"2012-03-10T13:28:23","guid":{"rendered":"http:\/\/blog.quppa.net\/?p=328"},"modified":"2012-03-11T00:28:23","modified_gmt":"2012-03-10T13:28:23","slug":"wpf-using-system-colours-in-animations","status":"publish","type":"post","link":"https:\/\/www.quppa.net\/blog\/2012\/03\/11\/wpf-using-system-colours-in-animations\/","title":{"rendered":"WPF: Using System Colours in Animations"},"content":{"rendered":"<p>WPF provides access to the <a title=\"Windows System Colours Reference\" href=\"http:\/\/www.quppa.net\/syscol\/\">Windows system colours<\/a> through the <a title=\"MSDN: System.Windows.SystemColors\" href=\"http:\/\/msdn.microsoft.com\/en-us\/library\/system.windows.systemcolors.aspx\">System.Windows.SystemColors class<\/a>. As the MSDN documentation indicates, it\u2019s possible to bind to these colours dynamically using the *Key resources, so when the system colours change, so will the appearance of your application.<\/p>\n<p>This code will set the colour of a TextBlock to the \u2018GrayText\u2019 system colour, and will change automatically if the user switches themes:<\/p>\n<pre class=\"lang:xaml decode:true \">&lt;TextBlock Foreground=&quot;{DynamicResource {x:Static SystemColors.GrayTextBrushKey}}&quot;&gt;\n  Text\n&lt;\/TextBlock&gt;<\/pre>\n<p>In many cases, there\u2019s no reason not to bind dynamically. Problems arise with animations, however. From <a title=\"MSDN: Storyboards Overview\" href=\"http:\/\/msdn.microsoft.com\/en-us\/library\/ms742868.aspx\">MSDN<\/a>:<\/p>\n<blockquote>\n<p>You can&#8217;t use dynamic resource references or data binding expressions to set Storyboard or animation property values. That&#8217;s because everything inside a ControlTemplate must be thread-safe, and the timing system must Freeze Storyboard objects to make them thread-safe. A Storyboard cannot be frozen if it or its child timelines contain dynamic resource references or data binding expressions.<\/p>\n<\/blockquote>\n<p>This means that you\u2019re stuck using static references to system colours in your animation storyboards \u2013 if the user changes the system colours while your application is running, your storyboards won\u2019t update automatically. Worst-case scenario, you might end up with unreadable text.<\/p>\n<p>I don\u2019t think there are any workarounds that don\u2019t involve reloading windows and\/or resource dictionaries (depending on where the style code is located). Reloading a window is easy enough \u2013 just be careful if you\u2019re closing your application\u2019s last window: the program will shut down if there are no remaining references to any windows.<\/p>\n<p>The method for reloading a resource dictionary is a bit less obvious. It seems that XAML files accessed by their <a title=\"MSDN: Pack URIs in WPF\" href=\"http:\/\/msdn.microsoft.com\/en-us\/library\/aa970069.aspx\">pack URIs <\/a>are already compiled, so the system colours will be fixed in place once the program starts up. To get around this, change the build action for the XAML file containing the resource dictionary to \u2018Embedded Resource\u2019. You can then (re)build the resource dictionary as you please using XamlReader:<\/p>\n<pre class=\"lang:c# decode:true \">ResourceDictionary resdic;\nusing (XmlTextReader xr = new XmlTextReader(Assembly.GetExecutingAssembly().GetManifestResourceStream(&quot;ProjectNameSpace.MyResourceDictionary.xaml&quot;)))\n  resdic = (ResourceDictionary)XamlReader.Load(xr);<\/pre>\n<p>Remove the old resource dictionary from your application\u2019s merged resource dictionaries, then add the new one.<\/p>\n<p>Creating a new resource dictionary like this seems to be fairly slow, so try to avoid doing it on a regular basis. To tell when the Windows theme or system colours have changed, you\u2019ll need to listen for the window messages <a title=\"MSDN: WM_THEMECHANGED\" href=\"http:\/\/msdn.microsoft.com\/en-us\/library\/windows\/desktop\/ms632650.aspx\">WM_THEMECHANGED<\/a> and <a title=\"MSDN: WM_SYSCOLORCHANGE\" href=\"http:\/\/msdn.microsoft.com\/en-us\/library\/dd145223.aspx\">WM_SYSCOLORCHANGE<\/a>. See <a title=\"Quppa&#39;s Blog: Windows 7-style Notification Area Applications in WPF: Part 1 - Removing Resize\" href=\"https:\/\/www.quppa.net\/blog\/2010\/12\/07\/windows-7-style-notification-area-applications-in-wpf-part-1-removing-resize\/\">this post<\/a> for information about listening for window messages in WPF.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>WPF provides access to the Windows system colours through the System.Windows.SystemColors class. As the MSDN documentation indicates, it\u2019s possible to bind to these colours dynamically using the *Key resources, so when the system colours change, so will the appearance of your application. This code will set the colour of a TextBlock to the \u2018GrayText\u2019 system &hellip; <a href=\"https:\/\/www.quppa.net\/blog\/2012\/03\/11\/wpf-using-system-colours-in-animations\/\" class=\"more-link\">Continue reading<span class=\"screen-reader-text\"> &#8220;WPF: Using System Colours in Animations&#8221;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[6,9],"tags":[21,34,117,142,185],"class_list":["post-328","post","type-post","status-publish","format-standard","hentry","category-programming","category-windows","tag-binding","tag-colour","tag-resourcedictionary","tag-style","tag-wpf"],"_links":{"self":[{"href":"https:\/\/www.quppa.net\/blog\/wp-json\/wp\/v2\/posts\/328","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.quppa.net\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.quppa.net\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.quppa.net\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.quppa.net\/blog\/wp-json\/wp\/v2\/comments?post=328"}],"version-history":[{"count":0,"href":"https:\/\/www.quppa.net\/blog\/wp-json\/wp\/v2\/posts\/328\/revisions"}],"wp:attachment":[{"href":"https:\/\/www.quppa.net\/blog\/wp-json\/wp\/v2\/media?parent=328"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.quppa.net\/blog\/wp-json\/wp\/v2\/categories?post=328"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.quppa.net\/blog\/wp-json\/wp\/v2\/tags?post=328"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}