web-dev-qa-db-ja.com

プログラムでWPFDataGridの行またはセルを選択するにはどうすればよいですか?

WinForm DataGridViewでは、初期化時に最初の行を自動的に選択します。その機能をオフにしようとしたとき、それは私を夢中にさせました。 WPF DataGridに移行すると、Microsoftはこの機能をオフにすることを決定したようです。これは良いことだと思います。ただし、現在この機能を有効にするのに苦労しています。一部のDataGridでは、データバインディングを介してグリッドにデータが入力された後、最初の行が自動的に選択されるようにします。インターネットにはいくつかの提案がありますが、私はそれを機能させることができませんでした。ここでの幸運を祈っています。

9
newman

セットする IsSynchronizedWithCurrentItem = "true"

編集:

あなたのコメントに対処するために、DataGridのSelectionUnitが「Cell」に設定されていると思いますか?これが最善の解決策かどうかはわかりませんが、できることの1つは、DataGridのLoadedイベントを処理し、選択したセルをコードビハインドで手動で設定することです。したがって、次のようなものになります。

<DataGrid x:Name="dg" AutoGenerateColumns="False" IsSynchronizedWithCurrentItem="True"
            SelectedCellsChanged="dg_SelectedCellsChanged" SelectionUnit="Cell"
            Loaded="dg_Loaded">
    ...
</DataGrid>

イベントハンドラー:

private void dg_Loaded(object sender, RoutedEventArgs e)
{
    if ((dg.Items.Count > 0) &&
        (dg.Columns.Count > 0))
    {
        //Select the first column of the first item.
        dg.CurrentCell = new DataGridCellInfo(dg.Items[0], dg.Columns[0]);
        dg.SelectedCells.Add(dg.CurrentCell);
    }
}

これは、DataGrid.SelectionUnitが「Cell」に設定されている場合にのみ機能することに注意してください。そうでなければ、例外がスローされると思います。

EDIT2:

XAML:

<Window x:Class="WpfApplication1.MainWindow"
        xmlns="http://schemas.Microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.Microsoft.com/winfx/2006/xaml"
        Title="MainWindow" Height="350" Width="525">
    <StackPanel>
        <Button Click="Button_Click">Reset</Button>
        <DataGrid x:Name="dg" AutoGenerateColumns="False" IsSynchronizedWithCurrentItem="True"
                SelectionUnit="Cell"
                DataContextChanged="dg_DataContextChanged"
                ItemsSource="{Binding Items}"
                Loaded="dg_Loaded">
            <DataGrid.Columns>
                <DataGridTextColumn Binding="{Binding}"/>
            </DataGrid.Columns>
        </DataGrid>
    </StackPanel>
</Window>

コードビハインド:

namespace WpfApplication1
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        public MainWindow()
        {
            InitializeComponent();
            this.LoadItems();
        }

        private void Button_Click(object sender, RoutedEventArgs e)
        {
            this.LoadItems();
        }

        private void LoadItems()
        {
            this.DataContext = new { Items = new List<string> { "Item1", "Item2", "Item3" } };
            this.SelectFirstItem();
        }

        private void dg_Loaded(object sender, RoutedEventArgs e)
        {
            SelectFirstItem();
        }

        void SelectFirstItem()
        {
            if ((dg.Items.Count > 0) &&
                (dg.Columns.Count > 0))
            {
                //Select the first column of the first item.
                dg.CurrentCell = new DataGridCellInfo(dg.Items[0], dg.Columns[0]);
                dg.SelectedCells.Add(dg.CurrentCell);
            }
        }

        private void dg_DataContextChanged(object sender, DependencyPropertyChangedEventArgs e)
        {
            this.SelectFirstItem();
        }
    }
}
9
ASanch

これは、DataGrid.Loadedイベントで一貫して実行できます。最初の行を取得して、その行に選択イベントを発生させるだけです。

void MyGridLoaded(...) {
DataGridRow r = yourGrid.ItemContainergenerator.ContainerFromIndex(0) as DataGridRow;
  if(r != null) {
     r.IsSelected = false;
     r.IsSelected = true;
  }

} 

コントロールが読み込まれるまでオブジェクトから選択イベントが発生することが保証されていない可能性があるため、これがバグかどうかはわかりません。わからない。

3
aappddeevv

あなたはこれを試すことができます。

        this.dataGrid.SelectionMode = DataGridSelectionMode.Single;

        // Selects the 4th row.
        this.dataGrid.SelectedIndex = 3;
1
Prince Ashitaka

ItemContainerGenerator.StatusChangedイベントを通じてこの問題の解決策を見つけたことを報告できてうれしいです。

dataGrid.ItemContainerGenerator.StatusChanged += new EventHandler(ItemContainerGenerator_StatusChanged);

void ItemContainerGenerator_StatusChanged(object sender, EventArgs e)
        {
            if (dataGrid.ItemContainerGenerator.Status == GeneratorStatus.ContainersGenerated)
            {
                dataGrid.SelectedIndex = 0;
            }
        }

このイベントがContainersGeneratedステータスで発生すると、dataGridが完全に初期化されているように見えます。私にとって、これはWinFormでのDataGridViewのDataBindingCompleteイベントに似ています。その場合、「DataContextChanged」イベントは実際には「DataContextChanging」イベントと呼ばれる必要があります。

これは投稿に触発されました ここ 別の手がかりを探しているときに偶然見つけました。

1
newman