[英]Change Theme Dynamically Telerik WPF
我需要允许用户在使用 telerik WPF 控件创建的应用程序中动态更改主题。
我正在为我的 XAML 中的每个 telerik 控件设置绑定,如下所示:
XAML:
telerik:StyleManager.Theme="{Binding SelectedSMTheme, Mode=TwoWay}"
视图模型:
private Theme selectedSMTheme;
public Theme SelectedSMTheme
{
get
{
return selectedSMTheme;
}
set
{
selectedSMTheme = value;
RaisePropertyChange("SelectedSMTheme");
}
}
并在用户 select 主题时更改此SelectedSMTheme
。
改变主题:
SelectedSMTheme = new Expression_DarkTheme();
在运行应用程序时是否有任何其他方法可以更改 telerik 控件的主题。 因为,在这里我需要为整个应用程序中的每个控件指定telerik:StyleManager.Theme
。
您可以使用StyleManager.ApplicationTheme
来设置初始主题。 设置此属性会影响应用程序中的所有控件。
您的 App.xaml.cs 构造函数应如下所示:
public partial class App : Application
{
public App()
{
StyleManager.ApplicationTheme = new Expression_DarkTheme();
this.InitializeComponent();
}
}
要在运行时切换主题,您应该清除应用程序资源并添加新资源。
private void btnChangeTheme_Click(object sender, RoutedEventArgs e)
{
Application.Current.Resources.MergedDictionaries.Clear();
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary()
{
Source = new Uri("/Telerik.Windows.Themes.Green;component/Themes/System.Windows.xaml", UriKind.RelativeOrAbsolute)
});
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary()
{
Source = new Uri("/Telerik.Windows.Themes.Green;component/Themes/Telerik.Windows.Controls.xaml", UriKind.RelativeOrAbsolute)
});
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary()
{
Source = new Uri("/Telerik.Windows.Themes.Green;component/Themes/Telerik.Windows.Controls.Input.xaml", UriKind.RelativeOrAbsolute)
});
}
您必须记住从位于安装文件夹中的 Binaries.NoXaml 文件夹中添加所需的程序集(在我的例子中是: C:\\Program Files (x86)\\Progress\\Telerik UI for WPF R2 2018\\Binaries.NoXaml
):
Telerik.Windows.Controls.dll
Telerik.Windows.Controls.Input.dll
Telerik.Windows.Themes.Expression_Dark.dll
和Telerik.Windows.Themes.Green.dll
请阅读以下文章以获取更多信息:
https://docs.telerik.com/devtools/wpf/styling-and-appearance/how-to/styling-apperance-themes-runtime
我正在使用与 kmatyaszek 提供的类似解决方案,除了我在 ComboBox 中执行此操作:
private void StyleCombo_OnSelectionChanged(object sender, SelectionChangedEventArgs e)
{
var selectedTheme = StyleCombo.SelectedItem as ThemeNames;
Application.Current.Resources.MergedDictionaries.Clear();
// XAML
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary
{
Source = new Uri("/Telerik.Windows.Themes." + selectedTheme.Value + ";component/Themes/System.Windows.xaml", UriKind.RelativeOrAbsolute)
});
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary
{
Source = new Uri("/Telerik.Windows.Themes." + selectedTheme.Value + ";component/Themes/Telerik.Windows.Controls.xaml", UriKind.RelativeOrAbsolute)
});
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary
{
Source = new Uri("/Telerik.Windows.Themes." + selectedTheme.Value + ";component/Themes/Telerik.Windows.Controls.Input.xaml", UriKind.RelativeOrAbsolute)
});
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary
{
Source = new Uri("/Telerik.Windows.Themes." + selectedTheme.Value + ";component/Themes/Telerik.Windows.Controls.Navigation.xaml", UriKind.RelativeOrAbsolute)
});
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary
{
Source = new Uri("/Telerik.Windows.Themes." + selectedTheme.Value + ";component/Themes/Telerik.Windows.Controls.Data.xaml", UriKind.RelativeOrAbsolute)
});
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary
{
Source = new Uri("/Telerik.Windows.Themes." + selectedTheme.Value + ";component/Themes/Telerik.Windows.Controls.DataVisualization.xaml", UriKind.RelativeOrAbsolute)
});
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary
{
Source = new Uri("/Telerik.Windows.Themes." + selectedTheme.Value + ";component/Themes/Telerik.Windows.Controls.Docking.xaml", UriKind.RelativeOrAbsolute)
});
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary
{
Source = new Uri("/Telerik.Windows.Themes." + selectedTheme.Value + ";component/Themes/Telerik.Windows.Controls.GridView.xaml", UriKind.RelativeOrAbsolute)
});
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary
{
Source = new Uri("/Telerik.Windows.Themes." + selectedTheme.Value + ";component/Themes/Telerik.Windows.Controls.Pivot.xaml", UriKind.RelativeOrAbsolute)
});
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary
{
Source = new Uri("/Telerik.Windows.Themes." + selectedTheme.Value + ";component/Themes/Telerik.Windows.Controls.PivotFieldList.xaml", UriKind.RelativeOrAbsolute)
});
Application.Current.Resources.MergedDictionaries.Add(new ResourceDictionary
{
Source = new Uri("/Telerik.Windows.Themes." + selectedTheme.Value + ";component/Themes/Telerik.Windows.Controls.VirtualGrid.xaml", UriKind.RelativeOrAbsolute)
});
}
您在评论部分说过,某些控件不会动态更改 - 这是 NoXaml 库的已知问题。 我可以向您推荐的是手动设置这些控件的参数。 就我而言,它看起来像这样:
// Main Grid
if (selectedTheme.Name == "Visual Studio 2013 Dark")
{
VisualStudio2013Palette.LoadPreset(VisualStudio2013Palette.ColorVariation.Dark);
App.StronaGlowna.MainGrid.Background = (SolidColorBrush)new BrushConverter().ConvertFrom("#FF1E1E1E");
}
if (selectedTheme.Name == "Visual Studio 2013 Blue")
{
VisualStudio2013Palette.LoadPreset(VisualStudio2013Palette.ColorVariation.Blue);
}
if (selectedTheme.Name == "Visual Studio 2013")
{
VisualStudio2013Palette.LoadPreset(VisualStudio2013Palette.ColorVariation.Light);
App.StronaGlowna.MainGrid.Background = Brushes.White;
}
if (selectedTheme.Name == "Dark")
{
VisualStudio2013Palette.LoadPreset(VisualStudio2013Palette.ColorVariation.Dark);
App.StronaGlowna.MainGrid.Background = (SolidColorBrush)new BrushConverter().ConvertFrom("#FF3D3D3D");
}
if (selectedTheme.Name == "Green")
{
GreenPalette.LoadPreset(GreenPalette.ColorVariation.Dark);
App.StronaGlowna.MainGrid.Background = (SolidColorBrush)new BrushConverter().ConvertFrom("#FF1D1E21");
}
if (selectedTheme.Name == "Green Light")
{
GreenPalette.LoadPreset(GreenPalette.ColorVariation.Light);
App.StronaGlowna.MainGrid.Background = (SolidColorBrush)new BrushConverter().ConvertFrom("#FFE0E0E0");
}
if (selectedTheme.Name == "Vista" ||
selectedTheme.Name == "Visual Studio 2013 Blue" || selectedTheme.Name == "Office Black" ||
selectedTheme.Name == "Office Blue" ||
selectedTheme.Name == "Office Silver" || selectedTheme.Name == "Summer" ||
selectedTheme.Name == "Transparent" || selectedTheme.Name == "Windows 7")
{
App.StronaGlowna.MainGrid.Background = Brushes.White;
}
这个解决方案是由 Telerik 支持在 1 个支持票中提供给我的。 您可以在文档中找到大多数控件的十六进制颜色,例如这个是针对 Office2013 主题的。 另外,请记住,某些 WPF 控件不受样式的影响(我认为其中一个示例是 TextBox),因此如果您使用的是 vanilla WPF 控件,它们可能保持不变并需要您对新颜色进行硬编码。
相同但更好,从可用的主题 dll 动态加载并适用于任何使用的库(尝试 {} catch)
void LoadThemeNames()
{
var directory = AppDomain.CurrentDomain.BaseDirectory;
var files = Directory.GetFiles(directory, "Telerik.Windows.Themes.*.dll");
foreach (var item in files)
{
var name = item.Split('.')[3];
ThemeCombo.Items.Add(new RadComboBoxItem() { Content = name.Replace("_", " "), Name = name });
}
}
public void ChangeTheme(string selectedTheme)
{
Application.Current.Resources.MergedDictionaries.Clear();
string[] lst = new string[] {
"System.Windows.xaml",
"Telerik.Windows.Controls.xaml",
"Telerik.Windows.Controls.Input.xaml",
"Telerik.Windows.Controls.Navigation.xaml",
"Telerik.Windows.Controls.Data.xaml",
"Telerik.Windows.Controls.DataVisualization.xaml",
"Telerik.Windows.Controls.Docking.xaml",
"Telerik.Windows.Controls.GridView.xaml",
"Telerik.Windows.Controls.Pivot.xaml",
"Telerik.Windows.Controls.PivotFieldList.xaml",
"Telerik.Windows.Controls.VirtualGrid.xaml"};
foreach (var item in lst)
{
var uri = new Uri("/Telerik.Windows.Themes." + selectedTheme + ";component/Themes/" + item, UriKind.RelativeOrAbsolute);
if (uri != null)
{
try
{
var rsc = new ResourceDictionary { Source = uri };
Application.Current.Resources.MergedDictionaries.Add(rsc);
}
catch (Exception e) { }
}
}
}
private void RadComboBox_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
ChangeTheme(((RadComboBoxItem)ThemeCombo.SelectedItem).Name.ToString());
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.