使用copy命令使用MVVM-Light复制DataGrid RowDetails中的TextBlock.Text

时间:2014-09-11 20:38:07

标签: mvvm datagrid mvvm-light

我是WPF的新手,我正在尝试使用MVVM-Light重新编写WPF控件。事实证明,这比我想象的还要多。以下是一些背景知识:

这是一个winforms应用程序,其中包含一个包含WPF控件的ElementHost。我最初编写的WPF部分都错了,但确实有效。 WPF控件有一个WPF Toolkit DataGrid,它有几个数据绑定列以及带有数据绑定项的行详细信息区域。所有项目仅显示并绑定到TextBlock对象。在当前迭代中,右键单击记录中的任何TextBlock元素会显示一个上下文菜单,该菜单允许将TextBlock的文本复制到剪贴板。

这是通过挂钩PreviewMouseDown按钮,查看e.OriginalSource,走可视树直到我们找到TextBlock并缓存它来完成的。

请求复制命令时,'可以复制'检查是否有TextBlock'复制对象'并使用Text属性提取值。不优雅,但确实有效。这都是在wpf控件后面的代码中完成的。

我试图以MVVM方式复制此行为(右键单击并复制TextBlock文本值)。如果它与ctl-c一起工作会很酷,但那不是必要的。上下文菜单足够了。

我几天来一直在反对这个问题,所以现在是时候看看是否有人可以提供帮助了。这是我到目前为止所尝试的内容。

  1. 尝试使用扩展,但不确定如何使这项工作。我确实阅读了很多关于扩展的内容,而且似乎暗示这是一种应该有效的方法。我只是无法绕过它。
  2. 尝试附加将ApplicationCommands.Copy挂钩到VM的行为。这是有效的,我可以将它复制到我的“可以复制'并且'执行' VM中的方法,但我没有足够的信息来查找单击的TextBlock,以便我可以从中获取文本。
  3. 通过鼠标单击使用EventToCommand并通过转换器抓取文本以便可以将其缓存在VM中,开始沿着相同的路径走。然后,2中的处理程序可以根据“复制值”进行操作。如果它存在这似乎可能让我接近,但仍然感觉有点像黑客。
  4. 没有任何输入,我可能会选择选项3,因为它确实将代码保持在2个位置,在转换器中,VM和方法当前有效。看起来似乎应该有一种更简单的方法。

    我觉得值得看看其他人可能会提供什么想法。

    提前感谢任何输入,

    根据要求添加屏幕截图和代码:

    基本上我需要复制显示的文本框中包含的任何文本。请注意,列绑定到成员,但详细信息依赖于.ToString()方法。显示的任何文本都需要能够按照您所看到的内容进行复制。

    原来我太新了,无法发布图片。 GUI非常简单,所以我希望代码是足够的。

    这是用于构建该GUI的代码:

    <Window x:Class="DemoCopy.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:dg="http://schemas.microsoft.com/wpf/2008/toolkit"
    xmlns:local="clr-namespace:DemoCopy"
    DataContext="{Binding Source={StaticResource Locator}, Path=Main}"
    Title="MainWindow" Height="350" Width="525">
    <Grid>
        <dg:DataGrid Margin="10" ItemsSource="{Binding NamesList}" AutoGenerateColumns="False">
            <dg:DataGrid.ContextMenu>
                <ContextMenu>
                    <MenuItem Header="Copy" Command="ApplicationCommands.Copy" />
                </ContextMenu>
            </dg:DataGrid.ContextMenu>
            <dg:DataGrid.RowDetailsTemplate>
                <DataTemplate>
                    <Border BorderThickness="1" BorderBrush="Black" Margin="1" Background="White" Padding="10">
                        <TextBlock Text="{Binding}" />
                    </Border>
                </DataTemplate>
            </dg:DataGrid.RowDetailsTemplate>
            <dg:DataGrid.Columns>
                <dg:DataGridTemplateColumn ClipboardContentBinding="{Binding First}" Width="*">
                    <dg:DataGridTemplateColumn.Header>First Name</dg:DataGridTemplateColumn.Header>
                    <dg:DataGridTemplateColumn.CellTemplate>
                        <DataTemplate>
                            <TextBlock Text="{Binding First}" />
                        </DataTemplate>
                    </dg:DataGridTemplateColumn.CellTemplate>
                </dg:DataGridTemplateColumn>
                <dg:DataGridTemplateColumn ClipboardContentBinding="{Binding Middle}" Width="50">
                    <dg:DataGridTemplateColumn.Header>Middle Name</dg:DataGridTemplateColumn.Header>
                    <dg:DataGridTemplateColumn.CellTemplate>
                        <DataTemplate>
                            <TextBlock Text="{Binding Middle}" />
                        </DataTemplate>
                    </dg:DataGridTemplateColumn.CellTemplate>
                </dg:DataGridTemplateColumn>
                <dg:DataGridTemplateColumn ClipboardContentBinding="{Binding Last}" Width="*">
                    <dg:DataGridTemplateColumn.Header>Last Name</dg:DataGridTemplateColumn.Header>
                    <dg:DataGridTemplateColumn.CellTemplate>
                        <DataTemplate>
                            <TextBlock Text="{Binding Last}" />
                        </DataTemplate>
                    </dg:DataGridTemplateColumn.CellTemplate>
                </dg:DataGridTemplateColumn>
            </dg:DataGrid.Columns>
        </dg:DataGrid>
    </Grid>
    

        public class MainViewModel : ViewModelBase
    {
        private IList<Model.Name> namesList;
        public IList<Model.Name> NamesList
        {
            get { return namesList; }
            set
            {
                if (namesList == value)
                    return;
                namesList = value;
                RaisePropertyChanged("NamesList");
            }
        }
    
        /// <summary>
        /// Initializes a new instance of the MainViewModel class.
        /// </summary>
        public MainViewModel()
        {
            if (IsInDesignMode)
            {
                NamesList = new List<Model.Name>();
                NamesList.Add(new Model.Name()
                {
                    First = "John",
                    Middle = "M",
                    Last = "Doe"
                });
                NamesList.Add(new Model.Name()
                {
                    First = "Jane",
                    Middle = "P",
                    Last = "Doe"
                });
            }
            else
            {
                NamesList = new List<Model.Name>();
                NamesList.Add(new Model.Name()
                {
                    First = "John",
                    Middle = "M",
                    Last = "Doe"
                });
                NamesList.Add(new Model.Name()
                {
                    First = "Jane",
                    Middle = "P",
                    Last = "Doe"
                }); 
            }
        }
    }
    
    public class Name
    {
        public string First { get; set; }
        public string Middle { get; set; }
        public string Last { get; set; }
    
        public override string ToString()
        {
            return string.Format("{0} {1} {2}", First, Middle, Last);
        }
    }
    

    苏格兰人。

0 个答案:

没有答案