Я создал пользовательскую кнопку WPF управление с помощью ControlTemplate , определенной в ресурсе . Этот шаблон использует свойства DynamicResource для начального фона и переднего плана (для поддержки динамического переключения темы между режимами Light/Dark) и StaticResource в Visualstate.storyboard анимации для окрашенных изменений на мыши , нажали , и т. Д. Кнопка запускает VisualState (например, MouseOver ), изменение цвета, определяемое StaticResource в том, что изображение visualstate «Скаунная зал» влияет на все остальные экземпляры одинаковых Custom кнопки на экране . Это неожиданное поведение, поскольку Visualstates в идеале следует локализовать в конкретном экземпляре управления. Использование тематических SolidColorBrush ресурсов.
фрагменты кода (упрощенное):
github Repo с полному коде.
современный стиль
Код: Выделить всё
< /code>
modernbutton.xaml.cs
public partial class ModernButton : Button
{
#region Constructors
static ModernButton()
{
DefaultStyleKeyProperty.OverrideMetadata(typeof(ModernButton), new FrameworkPropertyMetadata(typeof(ModernButton)));
}
#endregion
#region DependencyProperties
public static readonly DependencyProperty CornerRadiusProperty =
DependencyProperty.Register(
nameof(CornerRadius),
typeof(CornerRadius),
typeof(ModernButton),
new PropertyMetadata(new CornerRadius(0))); // Default corner radius value
#endregion
#region Properties
public CornerRadius CornerRadius
{
get { return (CornerRadius)GetValue(CornerRadiusProperty); }
set { SetValue(CornerRadiusProperty, value); }
}
#endregion
}
< /code>
thememanager.cs
public class ThemeManager
{
#region Fields
private readonly Dictionary AvailableThemes = new()
{
{ WpfTheme.GithubDark, "pack://application:,,,/Wpf.Modern.Themes;component/Themes/Github/Themes/GithubDarkTheme.xaml" },
{ WpfTheme.GithubLight, "pack://application:,,,/Wpf.Modern.Themes;component/Themes/Github/Themes/GithubLightTheme.xaml" },
};
#endregion
#region Consts
private const string ThemeResourceKey = "CurrentThemeLibrary";
#endregion
#region Methods
public void ApplyTheme(WpfTheme theme)
{
if (!AvailableThemes.ContainsKey(theme))
throw new ArgumentException($"Theme '{theme}' is not available.");
var app = Application.Current;
var oldTheme = CurrentTheme;
// Remove existing theme
var existingTheme = app.Resources.MergedDictionaries
.FirstOrDefault(d => d.Contains(ThemeResourceKey));
if (existingTheme != null)
{
app.Resources.MergedDictionaries.Remove(existingTheme);
}
// Add new theme
var themeUri = new Uri(AvailableThemes[theme], UriKind.Absolute);
var newTheme = new ResourceDictionary { Source = themeUri };
newTheme[ThemeResourceKey] = theme;
app.Resources.MergedDictionaries.Add(newTheme);
// Force refresh of all windows
foreach (Window window in app.Windows)
{
window.InvalidateVisual();
}
}
#endregion
}
Подробнее здесь: https://stackoverflow.com/questions/796 ... aticresour