禁用时未显示任何内容的WPF ComboBox(IsEnabled == false)

时间:2011-01-19 21:06:41

标签: wpf combobox styles isenabled control-template

我正在想办法让WPF ComboBox显示为空白,就像IsEnabled设置为false时一样,没有选择任何内容。就像我一直在努力做到这一点,而不必重新定义ComboBox的整个控件模板,这总是我与WPF的斗争。如果有人比重新定义整个ComboBox控制模板更优雅,请告诉我。

我尝试做的原因是我有一个CheckBox表示“全部”选项,当选中它时会禁用ComboBox,用于仅选择一个单独的项目。如果我的CheckBox被选中,则有时会让用户感到困惑,因为该值在该状态下没有任何意义,因此可以看到ComboBox中剩余的值。

另一个要求是,该解决方案无法修改SelectedValue的{​​{1}},SelectedIndexSelectedItem值,因为我希望保留之前预先选择的项目用户取消选中“全部”ComboBox

的情况

基于HCL答案的解决方案:

CheckBox

3 个答案:

答案 0 :(得分:1)

您可以使用触发器执行某些操作:

禁用该框时,尝试将ItemTemplate设置为空DataTemplate。这将影响所选项目的呈现,因此将其隐藏 另一个简单但不太好的解决方案是将前景色设置为与背景色相同。

答案 1 :(得分:0)

我相信你可以用Style做到这一点,而不是重新定义控件模板。使用IsEnabled属性上的Trigger设置ComboBox中显示的文本。更改SelectedItem将是我的第一种方法,但由于您不想这样做,您可能会发现设置DisplayMemberPath成功。这样的事情(未经测试)......

<Style TargetType="{x:Type ComboBox}">
    <Style.Triggers>
        <Trigger Property="IsEnabled" Value="False">
            <Trigger.Setters>
                <Setter Property="DisplayMemberPath" Value="{x:Null}"/>
            </Trigger.Setters>
        </Trigger>
    </Style.Triggers>
</Style>

答案 2 :(得分:0)

这是一种可以满足您需求的风格。它采用了我一直使用的技术:包含控件的多个版本的网格,以及确保一次只能看到一个版本的数据触发器。

    <ComboBox.Style>
      <Style TargetType="ComboBox">
        <Setter Property="Template">
          <Setter.Value>
            <ControlTemplate TargetType="ComboBox">
              <DockPanel>
                <CheckBox x:Name="IsActive" DockPanel.Dock="Left"/>
                <Grid>
                  <ComboBox
                    ItemsSource="{TemplateBinding ItemsSource}"
                    SelectedItem="{TemplateBinding SelectedItem}"
                    SelectedIndex="{TemplateBinding SelectedIndex}"
                    SelectedValue="{TemplateBinding SelectedValue}">
                    <ComboBox.Style>
                      <Style TargetType="ComboBox">
                        <Setter Property="Visibility" Value="Visible"/>
                        <Style.Triggers>
                          <DataTrigger Binding="{Binding ElementName=IsActive, Path=IsChecked}" Value="False">
                            <Setter Property="Visibility" Value="Collapsed"/>
                          </DataTrigger>
                        </Style.Triggers>
                      </Style>
                    </ComboBox.Style>
                  </ComboBox>
                  <ComboBox>
                    <ComboBox.Style>
                      <Style TargetType="ComboBox">
                        <Setter Property="Visibility" Value="Collapsed"/>
                        <Style.Triggers>
                          <DataTrigger Binding="{Binding ElementName=IsActive, Path=IsChecked}" Value="False">
                            <Setter Property="Visibility" Value="Visible"/>
                          </DataTrigger>
                        </Style.Triggers>
                      </Style>
                    </ComboBox.Style>                      
                  </ComboBox>
                </Grid>
              </DockPanel>
            </ControlTemplate>
          </Setter.Value>
        </Setter>
      </Style>
    </ComboBox.Style>

这样可以根据需要保留所选项目,所选索引和所选值。事实上,它做得太好了;实际上并没有告诉用户停用组合框的方法,因为ComboBox上没有公开此信息的属性。我可能实际上将此实现为从ComboBox派生的自定义控件,该控件将复选框的值公开为IsActive属性。还有很多其他方法可以做到。