【问题标题】:How do I use an explicitly implemented interface property and wpf visiblity together properly?如何正确使用显式实现的接口属性和 wpf 可见性?
【发布时间】:2013-12-03 06:01:38
【问题描述】:

我有以下情况:

我有几个 ViewModel 对象,其中一些实现了接口ISomeInterface,有些则没有。这些接口公开了一个名为SomeEnumeration (IEnumerable<T>) 的属性。

例如:

public sealed class ViewModelA : ViewModelBase, ISomeInterface
{
    // ...

    IEnumerable<Foo> ISomeInterface.SomeEnumeration
    {
        get { ...; }
    }
}

public sealed class ViewModelB : ViewModelBase
{
    // ...
}

到目前为止,我的 XAML 的设计方式是两个 ViewModel 都恰好具有我要绑定的属性(即PropertyAPropertyB 等)。我还没有遇到我要绑定的属性在我设置为DataContext 的 ViewModel 上不存在的情况。但是,现在我会...而且它将针对明确实现的属性(我不确定这是否会对 WPF 绑定引擎产生任何影响)。

基本上,我的 xaml 将如下所示:

<StackPanel
  Visiblity="{Binding Path=SomeEnumeration, Converter={StaticResource AnyConverter}">
    ...
</StackPanel>

我不确定这是否可行,因为:

  1. 并非每个DataContext 都会包含该属性(如果不包含,则应将其隐藏)...在这种情况下我该怎么办?
  2. 对于确实包含该属性的DataContexts,它是明确实现的...您必须先进行转换还是什么?

【问题讨论】:

    标签: c# wpf data-binding datacontext explicit-interface


    【解决方案1】:

    通常,当您想使用 WPF 数据绑定引擎时,您还需要使用 FallbackValueTargetNullValue 绑定属性。这些到底是做什么的?

    FallbackValue: 获取或设置绑定不能时的值 返回一个值。
    TargetNullValue:获取或设置使用的值 当源的值为null时在目标中。

    Jon 在this answer 中很好地解释了绑定引擎:

    Binding.DoNothing 是您主动返回的对象实例 价值转换器;它指示绑定引擎不更新 目标财产的价值。这是Josh的一个很好的例子 史密斯,你可能会用它来做什么。

    FallbackValue 是您在绑定上设置的属性;它允许您 在以下情况下指定要应用于目标属性的值:

    • 无法解析绑定源(例如错误的绑定路径),或者
    • 绑定属性值等于 DependencyProperty.UnsetValue,或
    • 用于绑定的值转换器引发异常,或
    • 用于绑定的值转换器返回 DependencyProperty.UnsetValue,或
    • 绑定管道生成的值对目标属性无效(例如类型错误)

    TargetNullValue 也是您在绑定上设置的属性;它允许你 指定要应用于目标属性的值,如果值 源属性的值为空。例如,如果您将一个文本框绑定到 字符串属性 TargetNullValue 可让您选择出现在 如果源字符串为空,则为文本框。


    就绑定到“显式实现的接口”而言,真正的问题应该是如何设置接口属性的路径,因为如何实现该接口并不重要。这在 XAML 中其实很容易做到,这里有一个例子:

    <TextBox Text="{Binding Path=(local:ISomeInterface.SomeProperty)}" />
    

    所以,直接回答你的问题:

    1. 使用FallbackValue(必要时也可以使用TargetNullValue)。例如,由于绑定错误而无法解析绑定值时,传入 null。
    2. 使用正确的模式将 Path 属性绑定到接口的属性(参见上面的示例)。

    XAML 用法:

    <StackPanel Visiblity="{Binding Path=(local:ISomeInterface.SomeEnumeration),
                                    Converter={StaticResource AnyConverter},
                                    FallbackValue={x:Null}}">
        ...
    </StackPanel>
    

    最后一点:如果绑定提前失败,则 null FallbackValue 将不是传递给转换器的值,无论绑定在属性级别还是转换器级别等失败,它都将是最终使用的值。所以不要指望转换器在将 null 传入它时仍然会运行。

    【讨论】:

      【解决方案2】:

      对您的情况来说,一个快速而好的解决方法是将您的所有逻辑放在已经到位的转换器中。

      xaml : (你的绑定)

       <StackPanel
             Visiblity="{Binding Path=., Converter={StaticResource AnyConverter}">
             ...
       </StackPanel>
      

      cs : (你的转换器)

        Convert()
        {
             return value Is ISomeInterface ? 
                    (((ISomeInterface)value).SomeEnumeration == SomeEnumeration.SomeValue ? 
                    Visibility.Visible :  Visibility.Collapsed) : Visibility.Collapsed;       
        }
      

      【讨论】:

        猜你喜欢
        • 2013-02-04
        • 1970-01-01
        • 2016-03-27
        • 1970-01-01
        • 1970-01-01
        • 2020-08-24
        • 2014-07-11
        • 1970-01-01
        相关资源
        最近更新 更多