【问题标题】:WPF + MVVM: Override autocomplete in DataGridComboBoxColumnWPF + MVVM:覆盖 DataGridComboBoxColumn 中的自动完成功能
【发布时间】:2014-05-26 14:16:46
【问题描述】:

我已经搜索了很长时间,但无法弄清楚如何覆盖 DataGridComboBoxColumn 中的自动完成功能。

我想做的是这里解释的,除了一个组合框:Searching for items in a list box

即:我希望能够输入任何字符串,然后对 DataGridComboBoxColumn 中的 ComboBox 项应用过滤器,以仅将与此匹配的那些项显示为子字符串

我是 WPF 新手,已经在网上搜索了一段时间。我找到了诸如 EventSetters 和 CommandBehaviorCollection.Behaviors 之类的东西,但我无法清楚地了解可能性(和不可能性)。

我有:

  <DataGrid ... >
    ...
    <DataGrid.Columns>
      ...
      <MyCustomDataGridComboBoxColumn Header="My Header" MinWidth="200" >
        <DataGridComboBoxColumn.ElementStyle>
          <Style TargetType="ComboBox">
            <Setter Property="ItemsSource" Value="{Binding DataContext.MyData, RelativeSource={RelativeSource AncestorType={x:Type DataGrid}}}" />
            <Setter Property="SelectedItem" Value="{Binding DataItem, UpdateSourceTrigger=LostFocus, ValidatesOnDataErrors=True}" />
            <Setter Property="DisplayMemberPath" Value="HardwareId" />
          </Style>
        </DataGridComboBoxColumn.ElementStyle>
        <DataGridComboBoxColumn.EditingElementStyle>
          <Style TargetType="ComboBox">
            <Setter Property="ItemsSource" Value="{Binding DataContext.MyFilteredData, RelativeSource={RelativeSource AncestorType={x:Type DataGrid}}}" />
            <Setter Property="SelectedItem" Value="{Binding DataItem, UpdateSourceTrigger=LostFocus}" />
            <Setter Property="DisplayMemberPath" Value="HardwareId" />
            <Setter Property="IsEditable" Value="True"/>
            <Setter Property="Text" Value="{Binding DataContext.MyNewDataItem, RelativeSource={RelativeSource AncestorType={x:Type DataGrid}}, UpdateSourceTrigger=LostFocus, ValidatesOnDataErrors=True, NotifyOnValidationError=True}" />
          </Style>
        </DataGridComboBoxColumn.EditingElementStyle>
      </MyCustomDataGridComboBoxColumn>
      ...
    </DataGrid.Columns>
  </DataGrid>

理想情况下,我想创建一个继承自 DataGridComboBoxColumn 的新类,并为其提供一些自定义逻辑,例如在其构造函数中提供一个匿名函数,以便将来可以以不同的方式覆盖自动完成行为。

这有可能吗,还是我完全走错了路?

【问题讨论】:

    标签: c# wpf mvvm combobox autocomplete


    【解决方案1】:

    我并不是说您的方法是错误的,但是,我会以不同的方式处理它。对我来说,使用 DataGridTemplateColumn 并提供具有您所说的功能的 ComboBox 似乎更容易。

    <DataGridTemplateColumn Header="ColumnName" Width="*">
      <DataGridTemplateColumn.CellTemplate>
        <DataTemplate>
          <Grid>
            <YourCustomComboBox/>
          </Grid>
        </DataTemplate>
      </DataGridTemplateColumn.CellTemplate>
    </DataGridTemplateColumn>
    

    编辑:

    不久前,我需要一个具有相同功能的 ComboBox。我最终将 TextBox 与 Popup 控件组合在一起,因为它让我可以更好地控制它。

    <TextBox Text="{Binding Text, UpdateSourceTrigger=PropertyChanged}" x:Name="editBox"/>
    <Popup x:Name="textboxPopup" Width="{Binding ElementName=editBox, Path=ActualWidth, Mode=OneWay}"
                         PlacementTarget="{Binding ElementName=editBox}"
                         StaysOpen="False"
                         IsOpen="{Binding Path=IsOpen, Mode=OneWay}">
      <Grid>
        <DockPanel MaxHeight="500">
          <ListView SelectionMode="Single"
                  ItemsSource="{Binding Path=Suggestions}"
                  Name="popupList">
            <ListView.ItemContainerStyle>
              <Style TargetType="ListViewItem">
                <Style.Resources>
                <SolidColorBrush x:Key="{x:Static SystemColors.HighlightBrushKey}"Color="LightBlue"/>
                  <SolidColorBrush x:Key="{x:Static SystemColors.ControlBrushKey}" Color="LightBlue"/>
              </Style.Resources>
              <Style.Triggers>
                <Trigger Property="IsMouseOver" Value="true">
                  <Setter Property="Background" Value="LightBlue"/>
                </Trigger>
              </Style.Triggers>
            </Style>
          </ListView.ItemContainerStyle>
        </ListView>
      </DockPanel>
    </Grid>
    

    在代码隐藏中,我订阅了 TextChanged 事件和其他一些派上用场的事件。我不能分享我所有的代码,因为它是生产代码。但是,互联网上还有一些其他人具有类似的实现:using a ComboBoxusing a textbox,当然还有您在问题中发布的链接。那里有足够的东西。

    关于将您的自定义控件用作 TargetType... 我认为这没有什么问题,我一直都这样做。

    不应发生 CellTemplate 的错误。你使用正确吗? See this link for an example.

    【讨论】:

    • 嗨 Martijn,感谢您的回复。我已经从已经是一个自定义类的 DataGridComboBoxColumn 中抽象出来了。我现在不打算改变这一点。但是,我也可以这样做
    • 编辑:请注意,使用您的建议时,我收到错误“无法识别或无法访问成员“CellTemplate”。”
    • 嗨@Diana,我扩展了我的答案来解决你的cmets。
    • 嗨 Martijn,感谢您的更新。然而,不幸的是,这并没有让我更接近解决方案。我一直在网上搜索诸如触发器、行为之类的东西,但我找不到没有代码隐藏的示例(这与 MVVM 相悖)
    猜你喜欢
    • 2017-07-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-09-24
    • 2012-02-17
    • 2022-08-15
    • 2018-05-27
    相关资源
    最近更新 更多