3

我有一个包含三列的网格:

  1. 友好名称
  2. 大陆名称
  3. 国家的名字

第一列是可编辑的文本框列。第二列是显示大陆列表的组合框。第 3 列是一个组合框,显示基于在第 2 列中选择的大陆的国家列表。我想为这些列实现单击。我尝试了此链接中给出的解决方案 Single click edit in WPF DataGrid

但这仅适用于第一列,而不适用于其他两个 (DataGridTemplateColumn) 列。

这怎么可能。请建议。下面给出了示例 XAML 和数据描述。

<DataGrid Grid.Row="1" VerticalAlignment="Top"
                                   ItemsSource="{Binding Path=GeographyData,Mode=TwoWay,UpdateSourceTrigger=PropertyChanged}"
                                  Style="{StaticResource DataGridStyleNormal}">
                            <DataGrid.Columns>
                                <DataGridTextColumn Width="*" Header="Friendly name" Binding="{Binding Path=FriendlyName,Mode=TwoWay,UpdateSourceTrigger=PropertyChanged}"/>
                                <!--FilterDef -->
                                <DataGridTemplateColumn Width="*"
                                                        Header="Continents">
                                    <DataGridTemplateColumn.CellEditingTemplate>
                                        <DataTemplate>
                                            <ComboBox SelectedValue="{Binding ContinentId, Mode=TwoWay}"
                                                      SelectedValuePath="ID"
                                                      DisplayMemberPath="Name"
                                                      ItemsSource="{Binding Path=DataContext.ContinentsAndCountries,Mode=OneWay,UpdateSourceTrigger=PropertyChanged,RelativeSource={RelativeSource Mode=FindAncestor,AncestorType={x:Type DataGrid}}}"/>
                                        </DataTemplate>
                                    </DataGridTemplateColumn.CellEditingTemplate>
                                    <DataGridTemplateColumn.CellTemplate>
                                        <DataTemplate>
                                            <TextBlock>
                                               <TextBlock.Text>
                                                    <MultiBinding Converter="{StaticResource ContinentCaptionConverter}">
                                                          <Binding Path="ContinentId"/>
                                                          <Binding Path="DataContext.ContinentsAndCountries" RelativeSource="{RelativeSource Mode=FindAncestor,AncestorType={x:Type DataGrid}}"/>
                                                        </MultiBinding>
                                                </TextBlock.Text>
                                            </TextBlock>
                                        </DataTemplate>
                                    </DataGridTemplateColumn.CellTemplate>
                                </DataGridTemplateColumn>
                                <!--Level-->
                                <DataGridTemplateColumn Width="*"
                                                        Header="Countries">
                                    <DataGridTemplateColumn.CellEditingTemplate>
                                        <DataTemplate>
                                            <ComboBox SelectedValue="{Binding CountryId, Mode=TwoWay}"
                                                      SelectedValuePath="ID"
                                                      DisplayMemberPath="Name">
                                                <ComboBox.ItemsSource>
                                                    <MultiBinding Converter="{StaticResource CountryValuesConverter}">
                                                        <Binding Path="DataContext.ContinentsAndCountries" RelativeSource="{RelativeSource Mode=FindAncestor,AncestorType={x:Type DataGrid}}"/>
                                                        <Binding Path="ContinentId"/>
                                                    </MultiBinding>
                                                </ComboBox.ItemsSource>
                                            </ComboBox>
                                        </DataTemplate>
                                    </DataGridTemplateColumn.CellEditingTemplate>
                                    <DataGridTemplateColumn.CellTemplate>
                                        <DataTemplate>
                                            <TextBlock>
                                               <TextBlock.Text>
                                                    <MultiBinding Converter="{StaticResource CountryCaptionConverter}">
                                                            <Binding Path="DataContext.ContinentsAndCountries" RelativeSource="{RelativeSource Mode=FindAncestor,AncestorType={x:Type DataGrid}}"/>
                                                            <Binding Path="ContinentId"/>
                                                            <Binding Path="CountryId"/>
                                                        </MultiBinding>
                                                </TextBlock.Text>
                                            </TextBlock>
                                        </DataTemplate>
                                    </DataGridTemplateColumn.CellTemplate>
                                </DataGridTemplateColumn>
                            </DataGrid.Columns>
                        </DataGrid>

注意:数据“ContinentsAndCountries”是一个可观察的主从数据集合。

  • 吉里哈
4

2 回答 2

5

我通过设置组合框加载事件来做到这一点

private void DataGridComboboxTemplate_Loaded(object sender, RoutedEventArgs e)
    {
        if (sender != null)
        {
            ComboBox cmb = sender as ComboBox;
            cmb.IsDropDownOpen = true;
        }
    }
于 2012-04-25T15:02:58.847 回答
1

对不起,他死了;我终于想出了如何制作真正的单击 UX。您必须拦截 DataGridCell 的 OnGotFocus 事件,将单元格的模式设置为 IsEditing,然后在CellEditingTemplate中拦截 Actor 控件的 Loaded 事件:

<Window.Resources>
    <Style
        x:Key="AutoEditModeOnClick"
        TargetType="{x:Type DataGridCell}">

        <EventSetter Event="GotFocus" Handler="DataGridCell_OnGotFocus" />
    </Style>
</Window.Resources>

<DataGrid.Columns>
    <DataGridTemplateColumn
        CellStyle="{StaticResource AutoEditModeOnClick}"
        Header="Score">

        <!-- Example with ComboBox -->

        <DataGridTemplateColumn.CellTemplate>
            <DataTemplate>
                <!-- Some more XAML -->
            </DataTemplate>
        </DataGridTemplateColumn.CellTemplate>

        <DataGridTemplateColumn.CellEditingTemplate>
            <DataTemplate>
                <!-- Some more XAML -->
                <ComboBox
                    DisplayMemberPath="Description"
                    SelectedValuePath="RecordID"
                    SelectedValue="{Binding Score,
                        TargetNullValue=0,
                        UpdateSourceTrigger=PropertyChanged}"
                    ItemsSource="{Binding DataContext.ScoreOptions,
                        RelativeSource={RelativeSource
                            AncestorType={x:Type DataGrid}}}"
                    Loaded="Combobox_Loaded"/>
            </DataTemplate>
        </DataGridTemplateColumn.CellEditingTemplate>
    </DataGridTemplateColumn>

    <DataGridTemplateColumn
        CellStyle="{StaticResource AutoEditModeOnClick}"
        Header="Comment">

        <!-- Example with TextBox -->

        <DataGridTemplateColumn.CellTemplate>
            <DataTemplate>
                <!-- Some more XAML -->
            </DataTemplate>
        </DataGridTemplateColumn.CellTemplate>

        <DataGridTemplateColumn.CellEditingTemplate>
            <DataTemplate>
                <!-- Some more XAML -->
                <TextBox
                    Loaded="TextBox_Loaded"
                    Text="{Binding Comment,
                        UpdateSourceTrigger=LostFocus}"/>
            </DataTemplate>
        </DataGridTemplateColumn.CellEditingTemplate>
    </DataGridTemplateColumn>
</DataGrid.Columns>

在您的代码隐藏中,您需要三个处理程序;一个用于单元格,一个用于每种类型的控件(组合框、文本框):

    /// <summary>
    /// Skips the 'DataGridCell.Focus' step and goes straight into IsEditing
    /// </summary>
    private void DataGridCell_OnGotFocus(object sender, RoutedEventArgs e)
    {
        DataGridCell cell = sender as DataGridCell;
        cell.IsEditing = true;
    }

    /// <summary>
    /// Skips the 'IsEditing' step and goes straight into IsDropDownOpen
    /// </summary>
    private void Combobox_Loaded(object sender, RoutedEventArgs e)
    {
        ComboBox comboBox = sender as ComboBox;
        comboBox.IsDropDownOpen = true;
    }

    /// <summary>
    /// Skips the 'IsEditing' step and goes straight into Focus
    /// </summary>
    private void TextBox_Loaded(object sender, RoutedEventArgs e)
    {
        TextBox textBox = sender as TextBox;
        textBox.Focus();
    }
于 2016-01-25T07:26:17.077 回答