简体   繁体   English

如何获取WPF DataGrid单元的位置?

[英]How do get the location of a WPF DataGrid cell?

I have a DataGrid bound to a collection of Appointment objects. 我有一个绑定到Appointment对象集合的DataGrid The grid shows appointments for a given week, with columns as days, and rows as times, ergo each cell is bound to an appointment. 网格显示给定星期的约会,列为天,行为时间,因此每个单元格都绑定到一个约会。

When the user single clicks a cell, I want to show a small window with a summary of that cell's appointment. 当用户单击一个单元格时,我想显示一个小窗口,其中包含该单元格约会的摘要。 For reasons complex, I can't template the cell to show the summary, and more important, I want the summary to drop down and overlay the cells below the selected one. 出于复杂的原因,我无法将单元格模板化以显示摘要,更重要的是,我希望摘要下拉并覆盖所选单元格下方的单元格。

In my command linked to the single-click, through some magic, I get the DataGridCellInfo for the selected cell itself, but that object offers no hint of any positioning, only some dimensions. 在单击链接的命令中,通过某种魔术,我获得了所选单元格本身的DataGridCellInfo ,但是该对象没有提供任何定位的提示,仅提供了某些尺寸。 The input binding for double-click looks like this: 双击的输入绑定如下所示:

<DataGrid.InputBindings>
    <!--TODO Remove name 'TheGrid' and find parent DataGrid-->
    <MouseBinding MouseAction="LeftDoubleClick"  Command="{Binding ApptClickCommand}" CommandParameter="{Binding ElementName=TheGrid, Path=SelectedCells}" />
</DataGrid.InputBindings>

and the command code receives a parameter of type SelectedCellsCollection , which contains only one DataGridCellInfo . 并且命令代码接收一个类型为SelectedCellsCollection的参数,该参数仅包含一个DataGridCellInfo I have no other information to work with in the command. 我没有其他可在命令中使用的信息。 As it is, I'm cheating quite a bit being so intimate with the view inside the viewmodel, so I'd like to avoid going overboard and using code-behind events directly. 照原样,我欺骗了与ViewModel内部的视图如此亲密的关系,所以我想避免过度使用并直接使用代码隐藏事件。

A popup is something UI specific, and in my opinion should be positioned from the View somehow. 弹出窗口是特定于UI的,我认为应该以某种方式从View定位。

In the past when I did something similar , my ViewModel tracked the actual data, the SelectedItem, and a flag for IsDetailsVisible. 过去,当我做类似的事情时 ,我的ViewModel跟踪实际数据,SelectedItem和IsDetailsVisible的标志。

From the View, I would have a "popup" UserControl that sat on top of my grid. 从视图中,我将在网格顶部有一个“弹出” UserControl。 It's visibility was bound to the IsDetailsVisible property, and the data was bound to the SelectedItem . 它的可见性绑定到IsDetailsVisible属性,而数据绑定到SelectedItem For my project, the popup was centered, however it should be an easy case to have the View set the Top/Left properties of the PopupUserControl so it matches the cell the user clicked on. 对于我的项目,弹出窗口居中,但是让View设置PopupUserControl的Top / Left属性以使其与用户单击的单元格匹配应该是一个简单的例子。

For finding the actual grid cell in the UI there's a few ways to go about that. 为了在UI中找到实际的网格单元,有几种方法可以解决。 The easiest would probably be to use the Click or MouseDown event, and from there position the PopupUserControl according to the Clicked DataGridCell. 最简单的方法可能是使用Click或MouseDown事件,然后根据Clicked DataGridCell定位PopupUserControl。 As I said, this kind of thing to me is view-specific, so should go in the code-behind the View. 就像我说的,对我而言,这种事情是特定于视图的,因此应该放在视图后面的代码中。

Also, I never liked WPF's popup, so made my own custom UserControl that I would always use instead. 另外,我从不喜欢WPF的弹出窗口,所以我制作了自己的自定义UserControl,我将始终使用它。 The code can be found on my blog here if you're interested in using it or doing something similar. 该代码可以在我的博客上找到这里 ,如果你有兴趣使用它或做类似的东西。

Here is an example of how you could get the DataGridCell element and then find its screen coordinates using the Visual.PointToScreen method: 这是如何获取DataGridCell元素,然后使用Visual.PointToScreen方法查找其屏幕坐标的示例:

    private void AppClickCommandExecuted(IList<DataGridCellInfo> cells)
    {
        if(cells != null && cells.Count > 0)
        {
            DataGridCellInfo cellInfo = cells[0];
            FrameworkElement cellContent = cellInfo.Column.GetCellContent(cellInfo.Item);
            if (cellContent != null)
            {
                DataGridCell cell = cellContent.Parent as DataGridCell;
                if(cell != null)
                {
                    Point screenCoordinates = cell.PointToScreen(new Point(0, 0));
                    //place your popup based on the screen coordinates of the cell...
                }
            }
        }
    }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM