DataTrigger 使 WPF 按钮处于非活动状态,直到 TextBox 具有值

发布于 2024-10-11 08:44:04 字数 873 浏览 1 评论 0原文

我希望 Button 控件的属性为 IsEnabled="False",直到将值输入到 Window 中的 TextBox 中为止代码>.

到目前为止的代码:

<Button
  Content="Click Me"
  Name="ClickMe"
  VerticalAlignment="Top"
  Click="ClickMe_Click">
  <Button.Style>
    <Style>
      <Style.Triggers>
        <DataTrigger
          Binding="{Binding ElementName=textBox, Path=Length}"
          <!-- or even: Binding="{Binding Path=textBox.Length}" -->
          Value="0">
          <Setter
            Property="Button.IsEnabled"
            Value="false" />
          </DataTrigger>
      </Style.Triggers>
    </Style>
  </Button.Style>
</Button>

此外,是否可以让此 Button 控件的 IsEnabled 属性基于 3 个不同的 TextBox控制所有有价值观的人?

I want the Button control's property to be IsEnabled="False" until a value is entered into a TextBox in the Window.

Code so far:

<Button
  Content="Click Me"
  Name="ClickMe"
  VerticalAlignment="Top"
  Click="ClickMe_Click">
  <Button.Style>
    <Style>
      <Style.Triggers>
        <DataTrigger
          Binding="{Binding ElementName=textBox, Path=Length}"
          <!-- or even: Binding="{Binding Path=textBox.Length}" -->
          Value="0">
          <Setter
            Property="Button.IsEnabled"
            Value="false" />
          </DataTrigger>
      </Style.Triggers>
    </Style>
  </Button.Style>
</Button>

Also, is it possible to have this Button control's IsEnabled property be based on 3 different TextBox controls all having values?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

心在旅行 2024-10-18 08:44:04

假设您正在使用表示模型(例如 ViewModel),您应该直接绑定数据而不是 UI 元素。

<Style.Triggers>
    <MultiDataTrigger>
        <MultiDataTrigger.Conditions>
            <Condition Binding="{Binding FirstName}" Value="{x:Null}" />
            <Condition Binding="{Binding MiddleName}" Value="{x:Null}" />
            <Condition Binding="{Binding LastName}" Value="{x:Null}" />
        </MultiDataTrigger.Conditions>
        <Setter Property="Button.IsEnabled" Value="False" />
    </MultiDataTrigger>
</Style.Triggers>

也就是说,如果您使用的是表示模型,则始终可以添加 bool“EnableSave”属性并在那里处理所有表示逻辑,而不是在视图本身中。

更新

从注释中可以看出,我错误地将其设置为在 any TextBox 有值时启用 Button,但要求是当所有 TextBox 都有值时启用Button

从概念上讲,您所要做的就是反转条件 - 我们想要的是“如果所有条件都为真,则为真”,而不是“如果所有条件都为假,则为假”。

问题在于,无法在 XAML 中表示“not null”——也就是说,如果没有 IValueConverter,就不可能。我将创建一个 NullToBoolConverter,它对于 null 返回 false,对于 != null 返回 true代码>.

给定这样一个转换器:

<Style.Triggers>
    <MultiDataTrigger>
        <MultiDataTrigger.Conditions>
            <Condition Binding="{Binding FirstName,
                Converter={StaticResource NullToBoolConverter}}" Value="True" />
            <Condition Binding="{Binding MiddleName,
                Converter={StaticResource NullToBoolConverter}}" Value="True" />
            <Condition Binding="{Binding LastName,
                Converter={StaticResource NullToBoolConverter}}" Value="True" />
        </MultiDataTrigger.Conditions>
        <Setter Property="Button.IsEnabled" Value="True" />
    </MultiDataTrigger>
</Style.Triggers>

Assuming you are employing a presentation model, such as a ViewModel, you should bind directly the data instead of the UI elements.

<Style.Triggers>
    <MultiDataTrigger>
        <MultiDataTrigger.Conditions>
            <Condition Binding="{Binding FirstName}" Value="{x:Null}" />
            <Condition Binding="{Binding MiddleName}" Value="{x:Null}" />
            <Condition Binding="{Binding LastName}" Value="{x:Null}" />
        </MultiDataTrigger.Conditions>
        <Setter Property="Button.IsEnabled" Value="False" />
    </MultiDataTrigger>
</Style.Triggers>

That said, if you are using a presentation model, you can always add a bool "EnableSave" property and handle all the presentation logic there instead of in the view itself.

update

As can be seen by following the comments, I mistakenly set this up to enable the Button when any TextBox has a value, but the requirement is that the Button be enabled when all TextBoxes have values.

Conceptually, all you have to do is reverse the conditions -- instead of "false if all conditions false," we want "true if all conditions true."

The catch is that there is no way to say "not null" in the XAML -- no way without an IValueConverter, that is. I'd create a NullToBoolConverter that returns false for null and true for != null.

Given such a converter:

<Style.Triggers>
    <MultiDataTrigger>
        <MultiDataTrigger.Conditions>
            <Condition Binding="{Binding FirstName,
                Converter={StaticResource NullToBoolConverter}}" Value="True" />
            <Condition Binding="{Binding MiddleName,
                Converter={StaticResource NullToBoolConverter}}" Value="True" />
            <Condition Binding="{Binding LastName,
                Converter={StaticResource NullToBoolConverter}}" Value="True" />
        </MultiDataTrigger.Conditions>
        <Setter Property="Button.IsEnabled" Value="True" />
    </MultiDataTrigger>
</Style.Triggers>
oО清风挽发oО 2024-10-18 08:44:04

TextBox 没有 Length 属性。将绑定路径设置为 Text.Length 可能会起作用。

但更灵活的解决方案是使用 Converter< /a>,它可以根据传入的字符串值返回 true 或 false。然后,您可以绑定到 TextBox 的 Text 属性,如下所示:

在控件的资源中:

<localNamespace:MyEmptyStringToBooleanValueConverter x:Key="myValueConverter"/>

您的 DataTrigger 定义如下所示:

<DataTrigger Binding="{Binding ElementName=textBox, Path=Text, 
                               Converter={StaticResource myValueConverter}}"   
             Value="False">

至于您的第二个请求,您可以使用 多重绑定。在这种情况下,您必须使用值转换器来定义如何解释绑定结果。有关详细信息,请参阅链接的教程。

TextBox doesn't have a Length property. Setting your binding Path to Text.Length might work.

But a more-flexible solution would be to use a Converter, which can return true or false based on the value of the string passed into it. You can then bind to the TextBox's Text property, like so:

In your control's Resources:

<localNamespace:MyEmptyStringToBooleanValueConverter x:Key="myValueConverter"/>

Your DataTrigger definition then looks like this:

<DataTrigger Binding="{Binding ElementName=textBox, Path=Text, 
                               Converter={StaticResource myValueConverter}}"   
             Value="False">

As for your second request, you can use a MultiBinding. In this case, you must use a value converter to define how the results of the binding should be interpreted. See the linked tutorial for details.

゛时过境迁 2024-10-18 08:44:04

使用属性 x:Name="FirstName" 以及类似的其他代码,可以在数据出现在所有字段中时启用该按钮。

<Button.Style>
    <Style>
        <Style.Triggers>
            <DataTrigger Binding="{Binding ElementName=FirstName,Path=Text.Length, Mode=OneWay}" Value="0">
            <Setter Property="Button.IsEnabled" Value="False" />
            </DataTrigger>
            <DataTrigger Binding="{Binding ElementName=MiddleName,Path=Text.Length, Mode=OneWay}"  Value="0">
            <Setter Property="Button.IsEnabled" Value="False" />
            </DataTrigger>
            <DataTrigger Binding="{Binding ElementName=LastName,Path=Text.Length, Mode=OneWay}" Value="0">
            <Setter Property="Button.IsEnabled" Value="False" />
            </DataTrigger>                  
         </Style.Triggers>
     </Style>
 </Button.Style>

Using property x:Name="FirstName" and similarly for others following code will work to enable the button when the data is present in all the fields.

<Button.Style>
    <Style>
        <Style.Triggers>
            <DataTrigger Binding="{Binding ElementName=FirstName,Path=Text.Length, Mode=OneWay}" Value="0">
            <Setter Property="Button.IsEnabled" Value="False" />
            </DataTrigger>
            <DataTrigger Binding="{Binding ElementName=MiddleName,Path=Text.Length, Mode=OneWay}"  Value="0">
            <Setter Property="Button.IsEnabled" Value="False" />
            </DataTrigger>
            <DataTrigger Binding="{Binding ElementName=LastName,Path=Text.Length, Mode=OneWay}" Value="0">
            <Setter Property="Button.IsEnabled" Value="False" />
            </DataTrigger>                  
         </Style.Triggers>
     </Style>
 </Button.Style>
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文