如何在不将 WPF 从 Aero 恢复为 Classic 的情况下更改按钮的默认样式? [英] How do I alter the default style of a button without WPF reverting from Aero to Classic?

查看:25
本文介绍了如何在不将 WPF 从 Aero 恢复为 Classic 的情况下更改按钮的默认样式?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我已将 PresentationFramework.Aero 添加到我的 App.xaml 合并词典中,例如...

I've added PresentationFramework.Aero to my App.xaml merged dictionaries, as in...

<Application
    x:Class="TestApp.App"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
    <Application.Resources>
        <ResourceDictionary>
            <ResourceDictionary.MergedDictionaries>
                <ResourceDictionary
                    Source="/PresentationFramework.Aero;component/themes/Aero.NormalColor.xaml" />
                <ResourceDictionary
                     Source="pack://application:,,,/WPFToolkit;component/Themes/Aero.NormalColor.xaml" />
                <ResourceDictionary
                    Source="/CommonLibraryWpf;component/ResourceDictionaries/ButtonResourceDictionary.xaml" />
                    <!-- Note, ButtonResourceDictionary.xaml is defined in an external class library-->
            </ResourceDictionary.MergedDictionaries>
        </ResourceDictionary>
    </Application.Resources>
</Application>

我正在尝试稍微修改按钮的默认外观.我把这个样式放在我的 ButtonResourceDictionary 中:

I'm trying to modify the default look of buttons just slightly. I put this style in my ButtonResourceDictionary:

<Style TargetType="Button">
    <Setter Property="Padding" Value="3" />
    <Setter Property="FontWeight" Value="Bold" />
</Style>

所有按钮现在都有正确的填充和粗体文本,但它们看起来经典",而不是航空".我如何修复这种样式,让我的按钮看起来都是 Aero 风格,但也有这些细微的变化?我不想为每个按钮设置 Style 属性.

All buttons now have the correct padding and bold text, but they look "Classic", not "Aero". How do I fix this style so my buttons all look Aero but also have these minor changes? I would prefer not to have to set the Style property for every button.

更新

我应该首先提到这一点,但是如果我尝试使用 BasedOn,如下所示,我得到一个 StackOverflowException:

I should have mentioned this in the first place, but if I try to use BasedOn, as shown below, I get a StackOverflowException:

<Style BasedOn="{StaticResource {x:Type Button}}" TargetType="{x:Type Button}">
    <Setter Property="Padding" Value="3" />
    <Setter Property="FontWeight" Value="Bold" />
</Style>

这通常会起作用,但在合并 Aero 词典时无效.如果我将这些词典注释掉,异常就会消失.

This would normally work, but not with the Aero dictionaries merged in. If I comment those dictionaries out, the exception disappears.

更新 2

如果我添加一个 x:Key 属性并手动设置样式,它可以正常工作(带填充和粗体的 Aero 样式),但正如我所说,我更喜欢样式是自动的全局应用于所有按钮.

If I add an x:Key attribute and manually set the style, it works properly (Aero style with padding and bold), but as I said, I'd prefer that the style is automatically applied globally to all buttons.

更新 3

我刚刚发现了一个新的皱纹.在我的应用程序中,ButtonResourceDictionary.xaml 被放置在一个类库中(即,在一个外部项目中).如果我将此文件移动到本地文件夹,则一切正常.因此,问题似乎是由于引用各种外部资源字典而导致的不良交互.我正在更正我的 App.xaml 代码片段(上面)以反映 ButtonResourceDictionary 实际上是在外部定义的.

I just discovered a new wrinkle. In my app, ButtonResourceDictionary.xaml is placed in a class library (i.e., in an external project). If I move this file to a local folder, everything works fine. So, the problem seems to be a bad interaction caused by referencing various external resource dictionaries. I'm correcting my App.xaml code snippet (above) to reflect that ButtonResourceDictionary is actually defined externally.

推荐答案

我希望您在此期间找到了解决方案.对于其他所有人,这里有一个解决方法,这里是另一个.不过,我不确定这是否对您的具体情况有帮助(尤其是您引用了嵌入式资源字典这一事实).

I hope you've found a solution in the meantime. For everyone else, here is one workaround, and here is another. I am not sure whether this will help for your specific case though (especially the fact that you reference an embedded resource dictionary).

更新

这是我想出的解决方案:

Here's a solution I came up with:

<Style TargetType="TextBox" BasedOn="{Common:StaticApplicationResource {x:Type TextBox}}">
    <Setter Property="Height" Value="21"/>
</Style>

其中 StaticApplicationResource 是我编写的自定义 MarkupExtension,它只调用 TryFindResource:

Where StaticApplicationResource is a custom MarkupExtension I wrote that simply calls TryFindResource:

[MarkupExtensionReturnType(typeof(object))]
public class StaticApplicationResource : MarkupExtension
{
    public StaticApplicationResource(object pResourceKey)
    {
        mResourceKey = pResourceKey;
    }

    private object _ResourceKey;

    [ConstructorArgument("pResourceKey")]
    public object mResourceKey
    {
        get { return _ResourceKey; }
        set { _ResourceKey = value; }
    }

    public override object ProvideValue(IServiceProvider serviceProvider)
    {
        if (mResourceKey == null)
            return null;

        object o = Application.Current.TryFindResource(mResourceKey);

        return o;
    }
}

这样我就不必在我的 App.xaml 文件之外引用我的资源字典,这是我喜欢的方式:).您也可以在其中放置更复杂的逻辑,允许您以任何您喜欢的方式解析 BasedOn 样式.这是一篇很棒的文章,向您展示了如何加载来自代码的资源字典(以及框架自动解析的资源字典).

This way I don't have to reference my resource dictionaries outside of my App.xaml file , which is the way I like it :). You can also put more complicated logic in there too, allowing you to resolve the BasedOn style any way you like. Here is an excellent article showing you how to load resource dictionaries (and those that the framework resolves automatically) from code.

这篇关于如何在不将 WPF 从 Aero 恢复为 Classic 的情况下更改按钮的默认样式?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆