我正在使用模型来选择DataGrid中的项目,如下所示:

public ObservableCollection<MyModel> Models{
   get {return m_Models; }
}

public MyModel SelectedModel
{
   get{ return m_SelectedModel; }
   set{
        m_SelectedModel = value;
    }
    NotifyPropertyChanged("SelectedModel");
    NotifyPropertyChanged("Models");
}

这两个公共属性在作为窗口数据上下文的模型中。 Observable Collection绑定到数据网格,SelectedItem绑定到SelectedModel,就像在XAML中一样:

<DataGrid x:Name="MyDataGrid" AutoGenerateColumns="False" IsReadOnly="True" CanUserResizeColumns="True" CanUserAddRows="False" CanUserSortColumns="True"
                                  SelectionMode="Single" SelectionChanged="DataGrid_SelectionChanged" ItemsSource="{Binding Models}"
                                  CanUserResizeRows="False" IsTextSearchEnabled="True" RowHeaderWidth="0" SelectedItem="{Binding SelectedModel, Mode=TwoWay, NotifyOnTargetUpdated=True, NotifyOnSourceUpdated=True}" Grid.ColumnSpan="2" Margin="0,0,-0.4,-0.4">

因此,每当我更改SelectedModel时,数据网格中的SelectedItem都会更新。 这工作得很好,我已经能够基于SelectedItem填充其他数据。 确实,我的DataGrid_SelectionChanged事件处理程序在设置SelectedModel时被调用。

但是,无论何时选择新项目,我都希望数据网格自动滚动以显示SelectedItem。 我尝试了多种方法使它正常工作,但无济于事。 这是我尝试过的几件事(已确认此功能已通过调试器调用):

    private void DataGrid_SelectionChanged(object sender, SelectionChangedEventArgs e)
    {
        if(MyDataGrid.SelectedItem != null)
        {
           //All 3 of these have been tried separately and do not work
           MyDataGrid.ScrollIntoView(MyDataGrid.SelectedItem);
           MyDataGrid.ScrollIntoView(MyDataGrid.Items[MyDataGrid.SelectedIndex]);
           MyDataGrid.ScrollIntoView(_model.SelectedModel); //Didn't expect this one to work but just want to show that I'm trying things out here
        }
    }

我已经查看了ScrollIntoView的其他问题,但似乎都无法解决我的问题。 我将不胜感激。 谢谢。

#1楼 票数:0

不知道为什么它对您不起作用,但是它肯定可以正常工作。 在下面查看演示应用程序代码:

XAML

<Window x:Class="WpfApplication1.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:WpfApplication1"
        mc:Ignorable="d"
        Title="MainWindow" Height="350" Width="525">

    <Grid>
        <DataGrid x:Name="MyDataGrid" AutoGenerateColumns="False" IsReadOnly="True" CanUserResizeColumns="True" CanUserAddRows="False" CanUserSortColumns="True"
                  SelectionMode="Single" SelectionChanged="DataGrid_SelectionChanged" ItemsSource="{Binding Items}"
                  CanUserResizeRows="False" IsTextSearchEnabled="True" RowHeaderWidth="0" SelectedItem="{Binding SelectedItem, Mode=TwoWay, NotifyOnTargetUpdated=True, NotifyOnSourceUpdated=True}"
                  Grid.ColumnSpan="2" Margin="0,0,-0.4,-0.4">
            <DataGrid.Resources>
                <SolidColorBrush x:Key="{x:Static SystemColors.HighlightBrushKey}" Color="Red" />
                <SolidColorBrush x:Key="{x:Static SystemColors.InactiveSelectionHighlightBrushKey }" Color="Red" />
            </DataGrid.Resources>
            <DataGrid.Columns>
                <DataGridTextColumn Header="Id" Binding="{Binding Id}" />
                <DataGridTextColumn Header="Name" Binding="{Binding Name}" />
            </DataGrid.Columns>
        </DataGrid>
    </Grid>
</Window>

类文件

using System;
using System.ComponentModel;
using System.Linq;
using System.Timers;
using System.Windows;

namespace WpfApplication1
{
    public class Model
    {
        public int Id { get; set; }
        public string Name { get; set; }
    }

    public class ViewModel : INotifyPropertyChanged
    {
        public event PropertyChangedEventHandler PropertyChanged;

        private readonly Model[] items;

        public ViewModel()
        {
            items = Enumerable.Range(1, 101)
                              .Select(x => new Model
                              {
                                  Id = x,
                                  Name = $"Item {x}"
                              })
                              .ToArray();
        }

        public Model[] Items => items;

        private Model selectedItem;
        public Model SelectedItem
        {
            get { return selectedItem; }
            set
            {
                selectedItem = value;
                PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(nameof(SelectedItem)));
            }
        }

    }

    public partial class MainWindow : Window
    {
        private readonly Timer timer;
        private readonly ViewModel model;
        private readonly Random random;

        public MainWindow()
        {
            InitializeComponent();
            model = new ViewModel();
            random = new Random();
            timer = new Timer(2000);

            DataContext = model;

            timer.Elapsed += Timer_Elapsed;
            timer.Start();
        }

        private void Timer_Elapsed(Object sender, ElapsedEventArgs e)
        {
            var index = random.Next(model.Items.Length);
            model.SelectedItem = model.Items[index];
        }

        private void DataGrid_SelectionChanged(Object sender, System.Windows.Controls.SelectionChangedEventArgs e)
        {
            if (MyDataGrid.SelectedItem != null)
            {
                MyDataGrid.ScrollIntoView(MyDataGrid.SelectedItem);
            }
        }

        protected override void OnClosing(CancelEventArgs e)
        {
            base.OnClosing(e);

            timer.Stop();
            timer.Dispose();
        }
    }
}

在我看来,您的代码正在执行某些操作,可能会阻止框架滚动网格。

#2楼 票数:0 已采纳

我能够使ScrollIntoView工作,但是我需要将ScrollToView函数放入数据网格的Loaded回调中。 以下是解决问题的示例:

    private void DataGrid_Loaded(object sender, RoutedEventArgs e)
    {
        if(MyDataGrid.SelectedItem != null)
        {
            MyDataGrid.ScrollIntoView(MyDataGrid.SelectedItem);
        }
    }

我的猜测是,数据网格没有完全加载到SelectionChanged事件上,因此没有滚动到正确的位置。

  ask by Heisenberg translate from so

未解决问题?本站智能推荐:

3回复

如何使某个部分可滚动

我有以下XAML: 我希望wrapPanel仅可滚动,以便在滚动时txtBottomText控件将始终位于底部, logo图像控件将始终位于顶部-本质上仅允许wrapPanel可滚动。 我已经尝试过添加ScrollViewer,如上所示,但是它从未显示。 我什至尝试添加一个属性以使其始
2回复

在WPF中,如何更新用户控件中的主UI?

我有一个问题,我想更新一个用户控件中的主UI,我尝试了很多次,但我没有成功。测试分为两类,如下所示: 第一类: 我先是直接赋值了主窗口控件(tbInfo,TextBlock类型),没有成功。 于是我创建了一个textBlockUpdate类(实现了属性变更通知接口),并将其属性(TextMessag
1回复

在UI中处理设备输入和焦点

我最近一直在研究游戏开发,并接触过Microsoft的XNA4.0(分别为Monogame)。 不幸的是,XNA并未真正提供UI工具包,所以我开始自己编写一个(我知道那里有很多3rd party工具包,但是出于教育目的,我决定重新发明轮子)。 我的问题是:UI框架如何管理和编排设备输入,尤
1回复

WPF应用程序中的触摸模式

可能有些人已经注意到Office 2013包含一项称为触摸模式的新功能。 这就是它的样子 我想知道我是否可以在WPF中达到同样的效果。 有任何想法吗?
2回复

如何在WPF中绘制数字信号?

我需要绘制数字信号,并能够在WPF中移动线路的每一部分。 如下图所示,箭头指示线的一部分可以朝哪个方向移动。 单击并拖动“可单击区域”将使整个正方形向左或向右移动。 我想了几种方法: Polyline对象。 但是我无法控制生产线的每个部分。 Line对象。 每次更改时,
1回复

在网格中自动排列WPF控件

我有一个基于wpf(mvvm-light)的表单,带有Grid和六个按钮,三个按钮连续两列。 由于可以在设置中打开/关闭按钮,因此我想隐藏其中的一些按钮,但是我不想有空格。 我该如何实现?
1回复

在WPF应用程序中找不到Startupuri

我需要有关此问题的帮助 我需要放置启动视图Home.xaml但是当我运行该应用程序时,出现错误消息,提示未找到Home视图。 此错误的原因是什么? 我该如何解决?
2回复

如何在WPF中的元素上添加半透明阴影?

我想在WPF窗口的内容上添加半透明颜色(以指示窗口的状态)。 目前我正在使用填充Window的UserControl,并根据需要更改背景颜色和可见性。 此方法的问题是当UserControl可见时,我无法单击UserControl后面的Window中的任何控件(按钮,CheckBox)。