Accessing TintedResourceDictionary in XAML

Docking/MDI for WPF Forum

Posted 9 years ago by Alexandre De Riemaecker
Version: 10.1.0523
Avatar
We have a nested DockSite for which I create a TintedDictionary of the current theme. The color is the TabTintColor of the DocumentWindow the Docksite is nested in. Within this nested DockSite, I'd like to access some Brushes from this TintedDictionary via DynamicResource. How can I accomplish this? I use the following code:
  private void CreateThemeDictionary()
        {
            m_ThemeName = String.Format("Theme{0}{1}{2}", this.TabTintColor.R, this.TabTintColor.G, this.TabTintColor.B);

            try
            {
                if (!ThemeManager.IsThemeRegistered(m_ThemeName))
                {
                    ResourceDictionary _dockingResourceDictionary = ThemeManager.GetResourceDictionary(ThemeManager.CurrentTheme, DockingCommonDictionary.GroupName);
                    TintedResourceDictionary _tintedDictionary = new TintedResourceDictionary(_dockingResourceDictionary, this.TabTintColor);

                    ThemeManager.Register(m_ThemeName, DockingCommonDictionary.GroupName, _tintedDictionary);
                }

                this.Frame.LoadCompleted += new LoadCompletedEventHandler((object sender, NavigationEventArgs e) =>
                {
                    ThemeManager.SetTheme((DependencyObject)this.Page.NestedDockSite, m_ThemeName);
                });

            }

Comments (3)

Posted 9 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
Hi Alexandre,

Before we get to your question, in general you should only use change the theme on a particular element for testing (i.e. use SetTheme). Normally, you should just set the ThemeManager.CurrentTheme, which is applied application wide.

When you use SetTheme, then resource dictionary will be merged in the DockSite.Resources. If you use ThemeManager.CurrentTheme, then the resource dictionary will be loaded into the Application.Resources. So as long as you know the key, you can simply use "{DynamicResource KnownKey}" in your XAML. Then anything inside the DockSite (or in your application when using CurrentTheme) should be able to find it.

If you want to set a property to DynamicResource in code-behind, you can use SetResourceReference with the property and resource key.


Actipro Software Support

Posted 9 years ago by Alexandre De Riemaecker
Avatar
I understand that I shouldn't use SetTheme. How can I fulfill the following requirements without using SetTheme?

- Create TintedDictionary from the current Theme
- Use it on a nested DockSite without replacing the current theme
- Make the Tinted Theme resources XAML-accessible for everything inside the nested DockSite

Note: I doesn't really matter to us if the Tinted resources can be accessed with the same DynamicResource string we find in the Actipro Theme Browser.
Posted 9 years ago by Actipro Software Support - Cleveland, OH, USA
Avatar
Hi Alexandre,

When using registered themes and SetTheme, you may run into the case where your DockSite won't be garbage collected. There are times where the WPF ResourceDictionary will retain references to any "owner" objects, in this case the DockSite. Since the ResourceDictionary is registered with the ThemeManager, it will be retained until you unregister it or the application is closed. So if your nested DockSite is created/destroyed through out the life of your application, you may "leak" DockSite (and anything it references) instances. If you don't create/destroy nested DockSites then you probably won't experience a "leak".

If you need to create/destroy the nested DockSite, then you may try simply setting the DockSite.Resources to your _tintedDictionary. Alternatively, you can call DockSite.ClearValue(ThemeManager.ThemeProperty) before you "destroy" it. In either case, I'd recommend you run a memory profiler to verify the workaround and the DockSite instances are collected.

Hope that clears things up.


Actipro Software Support

The latest build of this product (v2019.1 build 0681) was released 1 month ago, which was after the last post in this thread.

Add Comment

Please log in to a validated account to post comments.