WPF随笔收录-DataGrid固定右侧列
一、前言
在项目开发过程中,DataGrid是经常使用到的一个数据展示控件,而通常表格的最后一列是作为操作列存在,比如会有编辑、删除等功能按钮。但WPF的原始DataGrid中,默认只支持固定左侧列,这跟大家习惯性操作列放最后不符,今天就来介绍一种简单的方式实现固定右侧列。(这里的实现方式参考的大佬的两个DataGrid合并在一起的方式,原博客:
https://www.cnblogs.com/akwkevin/p/17872348.html
)
二、正文
1、上面大佬的实现,就直接基于他自己的控件库里实现的,这里我介绍的方式是如何引用了别的第三方库的情况下,在项目代码中再实现自定义可以固定右侧列的DataGrid控件;
2、首先新建个项目,项目里引用了HandyControl控件库和微软的mvvm库。
3、给项目添加一个自定义控件,记得不是自定义用户控件,这里命名为MyDataGrid,然后就可以从上面大佬那里搬代码过来,关键就是添加RightFrozenCount这个依赖属性代码和两个DataGrid之间的滚动同步代码
public intRightFrozenCount
{get { return (int)GetValue(RightFrozenCountProperty); }set{ SetValue(RightFrozenCountProperty, value); }
}public static readonly DependencyProperty RightFrozenCountProperty =DependencyProperty.Register(nameof(RightFrozenCount),typeof(int), typeof(MyDataGrid),new PropertyMetadata(0, OnRightFrozenCountChanged));private static voidOnRightFrozenCountChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{if (d isMyDataGrid dataGridRightFrozen)
{
dataGridRightFrozen.OnRightFrozenCountChanged();
}
}private voidOnRightFrozenCountChanged()
{if (_rightDataGrid != null)
{if (RightFrozenCount > 0)
{for (int i = 0; i < _rightDataGrid.Columns.Count; i++)
{var column =_rightDataGrid.Columns[i];
_rightDataGrid.Columns.Remove(column);
Columns.Add(column);
}for (int i = 0; i < RightFrozenCount; i++)
{var last = Columns[^1];
Columns.Remove(last);
_rightDataGrid.Columns.Insert(0, last);
}
_rightDataGrid.SetCurrentValue(VisibilityProperty, Visibility.Visible);
}else{
_rightDataGrid.SetCurrentValue(VisibilityProperty, Visibility.Collapsed);
}
}
}
public override voidOnApplyTemplate()
{base.OnApplyTemplate();if (_scrollViewer != null)
{
_scrollViewer.ScrollChanged-=ScrollViewer_ScrollChanged;
}if (_rightScrollViewer != null)
{
_rightScrollViewer.ScrollChanged-=RightScrollViewer_ScrollChanged;
}if (_rightDataGrid != null)
{
_rightDataGrid.ScrollViewerChanged-=ScrollViewerChanged;
_rightDataGrid.SelectionChanged-=RightDataGrid_SelectionChanged;
}
_scrollViewer= GetTemplateChild(DG_ScrollViewer) asScrollViewer;if (_scrollViewer != null)
{
_scrollViewer.ScrollChanged+=ScrollViewer_ScrollChanged;
}
_rightDataGrid= GetTemplateChild(PART_Right) asDataGridScrollView;if (_rightDataGrid != null)
{
_rightDataGrid.ScrollViewerChanged+=ScrollViewerChanged;
_rightDataGrid.SelectionChanged+=RightDataGrid_SelectionChanged;
}
SelectionChanged+=DataGridRightFrozen_SelectionChanged;
}private voidScrollViewerChanged(ScrollViewer viewer)
{
_rightScrollViewer=viewer;
_rightScrollViewer.ScrollChanged+=RightScrollViewer_ScrollChanged;
}private void ScrollViewer_ScrollChanged(objectsender, ScrollChangedEventArgs e)
{
_rightScrollViewer?.ScrollToVerticalOffset(_scrollViewer.VerticalOffset);
}private void RightScrollViewer_ScrollChanged(objectsender, ScrollChangedEventArgs e)
{
_scrollViewer?.ScrollToVerticalOffset(_rightScrollViewer.VerticalOffset);
}private void RightDataGrid_SelectionChanged(objectsender, SelectionChangedEventArgs e)
{
SetCurrentValue(SelectedItemProperty, _rightDataGrid.SelectedItem);
}private void DataGridRightFrozen_SelectionChanged(objectsender, SelectionChangedEventArgs e)
{
_rightDataGrid.SetCurrentValue(SelectedItemProperty, SelectedItem);
}
4、接着去到HandyControl的开源库那里,找到DataGrid的样式,然后复制到项目中
5、然后对原来的Style进行修改,对ControlTemplate的布局添加上作为固定列的DataGrid
6、至此,自定义支持右侧列固定的DataGrid就完成了,效果如下: