From c8bacc12ebd4083b07282b57d951bf87e8995ab0 Mon Sep 17 00:00:00 2001 From: YeongJong Lee Date: Tue, 22 Dec 2020 13:00:32 +0900 Subject: [PATCH] [NUI] rewrite theme resource (#2405) Theme resources would only be updated by Tizen Theme Manager. So, this patch remove xaml support for theme resources. --- src/Tizen.NUI.Components/Theme/DefaultTheme.cs | 190 ++++++++++++++------- .../src/internal/Theme/DefaultTheme.cs | 8 +- src/Tizen.NUI/src/public/Theme/DefaultTheme.cs | 9 +- src/Tizen.NUI/src/public/Theme/Theme.cs | 157 +++++++++-------- src/Tizen.NUI/src/public/Theme/ThemeManager.cs | 27 ++- .../Samples/ThemeResourceSample.cs | 31 ++-- .../Tizen.NUI.Samples/Samples/res/SampleTheme.xaml | 16 -- .../Samples/res/SampleThemeResourceDark.xaml | 8 - .../Samples/res/SampleThemeResourceDefault.xaml | 8 - 9 files changed, 271 insertions(+), 183 deletions(-) delete mode 100644 test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/res/SampleTheme.xaml delete mode 100644 test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/res/SampleThemeResourceDark.xaml delete mode 100644 test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/res/SampleThemeResourceDefault.xaml diff --git a/src/Tizen.NUI.Components/Theme/DefaultTheme.cs b/src/Tizen.NUI.Components/Theme/DefaultTheme.cs index 6ba08b3..cf75992 100644 --- a/src/Tizen.NUI.Components/Theme/DefaultTheme.cs +++ b/src/Tizen.NUI.Components/Theme/DefaultTheme.cs @@ -1,4 +1,4 @@ -/* +/* * Copyright(c) 2020 Samsung Electronics Co., Ltd. * * Licensed under the Apache License, Version 2.0 (the "License"); @@ -16,34 +16,109 @@ */ #if !PROFILE_WEARABLE +using System.Collections.Generic; using Tizen.NUI.BaseComponents; +using Tizen.NUI.Binding; namespace Tizen.NUI.Components { // It is a C# version of res/Tizen.NUI.Components_Tizen.NUI.Theme.Common.xaml internal class DefaultThemeCreator : IThemeCreator { - public Theme Create() + public ResourceDictionary CreateThemeResource() => new ResourceDictionary() + { + ["ButtonBackgroundColorNormal"] = new Color(0.88f, 0.88f, 0.88f, 1), + ["ButtonBackgroundColorPressed"] = new Color(0.77f, 0.77f, 0.77f, 1), + ["ButtonBackgroundColorDisabled"] = new Color(0.88f, 0.88f, 0.88f, 1), + ["ButtonTextColorNormal"] = new Color(0.22f, 0.22f, 0.22f, 1), + ["ButtonTextColorPressed"] = new Color(0.11f, 0.11f, 0.11f, 1), + ["ButtonTextColorDisabled"] = new Color(0.66f, 0.66f, 0.66f, 1), + ["CheckBoxIconBackgroundImagePressed"] = FrameworkInformation.ResourcePath + "nui_component_default_checkbox_bg_p.png", + ["CheckBoxIconBackgroundImageSelected"] = FrameworkInformation.ResourcePath + "nui_component_default_checkbox_bg_p.png", + ["CheckBoxIconBackgroundImageOther"] = FrameworkInformation.ResourcePath + "nui_component_default_checkbox_bg_n.png", + ["CheckBoxIconImageResourceUrlPressed"] = "", + ["CheckBoxIconImageResourceUrlSelected"] = FrameworkInformation.ResourcePath + "nui_component_default_checkbox_s.png", + ["CheckBoxIconImageResourceUrlOther"] = "", + ["CheckBoxTextColorNormal"] = new Color(0.22f, 0.22f, 0.22f, 1), + ["CheckBoxTextColorPressed"] = new Color(0.11f, 0.11f, 0.11f, 1), + ["CheckBoxTextColorDisabled"] = new Color(0.66f, 0.66f, 0.66f, 1), + ["DropDownBackgroundImagePressed"] = FrameworkInformation.ResourcePath + "nui_component_default_checkbox_bg_p.png", + ["DropDownBackgroundImageOther"] = FrameworkInformation.ResourcePath + "nui_component_default_checkbox_bg_n.png", + ["DropDownIconImageResourceUrl"] = FrameworkInformation.ResourcePath + "nui_component_default_dropdown_button_icon.png", + ["DropDownListBackgroundImageResourceUrl"] = FrameworkInformation.ResourcePath + "nui_component_default_dropdown_list_bg.png", + ["DropDownDataItemBackgroundColorPressed"] = new Color(0.05f, 0.63f, 0.9f, 1), + ["DropDownDataItemBackgroundColorSelected"] = new Color(0.8f, 0.8f, 0.8f, 1), + ["DropDownDataItemBackgroundColorNormal"] = new Color(1, 1, 1, 1), + ["PopupBackgroundColor"] = new Color(0.9f, 0.9f, 0.9f, 1), + ["PopupImageShadowUrl"] = FrameworkInformation.ResourcePath + "nui_component_default_popup_shadow.png", + ["PopupButtonBackgroundColorNormal"] = new Color(1, 1, 1, 1), + ["PopupButtonBackgroundColorPressed"] = new Color(1, 1, 1, 0.5f), + ["PopupButtonOverlayBackgroundColorNormal"] = new Color(1, 1, 1, 1), + ["PopupButtonOverlayBackgroundColorPressed"] = new Color(0, 0, 0, 0.1f), + ["PopupButtonOverlayBackgroundColorSelected"] = new Color(1, 1, 1, 1), + ["PopupButtonTextColor"] = new Color(0.05f, 0.63f, 0.9f, 1), + ["ProgressTrackBackgroundColor"] = new Color(0, 0, 0, 0.1f), + ["ProgressBufferBackgroundColor"] = new Color(0.05f, 0.63f, 0.9f, 0.3f), + ["ProgressProgressBackgroundColor"] = new Color(0.05f, 0.63f, 0.9f, 1), + ["RadioButtonIconBackgroundImagePressed"] = FrameworkInformation.ResourcePath + "nui_component_default_radiobutton_p.png", + ["RadioButtonIconBackgroundImageSelected"] = FrameworkInformation.ResourcePath + "nui_component_default_radiobutton_s.png", + ["RadioButtonIconBackgroundImageOther"] = FrameworkInformation.ResourcePath + "nui_component_default_radiobutton_n.png", + ["RadioButtonTextColorNormal"] = new Color(0.22f, 0.22f, 0.22f, 1), + ["RadioButtonTextColorPressed"] = new Color(0.11f, 0.11f, 0.11f, 1), + ["RadioButtonTextColorDisabled"] = new Color(0.66f, 0.66f, 0.66f, 1), + ["SliderTrackColor"] = new Color(0, 0, 0, 0.1f), + ["SliderProgressColor"] = new Color(0.5f, 0.63f, 0.9f, 1), + ["SliderThumbImageResourceUrl"] = FrameworkInformation.ResourcePath + "nui_component_default_slider_thumb_n.png", + ["SliderThumbBackgroundImageNormal"] = FrameworkInformation.ResourcePath + "nui_component_default_slider_thumb_bg_p.png", + ["SliderThumbBackgroundImagePressed"] = FrameworkInformation.ResourcePath + "nui_component_default_slider_thumb_bg_p.png", + ["SwitchTrackImageResourceUrlNormal"] = FrameworkInformation.ResourcePath + "nui_component_default_switch_track_n.png", + ["SwitchTrackImageResourceUrlSelected"] = FrameworkInformation.ResourcePath + "nui_component_default_switch_track_s.png", + ["SwitchTrackImageResourceUrlDisabled"] = FrameworkInformation.ResourcePath + "nui_component_default_switch_track_d.png", + ["SwitchTrackImageResourceUrlDisabledSelected"] = FrameworkInformation.ResourcePath + "nui_component_default_switch_track_ds.png", + ["SwitchThumbImageResourceUrlNormal"] = FrameworkInformation.ResourcePath + "nui_component_default_switch_thumb_n.png", + ["SwitchThumbImageResourceUrlDisabled"] = FrameworkInformation.ResourcePath + "nui_component_default_switch_thumb_d.png", + ["SwitchThumbImageResourceUrlSelected"] = FrameworkInformation.ResourcePath + "nui_component_default_switch_thumb_n.png", + ["SwitchTextColorNormal"] = new Color(0.22f, 0.22f, 0.22f, 1), + ["SwitchTextColorPressed"] = new Color(0.11f, 0.11f, 0.11f, 1), + ["SwitchTextColorDisabled"] = new Color(0.66f, 0.66f, 0.66f, 1), + ["TabBackgroundColor"] = Color.Yellow, + ["TabUnderLineBackgroundColor"] = new Color(0.05f, 0.63f, 0.9f, 1.0f), + ["TabTextColorNormal"] = Color.Black, + ["TabTextColorSelected"] = new Color(0.05f, 0.63f, 0.9f, 1), + ["ToastBackgroundColor"] = new Color(0, 0, 0, 0.8f), + ["PaginationIndicatorImageUrlNormal"] = FrameworkInformation.ResourcePath + "nui_component_default_pagination_normal_dot.png", + ["PaginationIndicatorImageUrlSelected"] = FrameworkInformation.ResourcePath + "nui_component_default_pagination_focus_dot.png", + ["ScrollbarTrackColor"] = new Color(1, 1, 1, 0.15f), + ["ScrollbarThumbColor"] = new Color(0.6f, 0.6f, 0.6f, 1.0f), + }; + + public Theme Create() => Create(null); + + public Theme Create(IEnumerable> changedResources) { var theme = new Theme() { Id = "Tizen.NUI.Theme.Common" }; + theme.SetChangedResources(changedResources); + theme.Resources = CreateThemeResource(); + theme.OnThemeResourcesChanged(); + theme.AddStyleWithoutClone("Tizen.NUI.Components.Button", new ButtonStyle() { Size = new Size(100, 45), BackgroundColor = new Selector() { - Normal = new Color(0.88f, 0.88f, 0.88f, 1), - Pressed = new Color(0.77f, 0.77f, 0.77f, 1), - Disabled = new Color(0.88f, 0.88f, 0.88f, 1), + Normal = (Color)theme.Resources["ButtonBackgroundColorNormal"], + Pressed = (Color)theme.Resources["ButtonBackgroundColorPressed"], + Disabled = (Color)theme.Resources["ButtonBackgroundColorDisabled"], }, Text = new TextLabelStyle() { PointSize = 12, TextColor = new Selector() { - Normal = new Color(0.22f, 0.22f, 0.22f, 1), - Pressed = new Color(0.11f, 0.11f, 0.11f, 1), - Disabled = new Color(0.66f, 0.66f, 0.66f, 1), + Normal = (Color)theme.Resources["ButtonTextColorNormal"], + Pressed = (Color)theme.Resources["ButtonTextColorPressed"], + Disabled = (Color)theme.Resources["ButtonTextColorDisabled"], } } }); @@ -61,15 +136,15 @@ namespace Tizen.NUI.Components }, BackgroundImage = new Selector() { - Pressed = FrameworkInformation.ResourcePath + "nui_component_default_checkbox_bg_p.png", - Selected = FrameworkInformation.ResourcePath + "nui_component_default_checkbox_bg_p.png", - Other = FrameworkInformation.ResourcePath + "nui_component_default_checkbox_bg_n.png", + Pressed = (string)theme.Resources["CheckBoxIconBackgroundImagePressed"], + Selected = (string)theme.Resources["CheckBoxIconBackgroundImageSelected"], + Other = (string)theme.Resources["CheckBoxIconBackgroundImageOther"], }, ResourceUrl = new Selector() { - Pressed = "", - Selected = FrameworkInformation.ResourcePath + "nui_component_default_checkbox_s.png", - Other = "", + Pressed = (string)theme.Resources["CheckBoxIconImageResourceUrlPressed"], + Selected = (string)theme.Resources["CheckBoxIconImageResourceUrlSelected"], + Other = (string)theme.Resources["CheckBoxIconImageResourceUrlOther"], }, }, Text = new TextLabelStyle() @@ -77,9 +152,9 @@ namespace Tizen.NUI.Components PointSize = 12, TextColor = new Selector() { - Normal = new Color(0.22f, 0.22f, 0.22f, 1), - Pressed = new Color(0.11f, 0.11f, 0.11f, 1), - Disabled = new Color(0.66f, 0.66f, 0.66f, 1), + Normal = (Color)theme.Resources["CheckBoxTextColorNormal"], + Pressed = (Color)theme.Resources["CheckBoxTextColorPressed"], + Disabled = (Color)theme.Resources["CheckBoxTextColorDisabled"], } } }); @@ -87,10 +162,10 @@ namespace Tizen.NUI.Components theme.AddStyleWithoutClone("Tizen.NUI.Components.Popup", new PopupStyle() { Size = new Size(500, 280), - BackgroundColor = new Color(0.9f, 0.9f, 0.9f, 1), + BackgroundColor = (Color)theme.Resources["PopupBackgroundColor"], ImageShadow = new ImageShadow() { - Url = FrameworkInformation.ResourcePath + "nui_component_default_popup_shadow.png", + Url = (string)theme.Resources["PopupImageShadowUrl"], Border = new Rectangle(24, 24, 24, 24), Extents = new Vector2(48, 48) }, @@ -104,20 +179,21 @@ namespace Tizen.NUI.Components Size = new Size(0, 80), BackgroundColor = new Selector() { - Normal = new Color(1, 1, 1, 1), - Pressed = new Color(1, 1, 1, 0.5f), + Normal = (Color)theme.Resources["PopupButtonBackgroundColorNormal"], + Pressed = (Color)theme.Resources["PopupButtonBackgroundColorPressed"], }, Overlay = new ImageViewStyle() { BackgroundColor = new Selector() { - Pressed = new Color(0, 0, 0, 0.1f), - Other = new Color(1, 1, 1, 1), + Normal = (Color)theme.Resources["PopupButtonOverlayBackgroundColorNormal"], + Pressed = (Color)theme.Resources["PopupButtonOverlayBackgroundColorPressed"], + Other = (Color)theme.Resources["PopupButtonOverlayBackgroundColorSelected"], }, }, Text = new TextLabelStyle() { - TextColor = new Color(0.05f, 0.63f, 0.9f, 1), + TextColor = (Color)theme.Resources["PopupButtonTextColor"], } } }); @@ -127,15 +203,15 @@ namespace Tizen.NUI.Components Size = new Size(200, 5), Track = new ImageViewStyle() { - BackgroundColor = new Color(0, 0, 0, 0.1f), + BackgroundColor = (Color)theme.Resources["ProgressTrackBackgroundColor"], }, Buffer = new ImageViewStyle() { - BackgroundColor = new Color(0.05f, 0.63f, 0.9f, 0.3f), + BackgroundColor = (Color)theme.Resources["ProgressBufferBackgroundColor"], }, Progress = new ImageViewStyle() { - BackgroundColor = new Color(0.05f, 0.63f, 0.9f, 1), + BackgroundColor = (Color)theme.Resources["ProgressProgressBackgroundColor"], }, }); @@ -152,9 +228,9 @@ namespace Tizen.NUI.Components }, BackgroundImage = new Selector() { - Pressed = FrameworkInformation.ResourcePath + "nui_component_default_radiobutton_p.png", - Selected = FrameworkInformation.ResourcePath + "nui_component_default_radiobutton_s.png", - Other = FrameworkInformation.ResourcePath + "nui_component_default_radiobutton_n.png", + Pressed = (string)theme.Resources["RadioButtonIconBackgroundImagePressed"], + Selected = (string)theme.Resources["RadioButtonIconBackgroundImageSelected"], + Other = (string)theme.Resources["RadioButtonIconBackgroundImageOther"], } }, Text = new TextLabelStyle() @@ -162,9 +238,9 @@ namespace Tizen.NUI.Components PointSize = 12, TextColor = new Selector() { - Normal = new Color(0.22f, 0.22f, 0.22f, 1), - Pressed = new Color(0.11f, 0.11f, 0.11f, 1), - Disabled = new Color(0.66f, 0.66f, 0.66f, 1), + Normal = (Color)theme.Resources["RadioButtonTextColorNormal"], + Pressed = (Color)theme.Resources["RadioButtonTextColorPressed"], + Disabled = (Color)theme.Resources["RadioButtonTextColorDisabled"], } } }); @@ -175,20 +251,20 @@ namespace Tizen.NUI.Components TrackThickness = 5, Track = new ImageViewStyle() { - BackgroundColor = new Color(0, 0, 0, 0.1f), + BackgroundColor = (Color)theme.Resources["SliderTrackColor"], }, Progress = new ImageViewStyle() { - BackgroundColor = new Color(0.05f, 0.63f, 0.9f, 1), + BackgroundColor = (Color)theme.Resources["SliderProgressColor"], }, Thumb = new ImageViewStyle() { Size = new Size(50, 50), - ResourceUrl = FrameworkInformation.ResourcePath + "nui_component_default_slider_thumb_n.png", + ResourceUrl = (string)theme.Resources["SliderThumbImageResourceUrl"], BackgroundImage = new Selector() { - Normal = "", - Pressed = FrameworkInformation.ResourcePath + "nui_component_default_slider_thumb_bg_p.png", + Normal = (string)theme.Resources["SliderThumbBackgroundImageNormal"], + Pressed = (string)theme.Resources["SliderThumbBackgroundImagePressed"], } }, }); @@ -201,10 +277,10 @@ namespace Tizen.NUI.Components Size = new Size(96, 60), ResourceUrl = new Selector() { - Normal = FrameworkInformation.ResourcePath + "nui_component_default_switch_track_n.png", - Selected = FrameworkInformation.ResourcePath + "nui_component_default_switch_track_s.png", - Disabled = FrameworkInformation.ResourcePath + "nui_component_default_switch_track_d.png", - DisabledSelected = FrameworkInformation.ResourcePath + "nui_component_default_switch_track_ds.png", + Normal = (string)theme.Resources["SwitchTrackImageResourceUrlNormal"], + Selected = (string)theme.Resources["SwitchTrackImageResourceUrlSelected"], + Disabled = (string)theme.Resources["SwitchTrackImageResourceUrlDisabled"], + DisabledSelected = (string)theme.Resources["SwitchTrackImageResourceUrlDisabledSelected"], } }, Thumb = new ImageViewStyle() @@ -212,9 +288,9 @@ namespace Tizen.NUI.Components Size = new Size(60, 60), ResourceUrl = new Selector() { - Normal = FrameworkInformation.ResourcePath + "nui_component_default_switch_thumb_n.png", - Disabled = FrameworkInformation.ResourcePath + "nui_component_default_switch_thumb_d.png", - Selected = FrameworkInformation.ResourcePath + "nui_component_default_switch_thumb_n.png", + Normal = (string)theme.Resources["SwitchThumbImageResourceUrlNormal"], + Disabled = (string)theme.Resources["SwitchThumbImageResourceUrlDisabled"], + Selected = (string)theme.Resources["SwitchThumbImageResourceUrlSelected"], } }, Text = new TextLabelStyle() @@ -222,9 +298,9 @@ namespace Tizen.NUI.Components PointSize = 12, TextColor = new Selector() { - Normal = new Color(0.22f, 0.22f, 0.22f, 1), - Pressed = new Color(0.11f, 0.11f, 0.11f, 1), - Disabled = new Color(0.66f, 0.66f, 0.66f, 1), + Normal = (Color)theme.Resources["SwitchTextColorNormal"], + Pressed = (Color)theme.Resources["SwitchTextColorPressed"], + Disabled = (Color)theme.Resources["SwitchTextColorDisabled"], } } }); @@ -232,19 +308,19 @@ namespace Tizen.NUI.Components theme.AddStyleWithoutClone("Tizen.NUI.Components.Tab", new TabStyle() { Size = new Size(480, 80), - BackgroundColor = Color.Yellow, + BackgroundColor = (Color)theme.Resources["TabBackgroundColor"], UnderLine = new ViewStyle() { Size = new Size(0, 6), - BackgroundColor = new Color(0.05f, 0.63f, 0.9f, 1), + BackgroundColor = (Color)theme.Resources["TabUnderLineBackgroundColor"], }, Text = new TextLabelStyle() { PointSize = 16, TextColor = new Selector() { - Normal = Color.Black, - Selected = new Color(0.05f, 0.63f, 0.9f, 1), + Normal = (Color)theme.Resources["TabTextColorNormal"], + Selected = (Color)theme.Resources["TabTextColorSelected"], } } }); @@ -252,7 +328,7 @@ namespace Tizen.NUI.Components theme.AddStyleWithoutClone("Tizen.NUI.Components.Toast", new ToastStyle() { Size = new Size(480, 80), - BackgroundColor = new Color(0, 0, 0, 0.8f), + BackgroundColor = (Color)theme.Resources["ToastBackgroundColor"], Text = new TextLabelStyle() { Padding = new Extents(12, 12, 8, 8) @@ -268,8 +344,8 @@ namespace Tizen.NUI.Components { IndicatorImageUrl = new Selector() { - Normal = FrameworkInformation.ResourcePath + "nui_component_default_pagination_normal_dot.png", - Selected = FrameworkInformation.ResourcePath + "nui_component_default_pagination_focus_dot.png", + Normal = (string)theme.Resources["PaginationIndicatorImageUrlNormal"], + Selected = (string)theme.Resources["PaginationIndicatorImageUrlSelected"], } }); @@ -277,8 +353,8 @@ namespace Tizen.NUI.Components { TrackThickness = 6, ThumbThickness = 6, - TrackColor = new Color(1, 1, 1, 0.15f), - ThumbColor = new Color(0.6f, 0.6f, 0.6f, 1), + TrackColor = (Color)theme.Resources["ScrollbarTrackColor"], + ThumbColor = (Color)theme.Resources["ScrollbarThumbColor"], TrackPadding = 4 }); diff --git a/src/Tizen.NUI.Wearable/src/internal/Theme/DefaultTheme.cs b/src/Tizen.NUI.Wearable/src/internal/Theme/DefaultTheme.cs index 3a2560f..8eec8d6 100644 --- a/src/Tizen.NUI.Wearable/src/internal/Theme/DefaultTheme.cs +++ b/src/Tizen.NUI.Wearable/src/internal/Theme/DefaultTheme.cs @@ -1,4 +1,4 @@ -/* +/* * Copyright(c) 2020 Samsung Electronics Co., Ltd. * * Licensed under the Apache License, Version 2.0 (the "License"); @@ -15,14 +15,18 @@ * */ +using System.Collections.Generic; using Tizen.NUI.BaseComponents; namespace Tizen.NUI.Wearable { internal class DefaultThemeCreator : IThemeCreator { - public Theme Create() + public Theme Create() => Create(null); + + public Theme Create(IEnumerable> changedResources) { + _ = changedResources; var theme = new Theme() { Id = "Tizen.NUI.Theme.Common" }; theme.AddStyleWithoutClone("Tizen.NUI.Wearable.CircularPagination", new CircularPaginationStyle() diff --git a/src/Tizen.NUI/src/public/Theme/DefaultTheme.cs b/src/Tizen.NUI/src/public/Theme/DefaultTheme.cs index 6787990..0ecd0b2 100644 --- a/src/Tizen.NUI/src/public/Theme/DefaultTheme.cs +++ b/src/Tizen.NUI/src/public/Theme/DefaultTheme.cs @@ -16,13 +16,18 @@ */ #if !PROFILE_WEARABLE +using System.Collections.Generic; + namespace Tizen.NUI { internal class DefaultThemeCreator : IThemeCreator { - public Theme Create() + public Theme Create() => Create(null); + public Theme Create(IEnumerable> changedResources) { - return new Theme() { Id = "Tizen.NUI.Theme.Common" }; + Theme theme = new Theme() { Id = "Tizen.NUI.Theme.Common" }; + theme.SetChangedResources(changedResources); + return theme; } } } diff --git a/src/Tizen.NUI/src/public/Theme/Theme.cs b/src/Tizen.NUI/src/public/Theme/Theme.cs index 136ef0e..7c200da 100755 --- a/src/Tizen.NUI/src/public/Theme/Theme.cs +++ b/src/Tizen.NUI/src/public/Theme/Theme.cs @@ -38,28 +38,12 @@ namespace Tizen.NUI /// /// [EditorBrowsable(EditorBrowsableState.Never)] - public class Theme : BindableObject, IResourcesProvider + public class Theme : BindableObject { private readonly Dictionary map; + private IEnumerable> changedResources = null; private string baseTheme; - private string resource; - private string xamlFile; - - /// - /// The resource file path that is used in the theme. - /// - [EditorBrowsable(EditorBrowsableState.Never)] - public string Resource - { - get => resource; - set - { - if (resource == value) return; - resource = value; - - Reload(); - } - } + ResourceDictionary resources; /// Create an empty theme. [EditorBrowsable(EditorBrowsableState.Never)] @@ -81,29 +65,25 @@ namespace Tizen.NUI throw new ArgumentNullException(nameof(xamlFile), "The xaml file path cannot be null or empty string"); } - LoadFromXaml(xamlFile); - } - - /// - /// Create a new theme from the xaml file with theme resource. - /// - /// An absolute path to the xaml file. - /// An absolute path to the theme resource file. - /// Thrown when the given xamlFile or themeResource is null or empty string. - /// Thrown when there are file IO problems. - /// Thrown when the content of the xaml file is not valid xaml form. - [EditorBrowsable(EditorBrowsableState.Never)] - public Theme(string xamlFile, string themeResource) : this() - { - if (string.IsNullOrEmpty(xamlFile)) - throw new ArgumentNullException(nameof(xamlFile), "The xaml file path cannot be null or empty string"); - if (string.IsNullOrEmpty(themeResource)) - throw new ArgumentNullException(nameof(themeResource), "The theme resource file path cannot be null or empty string"); - - resource = themeResource; - XamlResources.SetAndLoadSource(new Uri(themeResource), themeResource, Assembly.GetAssembly(GetType()), null); - - LoadFromXaml(xamlFile); + try + { + using (var reader = XmlReader.Create(xamlFile)) + { + XamlLoader.Load(this, reader); + } + } + catch (System.IO.IOException) + { + Tizen.Log.Error("NUI", $"Could not load \"{xamlFile}\".\n"); + throw; + } + catch (Exception) + { + Tizen.Log.Error("NUI", $"Could not parse \"{xamlFile}\".\n"); + Tizen.Log.Error("NUI", "Make sure the all used assemblies (e.g. Tizen.NUI.Components) are included in the application project.\n"); + Tizen.Log.Error("NUI", "Make sure the type and namespace are correct.\n"); + throw; + } } /// @@ -145,11 +125,37 @@ namespace Tizen.NUI /// [EditorBrowsable(EditorBrowsableState.Never)] - public bool IsResourcesCreated { get; } = true; + public bool IsResourcesCreated => resources != null; /// [EditorBrowsable(EditorBrowsableState.Never)] - public ResourceDictionary XamlResources { get; set; } = new ResourceDictionary(); + internal ResourceDictionary Resources + { + get + { + if (resources != null) + return resources; + resources = new ResourceDictionary(); + ((IResourceDictionary)resources).ValuesChanged += OnThemeResourcesChanged; + return resources; + } + set + { + if (resources == value) + return; + + if (resources != null) + { + ((IResourceDictionary)resources).ValuesChanged -= OnThemeResourcesChanged; + } + resources = value; + if (resources != null) + { + // This callback will be removed when Resource.Source is assigned. + ((IResourceDictionary)resources).ValuesChanged += OnThemeResourcesChanged; + } + } + } /// /// For Xaml use only. @@ -254,6 +260,7 @@ namespace Tizen.NUI var result = new Theme() { Id = this.Id, + Resources = Resources }; foreach (var item in this) @@ -282,8 +289,6 @@ namespace Tizen.NUI if (theme == null) throw new ArgumentNullException(nameof(theme)); - this.xamlFile = theme.xamlFile; - if (Id == null) Id = theme.Id; foreach (var item in theme) @@ -325,6 +330,14 @@ namespace Tizen.NUI map[item.Key] = item.Value; } } + + if (theme.resources != null) + { + foreach (var res in theme.resources) + { + Resources[res.Key] = res.Value; + } + } } /// @@ -332,43 +345,37 @@ namespace Tizen.NUI /// internal void AddStyleWithoutClone(string styleName, ViewStyle value) => map[styleName] = value; - internal void Reload() + internal void SetChangedResources(IEnumerable> changedResources) { - if (xamlFile == null) - throw new InvalidOperationException("Cannot reload without xaml file."); - - map.Clear(); - if (Resource != null) - { - XamlResources.Clear(); - XamlResources.SetAndLoadSource(new Uri(Resource), Resource, Assembly.GetAssembly(GetType()), null); - } - - LoadFromXaml(xamlFile); + this.changedResources = changedResources; } - private void LoadFromXaml(string xamlFile) + internal void OnThemeResourcesChanged(object sender, ResourcesChangedEventArgs e) => OnThemeResourcesChanged(); + + internal void OnThemeResourcesChanged() { - try + if (changedResources != null) { - using (var reader = XmlReader.Create(xamlFile)) + // To avoid loop in infinite, remove OnThemeResourcesChanged callback. + ((IResourceDictionary)resources).ValuesChanged -= OnThemeResourcesChanged; + foreach (var changedResource in changedResources) { - this.xamlFile = xamlFile; - XamlLoader.Load(this, reader); + if (resources.TryGetValue(changedResource.Key, out object resourceValue)) + { + string changedValue = changedResource.Value; + + // check NUIResourcePath + string[] changedValues = changedValue.Split('/'); + if (changedValues[0] == "NUIResourcePath") + { + changedValue = changedValues[1]; + } + + Type toType = resourceValue.GetType(); + resources[changedResource.Key] = changedValue.ConvertTo(toType, () => toType.GetTypeInfo(), null); + } } } - catch (System.IO.IOException) - { - Tizen.Log.Error("NUI", $"Could not load \"{xamlFile}\".\n"); - throw; - } - catch (Exception) - { - Tizen.Log.Error("NUI", $"Could not parse \"{xamlFile}\".\n"); - Tizen.Log.Error("NUI", "Make sure the all used assemblies (e.g. Tizen.NUI.Components) are included in the application project.\n"); - Tizen.Log.Error("NUI", "Make sure the type and namespace are correct.\n"); - throw; - } } } } diff --git a/src/Tizen.NUI/src/public/Theme/ThemeManager.cs b/src/Tizen.NUI/src/public/Theme/ThemeManager.cs index 6ef43b6..10bd048 100755 --- a/src/Tizen.NUI/src/public/Theme/ThemeManager.cs +++ b/src/Tizen.NUI/src/public/Theme/ThemeManager.cs @@ -19,12 +19,14 @@ using System.Collections.Generic; using System.ComponentModel; using Tizen.NUI; using Tizen.NUI.BaseComponents; +using Tizen.NUI.Binding; namespace Tizen.NUI { internal interface IThemeCreator { Theme Create(); + Theme Create(IEnumerable> changedResources); } /// @@ -52,7 +54,7 @@ namespace Tizen.NUI private static Theme defaultTheme; private static readonly List builtinThemes = new List(); // Themes provided by framework. private static readonly List customThemes = new List(); // Themes registered by user. (Legacy support) - private static readonly List packages = new List(); + private static readonly List packages = new List(); static ThemeManager() { @@ -242,14 +244,31 @@ namespace Tizen.NUI return (Theme)result?.Clone(); } + /// + /// Update current theme resources. + /// + /// An enumerable collection of the changed resources + [EditorBrowsable(EditorBrowsableState.Never)] + public static void UpdateCurrentThemeResources(IEnumerable> changedResources) + { + if (CurrentTheme == null) // if current theme is default theme, + { + DefaultTheme.Clear(); + foreach (IThemeCreator themeCreator in packages) + { + DefaultTheme.MergeWithoutClone(themeCreator.Create(changedResources)); + } + NotifyThemeChanged(); + } + } + internal static void AddPackageTheme(IThemeCreator themeCreator) { - string name = themeCreator.GetType().FullName; - if (packages.FindIndex(x => string.Equals(x, name)) >= 0) + if (packages.Contains(themeCreator)) { return; } - packages.Add(name); + packages.Add(themeCreator); DefaultTheme.MergeWithoutClone(themeCreator.Create()); } diff --git a/test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/ThemeResourceSample.cs b/test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/ThemeResourceSample.cs index 766f7cf..44c05c0 100644 --- a/test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/ThemeResourceSample.cs +++ b/test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/ThemeResourceSample.cs @@ -1,4 +1,5 @@ -using Tizen.NUI; +using System.Collections.Generic; +using Tizen.NUI; using Tizen.NUI.BaseComponents; using Tizen.NUI.Components; @@ -6,12 +7,21 @@ namespace Tizen.NUI.Samples { public class ThemeResourceSample : IExample { + Dictionary DefaultThemeResources { get; } = new Dictionary() + { + {"ButtonBackgroundColorNormal", "0.054, 0.631, 0.921, 1" }, + {"ButtonBackgroundColorPressed", "0.454, 0.752, 0.905, 1" }, + {"ButtonBackgroundColorDisabled", "0.88, 0.88, 0.88, 1" }, + }; + Dictionary DarkThemeResources { get; } = new Dictionary() + { + {"ButtonBackgroundColorNormal", "0.309, 0.309, 0.309, 1" }, + {"ButtonBackgroundColorPressed", "0.631, 0.631, 0.631, 1" }, + {"ButtonBackgroundColorDisabled", "0.8, 0.8, 0.8, 1" }, + }; public void Activate() { - string resourceDefault = global::System.IO.Path.Combine("res", "resSampleThemeResourceDefault.xaml"); - string resourceDark = global::System.IO.Path.Combine("res", "SampleThemeResourceDark.xaml"); - Theme sampleTheme = new Theme(global::System.IO.Path.Combine("res", "SampleTheme.xaml"), resourceDefault); - ThemeManager.ApplyTheme(sampleTheme); + bool isCurrentThemeDefault = true; View root = new View(); root.WidthSpecification = LayoutParamPolicies.MatchParent; @@ -23,16 +33,15 @@ namespace Tizen.NUI.Samples button.Size = new Size2D(200, 200); button.Clicked += (object sender, ClickedEventArgs e) => { - if (sampleTheme.Resource == resourceDefault) + if (isCurrentThemeDefault) { - sampleTheme.Resource = resourceDark; - ThemeManager.ApplyTheme(sampleTheme); - + isCurrentThemeDefault = false; + ThemeManager.UpdateCurrentThemeResources(DarkThemeResources); } else { - sampleTheme.Resource = resourceDefault; - ThemeManager.ApplyTheme(sampleTheme); + isCurrentThemeDefault = true; + ThemeManager.UpdateCurrentThemeResources(DefaultThemeResources); } }; root.Add(button); diff --git a/test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/res/SampleTheme.xaml b/test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/res/SampleTheme.xaml deleted file mode 100644 index 041fd25..0000000 --- a/test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/res/SampleTheme.xaml +++ /dev/null @@ -1,16 +0,0 @@ - - - - - - - - - - - diff --git a/test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/res/SampleThemeResourceDark.xaml b/test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/res/SampleThemeResourceDark.xaml deleted file mode 100644 index c6ea46d..0000000 --- a/test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/res/SampleThemeResourceDark.xaml +++ /dev/null @@ -1,8 +0,0 @@ - - - 0.309, 0.309, 0.309,1 - 0.631,0.631,0.631,1 - 0.8,0.8,0.8,1 - diff --git a/test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/res/SampleThemeResourceDefault.xaml b/test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/res/SampleThemeResourceDefault.xaml deleted file mode 100644 index f198231..0000000 --- a/test/Tizen.NUI.Samples/Tizen.NUI.Samples/Samples/res/SampleThemeResourceDefault.xaml +++ /dev/null @@ -1,8 +0,0 @@ - - - 0.054, 0.631, 0.921,1 - 0.454, 0.752, 0.905,1 - 0.88,0.88,0.88,1 - -- 2.7.4