ScrollIntoView是否在virtualstackpannel中同步(特别是在WPF DataGrid中)?

时间:2011-04-30 16:56:53

标签: wpf wpfdatagrid itemscontrol setfocus itemcontainergenerator

我们有一个问题,即在有界集合的数据具有刷新后,将DataGrid的单元格聚焦。 例如,我们为其集合设置了一个过滤器,然后我们想重新聚焦存储列的存储单元格。

我们是否认为对ScrollIntoView的调用是同步的,这意味着在调用它之后我们创建了所需的行和单元格并且我们可以设置焦点? (再次,这意味着在我们调用ScrollIntoView之后,是否真的我们认为Itemsgenerator完成了它的工作,我们可以找到我们想要的单元格)

$

   //set filter of DataGrid Collection
DataGrid_Standard.ScrollIntoView(rowNumber,cellNumber);
//we sure our desired cell are created now
    DataGridRow row =           (DataGridRow)DataGrid_Standard.ItemContainerGenerator.ContainerFromIndex(index);
    if (row == null)
    {
        // may be virtualized, bring into view and try again
        DataGrid_Standard.ScrollIntoView(DataGrid_Standard.Items[index]);
        row = (DataGridRow)DataGrid_Standard.ItemContainerGenerator.ContainerFromIndex(index);
    }


        DataGridCellsPresenter presenter = GetVisualChild<DataGridCellsPresenter>(rowContainer);

        // try to get the cell but it may possibly be virtualized
        DataGridCell cell = (DataGridCell)presenter.ItemContainerGenerator.ContainerFromIndex(column);

            // now try to bring into view and retreive the cell
            DataGrid_Standard.ScrollIntoView(rowContainer, DataGrid_Standard.Columns[column]);
            cell = (DataGridCell)presenter.ItemContainerGenerator.ContainerFromIndex(column);             cell.focus();

Related

2 个答案:

答案 0 :(得分:0)

这是一个datagrid Selection更改事件处理程序,它将虚拟行移动到视图中,然后将焦点设置为该行。这对我有用:

        private void DataGrid_SelectionChanged(object sender, SelectionChangedEventArgs e)
    {
        DataGrid dg = (DataGrid)sender;
        if (dg.SelectedItem == null) return;
        dg.ScrollIntoView(dg.SelectedItem);

        DataGridRow dg_row = (DataGridRow)dg.ItemContainerGenerator.ContainerFromItem(dg.SelectedItem);
        if (dg_row == null) return;
       dg_row.MoveFocus(new TraversalRequest(FocusNavigationDirection.Next));

    }

编辑:使用dg_row.MoveFocus方法产生了不可取的效果(复选框列需要两次点击才能设置而不是一次)并且它对我来说效果更好

dg_row.Focus();

答案 1 :(得分:0)

Action action = () =>
      {
        dg .ScrollIntoView(dg .SelectedItem);

        var item = dg.ItemContainerGenerator.ContainerFromIndex(index) as DataGridRow;
        if (item == null) return;

        item.Focus();
      };

      Dispatcher.BeginInvoke(DispatcherPriority.Background, action);

这适用于您的情况。