wpf - 如何仅更改子类中 DependencyProperty 元数据的一个选项?

标签 wpf dependency-properties measureoverride

我们需要覆盖 DependencyProperty我们子类的元数据。现在我知道我可以使用 OverrideMetadata并指定全新的 FrameworkPropertyMetadata对象,但在大多数情况下,我希望这个新元数据与现有元数据完全相同,除了设置了一个额外的标志(特别是 AffectsMeasure )

我的想法是获取现有的元数据,创建一个新的元数据对象,将所有成员从旧的手动复制到新的(它不支持 Clone)更改我想要的一个,然后使用新的OverrideMetadata 调用。但是 da** 对于其他如此简单的事情来说,这是一项艰巨的工作!

我在这里错过了什么吗?

编辑

首先,我的意思是AffectsMeasure不是 AffectsRender (我在上面已经改变了),

但是...我刚刚发现我们类已经有了 AffectsMeasureWidth 设置的标志属性(property)。真正的问题在于 ListBox 的容器(例如 ListBoxItem) MeasureOverride仅在首次初始化时调用一次。

由于这在技术上是一个不相关的问题,我将开始一个新问题并关闭这个问题。

这是新问题的链接:

Why is a ListBoxItem not calling MeasureOverride when its width is changed?

最佳答案

从基类的元数据复制元数据绝对是要走的路。虽然不幸的是FrameworkPropertyMetadata类不公开他们给出的标志,他们公开为 bool属性来表示它们的状态。将这些值作为 FrameworkPropertyMetadataOptions 取回,您必须查看关联的属性并将它们作为一个整体读回。

static DerivedClass()
{
    var oldMeta = (FrameworkPropertyMetadata)BaseClass.SomeProperty.GetMetadata(typeof(BaseClass));
    var flags = GetFlags(oldMeta);

    // change the values as needed
    var meta = new FrameworkPropertyMetadata(
        oldMeta.DefaultValue,
        flags,
        oldMeta.PropertyChangedCallback,
        oldMeta.CoerceValueCallback,
        oldMeta.IsAnimationProhibited,
        oldMeta.DefaultUpdateSourceTrigger
    );

    BaseClass.SomeProperty.OverrideMetadata(typeof(DerivedClass), meta);
}

static FrameworkPropertyMetadataOptions GetFlags(FrameworkPropertyMetadata metadata)
{
    FrameworkPropertyMetadataOptions flags = FrameworkPropertyMetadataOptions.None;
    if (metadata.AffectsArrange)
        flags |= FrameworkPropertyMetadataOptions.AffectsArrange;
    if (metadata.AffectsMeasure)
        flags |= FrameworkPropertyMetadataOptions.AffectsMeasure;
    if (metadata.AffectsParentArrange)
        flags |= FrameworkPropertyMetadataOptions.AffectsParentArrange;
    if (metadata.AffectsParentMeasure)
        flags |= FrameworkPropertyMetadataOptions.AffectsParentMeasure;
    if (metadata.AffectsRender)
        flags |= FrameworkPropertyMetadataOptions.AffectsRender;
    if (metadata.BindsTwoWayByDefault)
        flags |= FrameworkPropertyMetadataOptions.BindsTwoWayByDefault;
    if (metadata.Inherits)
        flags |= FrameworkPropertyMetadataOptions.Inherits;
    if (metadata.Journal)
        flags |= FrameworkPropertyMetadataOptions.Journal;
    if (metadata.IsNotDataBindable)
        flags |= FrameworkPropertyMetadataOptions.NotDataBindable;
    if (metadata.OverridesInheritanceBehavior)
        flags |= FrameworkPropertyMetadataOptions.OverridesInheritanceBehavior;
    if (metadata.SubPropertiesDoNotAffectRender)
        flags |= FrameworkPropertyMetadataOptions.SubPropertiesDoNotAffectRender;
    return flags;
}

关于wpf - 如何仅更改子类中 DependencyProperty 元数据的一个选项?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/7643670/

相关文章:

c# - 在一个窗口中打开多个链接,然后在另一个窗口中打开多个链接

wpf - 无法在 Windows 8(WPF、.NET 4.0)下横向打印文档

c# - 如何隐藏没有可见项目的上下文菜单?

wpf - 如何使用子定义的附加属性?

c# - 在 Silverlight 4.0 中子类化 FrameworkElement - 测量通过问题

wpf - 如何拉伸(stretch) HeaderedContentControl 的内容?

c# - ViewModel 之间的 WPF 数据绑定(bind)

c# - 从标签 : are custom properties (with DP) not using the setter? 派生的 WPF 控件

wpf - Panel.Children 与 Panel.InternalChildren - 有什么区别?