选择矩形,如WPF DataGrid中的Excel

时间:2013-09-20 21:05:52

标签: c# wpf excel datagrid

此问题类似于Excel like drag selection in Wpf itemscontrol,但我想在DataGrid中进行,而不是ListBox。
我试图使WPF DataGrid中的选择矩形看起来像Excel一样,包括在较低RH角的小黑方块,并且没有围绕每个单独选定单元格的边框。 有没有人在WPF DataGrid中有一个这样的工作示例?

enter image description here

1 个答案:

答案 0 :(得分:2)

首先,您必须使用this answer中描述的方法隐藏焦点单元格上的边框:

<DataGrid.CellStyle>
   <Style TargetType="DataGridCell">
      <Setter Property="FocusVisualStyle" Value="{x:Null}"/>
   </Style>
</DataGrid.CellStyle>

然后,您需要使用OnSelectedCellsChanged的{​​{1}}事件来添加/删除将绘制选择矩形的装饰器。对于填充句柄,您可以使用DataGrid来处理拖放的内容:

Thumb

FillHandleAdorner类的代码:

    void DataGrid_OnSelectedCellsChanged(object sender, SelectedCellsChangedEventArgs e)
    {
        var datagrid = (System.Windows.Controls.DataGrid)sender;
        AdornerLayer adornerLayer = AdornerLayer.GetAdornerLayer(datagrid);
        if (datagrid.SelectedCells.Any())
        {
            DataGridCellInfo firstCellInfo = datagrid.SelectedCells.First();
            FrameworkElement firstElt = firstCellInfo.Column.GetCellContent(firstCellInfo.Item);

            DataGridCellInfo lastCellInfo = datagrid.SelectedCells.Last();
            FrameworkElement lastElt = lastCellInfo.Column.GetCellContent(lastCellInfo.Item);

            if (firstElt != null && lastElt != null)
            {
                var firstcell = (DataGridCell)firstElt.Parent;
                var lastCell = (DataGridCell) lastElt.Parent;
                Point topLeft = datagrid.PointFromScreen(firstcell.PointToScreen(new Point(0, 0)));
                Point bottomRight = datagrid.PointFromScreen(lastCell.PointToScreen(new Point(lastCell.ActualWidth, lastCell.ActualHeight)));
                var rect = new Rect(topLeft, bottomRight);
                if (fillHandleAdorner == null)
                {
                    fillHandleAdorner = new FillHandleAdorner(datagrid, rect);
                    adornerLayer.Add(fillHandleAdorner);
                }
                else
                    fillHandleAdorner.Rect = rect;
            }
        }
        else
        {
            adornerLayer.Remove(fillHandleAdorner);
            fillHandleAdorner = null;
        }
    }

代码不完整,因为它适用于尚未启动的项目,但它可以帮助您启动。