XAML 绑定到另一个元素的反面

Posted

技术标签:

【中文标题】XAML 绑定到另一个元素的反面【英文标题】:XAML Binding to the opposite of another element 【发布时间】:2011-11-24 06:49:33 【问题描述】:

我正在开发一个简单的练习,并想知道是否有一种方法可以仅使用 。例如。我在表单上有两个按钮,开始和停止也许是一个计时器。我不希望两者同时启用。当程序启动时,停止按钮应该被禁用。单击开始按钮时,应禁用它并启用停止按钮。然后反之亦然,直到用户退出。

我知道对此有更好的控制,而且我知道在代码中很容易做到。我只是想知道 XAML 中是否有某种 NOT 运算符可能看起来像这样:

<Button Content="_Start" Name="btnStart"/>
<Button Content="_Stop" Name="btnStop"
        IsEnabled="Binding ElementName=btnStart,
                    Path=Not(IsEnabled)"/>

或者类似的东西:

                    Path != IsEnabled"/>

甚至是这样的:

                    Path=IsEnabled.Not()"/>

我知道我可以直接绑定到开始按钮,但是当一个被启用时,另一个也是如此,当它被禁用时也是如此。看看我从哪里来。

我什至愿意接受某种 XAML 验证方法,它首先检查开始按钮的状态并强制停止按钮的状态相反。或任何其他不需要代码隐藏的类似黑客或解决方法。

感谢您对此的任何帮助。

编辑: 请记住,关键是没有代码落后。如果我必须在后面编写一行代码,我不妨只使用 onclick 事件处理程序和一个简单的 ?: 运算符。所以我只想要可以直接在 XAML 中工作的东西。

【问题讨论】:

相关:***.com/questions/2580467/… 【参考方案1】:

没有开箱即用的Not 操作。但是,使用自定义转换器很容易实现这一点:

public class NotConverter : IValueConverter

    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    
        return !(bool) value;
    

    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    
        return !(bool)value;
    

然后您可以将其指定为绑定上的转换器。

<Button Content="_Stop" Name="btnStop"
    IsEnabled="Binding ElementName=btnStart, Converter=StaticResource NotConverter Path=IsEnabled"/>

最后在您的窗口/页面上创建一个名为 NotConverter 的资源:

<Window.Resources>
    <ns:NotConverter x:Key="NotConverter" />
</Window.Resources>

您可以从MSDN获得有关IValueConverter的更多信息。

然后使用可以在任何你喜欢的地方使用这个值转换器。您可以将其从 Window 资源中拉出并使其成为应用程序级资源,这样您就不必在每个窗口中都指定它。

【讨论】:

@FrancisRodgers 如果想自己处理点击事件,那很好。但是你只需要编写这个值转换器一次。当您需要处理 17 个按钮时会发生什么情况?为所有 17 编写点击处理程序,还是编写一次值转换器?它可以重复使用。 好的,我明白你的意思。拍得很好。谢谢你。我仍然想知道我是否可以使用验证规则而不使用代码来做到这一点。只是为了好玩。 使用此方法时,我收到错误消息:“未找到类型 ns:NotConverter。验证您没有丢失程序集引用并且所有引用程序集都已构建”。我该如何解决这个问题。再次感谢。 @FrancisRodgers - 确保为 ns 添加一个 xmlns 到您的窗口/应用程序,这是您放置类型的名称空间。例如xmlns:ns="clr-namespace:Your.Namespace.Here" @FrancisRodgers 您可以在msdn.microsoft.com/en-us/library/ms747086.aspx了解有关 XAML 和命名空间的更多信息【参考方案2】:

如果我知道的话,你就不能绑定到 !Property,但是你可以写一个 IValueConverter 并在你的绑定中使用它。 这里详细解释了如何设置一个返回 Negated Boolean 值的 IValueConverter。

IValueConverter to negate a property

【讨论】:

如果没有代码,只有在 XAML 中,你能解释一下如何。我知道我可以使用代码来做到这一点,但是如果我必须编写一行代码,那么我不妨在代码中完成整个事情,因为它很容易实现和理解。所以我真正要寻找的是一些您通常不会每天看到的高级 XAML。如果是简单的 XAML,只要是没有任何代码的 XAML 就更好了。 在我的回答中的链接中,您可以阅读 Jobi Joy 的回答,他说使用 XAML 标记扩展可以在 xaml 中制作它,但它的工作量很大。而且我认为 IValueConverter 选项是最好的,因为您将来可以重用转换器,实际上非常简单,在转换和转换回方法中只有 2 行代码,然后您必须向您的应用程序添加资源,不要'不要忘记将 Converters 命名空间添加到您的 XAML,然后您将能够在您的绑定中使用转换器与 converter=StatickResource convertersresourcename

以上是关于XAML 绑定到另一个元素的反面的主要内容,如果未能解决你的问题,请参考以下文章

仅通过 XAML 将复选框绑定到元素可见性

C#如何在没有 XAML 的情况下创建到父元素的(两种方式)数据绑定

Knockout JS 将元素的属性绑定到另一个元素

wpf : 绑定到另一个 xaml 文件中的控件

如何在 XAML 元素中使用 StringFormat?

DataGridTextColumn 可见性绑定