mirror of
https://github.com/wwiinnddyy/LanMountainDesktop.git
synced 2026-06-20 23:54:26 +08:00
7.4 KiB
7.4 KiB
04-外观与主题系统
阑山桌面支持暗色/浅色主题切换,插件需要适配宿主的视觉风格,保持界面一致性。
🎨 主题系统概述
阑山桌面使用 Avalonia UI 的主题系统,支持:
- 浅色主题 - 明亮背景,深色文字
- 深色主题 - 深色背景,浅色文字
- 跟随系统 - 自动匹配 Windows/macOS 主题
🌗 检测当前主题
在组件中检测
using Avalonia;
using Avalonia.Styling;
public class MyWidget : Border
{
public MyWidget(PluginDesktopComponentContext context)
{
// 检测当前主题
var isDark = Application.Current?.ActualThemeVariant == ThemeVariant.Dark;
// 根据主题设置颜色
UpdateTheme(isDark);
// 监听主题变化
if (Application.Current != null)
{
Application.Current.ActualThemeVariantChanged += (_, _) =>
{
var newIsDark = Application.Current.ActualThemeVariant == ThemeVariant.Dark;
UpdateTheme(newIsDark);
};
}
}
private void UpdateTheme(bool isDark)
{
Background = new SolidColorBrush(
isDark ? Color.Parse("#FF1E1E1E") : Color.Parse("#FFFFFFFF"));
Foreground = new SolidColorBrush(
isDark ? Colors.White : Colors.Black);
}
}
📐 圆角系统
插件必须使用宿主提供的圆角系统,确保与内置组件视觉一致。
为什么插件不能使用 XAML 资源
插件运行在独立的 AssemblyLoadContext 中,无法直接访问宿主的资源字典。因此 {DynamicResource DesignCornerRadiusComponent} 在插件 XAML 中无效。
使用代码设置圆角
public class MyWidget : Border
{
public MyWidget(PluginDesktopComponentContext context)
{
// 方法 1:使用预设(推荐)
CornerRadius = context.Appearance.ResolveCornerRadius(
PluginCornerRadiusPreset.Component);
// 方法 2:带最小/最大值限制
CornerRadius = context.Appearance.ResolveCornerRadius(
PluginCornerRadiusPreset.Component,
minimum: new CornerRadius(8),
maximum: new CornerRadius(24));
// 方法 3:自定义基础值,应用全局缩放
CornerRadius = context.Appearance.ResolveScaledCornerRadius(
baseRadius: 16,
minimum: 8,
maximum: 32);
}
}
圆角预设
| 预设 | 默认值 | 用途 |
|---|---|---|
Micro |
6px | 微小元素 |
Xs |
12px | 小元素、图标容器 |
Sm |
14px | 小卡片 |
Md |
20px | 普通按钮/卡片 |
Lg |
28px | 大面板 |
Xl |
32px | 强调容器 |
Island |
36px | 大型容器 |
Component |
18px | 桌面组件标准 |
Default |
自适应 | 根据尺寸自动计算 |
内部元素圆角
组件内部的卡片、按钮应使用更小的圆角:
// 组件根容器 - 使用 Component 预设
CornerRadius = context.ResolveCornerRadius(PluginCornerRadiusPreset.Component);
// 内部卡片 - 使用 Md 预设
var innerCard = new Border
{
CornerRadius = context.ResolveCornerRadius(PluginCornerRadiusPreset.Md),
Background = new SolidColorBrush(Colors.LightGray)
};
// 按钮 - 使用 Sm 预设
var button = new Button
{
CornerRadius = context.ResolveCornerRadius(PluginCornerRadiusPreset.Sm)
};
🎨 颜色系统
推荐的颜色策略
// 透明背景(推荐)- 让宿主壁纸透出
Background = new SolidColorBrush(Colors.Transparent);
// 毛玻璃效果
Background = new SolidColorBrush(Color.Parse(isDark ? "#40FFFFFF" : "#40000000"));
// 卡片背景
Background = new SolidColorBrush(Color.Parse(isDark ? "#FF2D2D2D" : "#FFFFFFFF"));
// 强调色(使用系统强调色)
var accentColor = Color.Parse("#FF0078D4"); // 阑山桌面主色调
文字颜色
// 主要文字
Foreground = new SolidColorBrush(isDark ? Colors.White : Colors.Black);
// 次要文字
Foreground = new SolidColorBrush(isDark ? Color.Parse("#FFCCCCCC") : Color.Parse("#FF666666"));
// 禁用文字
Foreground = new SolidColorBrush(isDark ? Color.Parse("#FF666666") : Color.Parse("#FF999999"));
🔄 响应外观变化
订阅外观变化事件
public class MyWidget : Border
{
public MyWidget(PluginDesktopComponentContext context)
{
// 订阅外观变化
context.Appearance.AppearanceChanged += (_, _) =>
{
UpdateAppearance();
};
// 初始化
UpdateAppearance();
}
private void UpdateAppearance()
{
// 重新应用圆角(用户可能调整了全局圆角设置)
var context = ...; // 获取 context
CornerRadius = context.Appearance.ResolveCornerRadius(
PluginCornerRadiusPreset.Component);
// 更新主题颜色
var isDark = Application.Current?.ActualThemeVariant == ThemeVariant.Dark;
UpdateThemeColors(isDark);
}
}
🧩 使用 FluentAvalonia 控件
推荐使用 FluentAvalonia 控件库,它们自动适配主题:
<Window xmlns:ui="using:FluentAvalonia.UI.Controls">
<ui:SettingsExpander Header="设置项">
<ui:SettingsExpander.IconSource>
<ui:FontIconSource Glyph="" />
</ui:SettingsExpander.IconSource>
</ui:SettingsExpander>
</Window>
常用 FluentAvalonia 控件
| 控件 | 用途 |
|---|---|
SettingsExpander |
设置项展开器 |
SettingsCard |
设置卡片 |
ColorPicker |
颜色选择器 |
NumberBox |
数字输入框 |
ToggleSwitch |
开关 |
💡 最佳实践
1. 始终使用透明背景
// ✅ 好的做法
Background = new SolidColorBrush(Colors.Transparent);
// ❌ 避免硬编码背景色
Background = new SolidColorBrush(Colors.White);
2. 组件根容器必须使用 Component 圆角
// ✅ 正确
CornerRadius = context.ResolveCornerRadius(PluginCornerRadiusPreset.Component);
// ❌ 错误 - 硬编码
CornerRadius = new CornerRadius(18);
3. 响应主题变化
// ✅ 订阅变化事件
Application.Current.ActualThemeVariantChanged += OnThemeChanged;
// ❌ 只在构造函数中设置一次
4. 使用语义化颜色
// ✅ 根据用途选择颜色
var primaryText = isDark ? Colors.White : Colors.Black;
var secondaryText = isDark ? Color.Parse("#FFCCCCCC") : Color.Parse("#FF666666");
// ❌ 避免随意使用颜色
var textColor = Color.Parse("#FF123456");
🐛 常见问题
问题 1:圆角不生效
原因: 在 XAML 中使用 {DynamicResource}
解决: 在代码中设置圆角(见上文)
问题 2:主题切换后颜色不对
原因: 没有订阅主题变化事件
解决: 添加 ActualThemeVariantChanged 事件处理
问题 3:组件与内置组件风格不一致
排查:
- 检查圆角是否使用
PluginCornerRadiusPreset.Component - 检查背景是否透明
- 检查是否使用了 FluentAvalonia 控件
📚 参考资源
🎯 下一步
学习插件间通信:
👉 05-插件间通信 - 与其他插件协作
最后更新:2026年4月