我正在WinXP上编写一个WPF应用程序,我用这样的vista主题覆盖了默认主题:
protected override void OnStartup(StartupEventArgs e)
{
base.OnStartup(e);
var themerd = new ResourceDictionary();
themerd.Source = new Uri(@"PresentationFramework.Aero;V3.0.0.0;31bf3856ad364e35;component\themes/aero.normalcolor.xaml", UriKind.Relative);
Resources.MergedDictionaries.Add(themerd);
}
Run Code Online (Sandbox Code Playgroud)
它主要工作得很好.当我使用按钮等控件时:
<Button />
Run Code Online (Sandbox Code Playgroud)
样式看起来很好,但如果我使用具有不同样式的Button,如下所示:
<Button>
<Button.Style>
<Style TargetType="Button">
<Setter Property="Width" Value="80" />
</Style>
</Button.Style>
</Button>
Run Code Online (Sandbox Code Playgroud)
该样式将使用标准的WinXP样式覆盖指定的主题样式,而不是在其上构建.这对我来说是非常有限的.有没有办法避免这个问题?
Ray*_*rns 10
为什么会这样
仅使用当前主题的资源字典生成样式的默认BasedOn = .您为覆盖主题而显示的技术实际上并未更改正在使用的主题词典:它只是将主题资源字典中的资源添加到应用程序的资源字典中.由于当前主题未更改,因此默认的BasedOn也保持不变.
如何解决它
选项1:通过拦截对Win32级别的uxtheme.dll!GetCurrentThemeName的调用来本地覆盖主题.这非常复杂,但适用于所有样式而不更改XAML.
选项2:使用自定义MarkupExtension设置BasedOn.它看起来像这样:
<Style TargetType="Button" BasedOn="{DefaultAeroStyle Button}"> ...
Run Code Online (Sandbox Code Playgroud)
您的自定义MarkupExtension将在首次使用时加载Aero主题词典并将其存储在静态字段中.它的构造函数将采用Type,并且其ProvideValue将查找字典中的类型以查找样式.
选项3:将BasedOn设置为中间命名样式.它看起来像这样:
<Application ...>
<Application.Resources>
<ResourceDictionary>
<ResourceDictionary.MergedDictionaries>
<ResourceDictionary Source="... theme path ..." />
</ResourceDictionary.MergedDictionaries>
<Style x:Key="ThemeButtonStyle" TargetType="Button" BasedOn="{StaticResource {x:Type Button}}" />
<Style x:Key="ThemeListBoxStyle" TargetType="ListBox" BasedOn="{StaticResource {x:Type ListBox}}" />
...
</ResourceDictionary>
</Application.Resources>
</Application>
Run Code Online (Sandbox Code Playgroud)
现在在您的低级词典中,您可以说:
<Style TargetType="Button" BasedOn="{StaticResource ThemeButtonStyle}" />
Run Code Online (Sandbox Code Playgroud)
选项4:使用静态属性和x:静态标记扩展名设置BasedOn
| 归档时间: |
|
| 查看次数: |
3653 次 |
| 最近记录: |