根据 light/dark 主题在运行时切换 XAML 资源?
Switch XAML resources at runtime based on light/dark theme?
我有一个使用 MahApps(“轻”模式)的 WPF 应用程序,我现在为用户提供了一种切换模式的方法 (light/dark)。许多应用程序的颜色明显根据模式而变化,通过比较 \Styles\Themes\Light.colour_name.xaml 和 Dark 可以看出。 colour_name.xaml 文件,但我想通过实现我自己的 xaml <Color>
资源以某种方式“扩展”这些文件这也会根据所选模式而改变。这能做到吗?
一个示例是当前使用蓝色绘制点的图表 - 这些图表在“浅色”模式下看起来不错,但在“深色”模式下有点暗。我意识到我可以使用更合适的蓝色阴影,它在两种模式下看起来都不错,但如果我可以定义一个 Color 资源,它会更灵活(比如)在灯光模式下 'Blue' 但 'Lime' 在深色模式下。这种功能也可能有其他用途,例如彩色通知消息。
您可以根据 built-in 主题创建自定义主题。创建一个资源字典,合并基础主题的资源字典并覆盖现有画笔并添加新画笔。
浅色主题词典(Light.Blue.Custom.xaml
):
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:options="http://schemas.microsoft.com/winfx/2006/xaml/presentation/options" >
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="pack://application:,,,/MahApps.Metro;component/Styles/Themes/Light.Blue.xaml" />
</ResourceDictionary.MergedDictionaries>
<!-- Overriding default brushes -->
<SolidColorBrush x:Key="MahApps.Brushes.Button.Border.MouseOver" Color="Blue" options:Freeze="True" />
<!-- Adding your own brushes -->
<SolidColorBrush x:Key="My.Brushes.Notification.Alert" Color="Red" options:Freeze="True" />
</ResourceDictionary>
深色主题词典(Dark.Blue.Custom.xaml
):
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:options="http://schemas.microsoft.com/winfx/2006/xaml/presentation/options" >
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="pack://application:,,,/MahApps.Metro;component/Styles/Themes/Dark.Blue.xaml" />
</ResourceDictionary.MergedDictionaries>
<!-- Overriding default brushes -->
<SolidColorBrush x:Key="MahApps.Brushes.Button.Border.MouseOver" Color="DarkBlue" options:Freeze="True" />
<!-- Adding your own brushes -->
<SolidColorBrush x:Key="My.Brushes.Notification.Alert" Color="DarkRed" options:Freeze="True" />
</ResourceDictionary>
在您的应用程序中注册主题词典。您 必须在 class 和资源字典 URI 中用您的应用程序的真实名称替换 虚拟名称 YourApp
。
public partial class YourApp : Application
{
protected override void OnStartup(StartupEventArgs e)
{
base.OnStartup(e);
var lightBlueCustomTheme = ThemeManager.Current.AddLibraryTheme(new LibraryTheme(
new Uri("pack://application:,,,/YourApp;component/Light.Blue.Custom.xaml"),
MahAppsLibraryThemeProvider.DefaultInstance));
var darkBlueCustomTheme = ThemeManager.Current.AddLibraryTheme(new LibraryTheme(
new Uri("pack://application:,,,/YourApp;component/Dark.Blue.Custom.xaml"),
MahAppsLibraryThemeProvider.DefaultInstance));
ThemeManager.Current.ChangeTheme(this, lightBlueCustomTheme);
// Optionally enable App Mode theme switching
// ThemeManager.Current.ThemeSyncMode = ThemeSyncMode.SyncWithAppMode;
// ThemeManager.Current.SyncTheme();
}
}
请注意,您需要为 both Light 和 Dark 提供主题,如果您想切换模式。有关主题和自定义的更多信息,您可以参考 documentation.
我有一个使用 MahApps(“轻”模式)的 WPF 应用程序,我现在为用户提供了一种切换模式的方法 (light/dark)。许多应用程序的颜色明显根据模式而变化,通过比较 \Styles\Themes\Light.colour_name.xaml 和 Dark 可以看出。 colour_name.xaml 文件,但我想通过实现我自己的 xaml <Color>
资源以某种方式“扩展”这些文件这也会根据所选模式而改变。这能做到吗?
一个示例是当前使用蓝色绘制点的图表 - 这些图表在“浅色”模式下看起来不错,但在“深色”模式下有点暗。我意识到我可以使用更合适的蓝色阴影,它在两种模式下看起来都不错,但如果我可以定义一个 Color 资源,它会更灵活(比如)在灯光模式下 'Blue' 但 'Lime' 在深色模式下。这种功能也可能有其他用途,例如彩色通知消息。
您可以根据 built-in 主题创建自定义主题。创建一个资源字典,合并基础主题的资源字典并覆盖现有画笔并添加新画笔。
浅色主题词典(Light.Blue.Custom.xaml
):
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:options="http://schemas.microsoft.com/winfx/2006/xaml/presentation/options" >
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="pack://application:,,,/MahApps.Metro;component/Styles/Themes/Light.Blue.xaml" />
</ResourceDictionary.MergedDictionaries>
<!-- Overriding default brushes -->
<SolidColorBrush x:Key="MahApps.Brushes.Button.Border.MouseOver" Color="Blue" options:Freeze="True" />
<!-- Adding your own brushes -->
<SolidColorBrush x:Key="My.Brushes.Notification.Alert" Color="Red" options:Freeze="True" />
</ResourceDictionary>
深色主题词典(Dark.Blue.Custom.xaml
):
<ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:options="http://schemas.microsoft.com/winfx/2006/xaml/presentation/options" >
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="pack://application:,,,/MahApps.Metro;component/Styles/Themes/Dark.Blue.xaml" />
</ResourceDictionary.MergedDictionaries>
<!-- Overriding default brushes -->
<SolidColorBrush x:Key="MahApps.Brushes.Button.Border.MouseOver" Color="DarkBlue" options:Freeze="True" />
<!-- Adding your own brushes -->
<SolidColorBrush x:Key="My.Brushes.Notification.Alert" Color="DarkRed" options:Freeze="True" />
</ResourceDictionary>
在您的应用程序中注册主题词典。您 必须在 class 和资源字典 URI 中用您的应用程序的真实名称替换 虚拟名称 YourApp
。
public partial class YourApp : Application
{
protected override void OnStartup(StartupEventArgs e)
{
base.OnStartup(e);
var lightBlueCustomTheme = ThemeManager.Current.AddLibraryTheme(new LibraryTheme(
new Uri("pack://application:,,,/YourApp;component/Light.Blue.Custom.xaml"),
MahAppsLibraryThemeProvider.DefaultInstance));
var darkBlueCustomTheme = ThemeManager.Current.AddLibraryTheme(new LibraryTheme(
new Uri("pack://application:,,,/YourApp;component/Dark.Blue.Custom.xaml"),
MahAppsLibraryThemeProvider.DefaultInstance));
ThemeManager.Current.ChangeTheme(this, lightBlueCustomTheme);
// Optionally enable App Mode theme switching
// ThemeManager.Current.ThemeSyncMode = ThemeSyncMode.SyncWithAppMode;
// ThemeManager.Current.SyncTheme();
}
}
请注意,您需要为 both Light 和 Dark 提供主题,如果您想切换模式。有关主题和自定义的更多信息,您可以参考 documentation.