首页 文章

WPF将文件从Windows资源管理器拖放到TreeView上

提问于
浏览
6

我试图制作一个非常简单的,或者我认为,程序将文件从桌面/资源管理器拖放到wpf树视图上 .

这个例子中的树视图很简单,所以我可以隔离我遇到的拖放问题 . 我已将AllowDrop设置为整个地方的True,我仍然无法触发Drop或DragOver事件 . 我专注于树视图控件,因为我希望能够将文件拖动到具有分层结构的不同节点中 . Right now I would settle for just being able to get the DragOver or Drop events to fire when I drag a file onto the treeview.

我通过查看这样的例子开始了:Drag & Drop in Treeview

我的问题与此类似:Drag drop files from explorer onto Telerik WPF treeview . 但是我使用的是wpf treeview,而不是telerik .

这是我到目前为止的代码

XAML:

<Window x:Class="WpfDragAndDropTest.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:local="clr-namespace:WpfDragAndDropTest"
        Title="MainWindow" Height="350" Width="525">
    <Grid>
        <TreeView Name="TreeView1">
            <TreeView.ItemContainerStyle>
                <Style TargetType="{x:Type TreeViewItem}" >
                    <Setter Property="TreeViewItem.AllowDrop" Value="True"/>
                    <EventSetter Event="TreeViewItem.DragOver" Handler="TreeView1_DragOver" />
                    <EventSetter Event="TreeViewItem.Drop" Handler="TreeView1_Drop" />
                    <EventSetter Event="TreeViewItem.MouseMove" Handler="TreeView1_MouseMove" />
                </Style>
            </TreeView.ItemContainerStyle>

            <TreeView.Resources>
                <DataTemplate DataType="{x:Type local:TestClass}">
                    <StackPanel Orientation="Vertical"  >
                        <TextBlock Text="{Binding Path=Title}" />
                        <TextBlock Text="{Binding Path=Url}" />
                    </StackPanel>
                </DataTemplate>
            </TreeView.Resources>

        </TreeView>
    </Grid>
    </Window>

码:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;

namespace WpfDragAndDropTest
{
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
    public MainWindow()
    {
        InitializeComponent();

        TreeView1.ItemsSource = new[] 
        { 
            new TestClass { Title = "Google", Url = "http://www.google.com" }, 
            new TestClass { Title = "Microsoft", Url = "http://www.microsoft.com" },
            new TestClass{ Title="Netflix", Url="http://www.netflix.com" }
        };
    }

    private void TreeView1_Drop(object sender, DragEventArgs e)
    {

    }

    private void TreeView1_DragOver(object sender, DragEventArgs e)
    {

    }

    private void TreeView1_MouseMove(object sender, MouseEventArgs e)
    {

    }
}


public class TestClass
{
    public string Title { get; set; }
    public string Url { get; set; }
}
}

Edit 我把那个解释我问题的文字加粗了,因为事件没有解雇 .

我将我的xaml切换到了这个,当我在树视图上拖动文件时,我仍然会得到一个带有一条直线的黑色圆圈,唯一的事件就是MouseMove . 如果我使用鼠标执行这些操作,则不会触发拖放 .

<TreeView Name="TreeView1" AllowDrop="True" DragOver="TreeView1_DragOver" Drop="TreeView1_Drop" MouseMove="TreeView1_MouseMove">


        <TreeView.Resources>
            <DataTemplate DataType="{x:Type local:TestClass}">
                <StackPanel Orientation="Vertical"  >
                    <TextBlock Text="{Binding Path=Title}" />
                    <TextBlock Text="{Binding Path=Url}" />
                </StackPanel>
            </DataTemplate>
        </TreeView.Resources>

    </TreeView>

Edit 我尝试了一个空白的树视图,并且能够将文件拖过它,光标不是黑色圆圈,而是通过它 .

<TreeView Height="312" Background="#FFCFDBF9" AllowDrop="True"/>

然而,当添加DataTemplate时,就是黑色圆圈开始出现的时候 . 这必须是某种数据绑定问题?

Edit 我现在开始到某个地方 .

我将我的xaml更改为this并且事件开始触发:

<TreeView Name="TreeView1" Background="#FFC9D7FF">


    <TreeView.Resources>
        <DataTemplate DataType="{x:Type local:TestClass}">
            <StackPanel Orientation="Vertical"  AllowDrop="True" DragOver="TreeView1_DragOver" Drop="TreeView1_Drop" MouseMove="TreeView1_MouseMove" >
                <TextBlock Text="{Binding Path=Title}" />
                <TextBlock Text="{Binding Path=Url}" />
            </StackPanel>
        </DataTemplate>
    </TreeView.Resources>

</TreeView>

edit 我发现如果我从表达式混合运行项目,我只能拖放到stackpanel . 如果我从visual studio运行它,它会显示黑色圆圈,并在其中显示一条直线 . 这根本没有任何意义 . For this seperate problem I have started another question here: Visual Studio 2010 WPF Project ran in debug or relase will not allow drag and drop to any control

This is all due to running visual studio as administrator. Apparently the same is true for notepad.exe, if you run something as administrator you can't drag and drop. So now for IIS debugging I have to run as administrator and for dragging and dropping I need to figure out how to run in normal mode...

1 回答

  • 1

    我认为问题是你没有在TreeViewItems上拖动项目 . 这是必要的,因为您的事件仅为TreeViewItems注册 . 如果要拖放到树的父级别,则需要将相应的事件添加到树中 .

    此解决方案将遇到的问题是TreeView事件将首先触发 . 所以现在你必须知道你正在哪个节点才能正确添加它 . 有解决方案可以确定您所在的节点 . 但是,我建议在树中添加一个始终存在的顶级元素 . 然后像往常一样将事件连接到TreeViewItems . 这样,您可以在顶级添加而无需处理TreeView事件,因为您可以拖动到该顶级项目 .

    下面是我用来测试它的内容,如果我直接拖到TreeViewItems上,我就会看到断点 . 您可能无法识别某些名称空间,但这是因为它引用了我的项目 .

    XAML:

    <TreeView x:Name="treeView">
         <TreeView.ItemContainerStyle>
            <Style TargetType="{x:Type TreeViewItem}" >
               <Setter Property="TreeViewItem.AllowDrop" Value="True"/>
               <EventSetter Event="TreeViewItem.DragOver" Handler="treeView_DragOver" />
               <EventSetter Event="TreeViewItem.Drop" Handler="treeView_Drop" />
               <EventSetter Event="TreeViewItem.MouseMove" Handler="treeView_MouseMove" />
            </Style>
         </TreeView.ItemContainerStyle>
    
         <TreeView.Resources>
            <DataTemplate DataType="{x:Type FileExplorerDragDrop:TestClass}">
               <StackPanel Orientation="Vertical"  >
                  <TextBlock Text="{Binding Path=Title}" />
                  <TextBlock Text="{Binding Path=Url}" />
               </StackPanel>
            </DataTemplate>
         </TreeView.Resources>
      </TreeView>
    

    Code behind:

    public MainWindow()
      {
         InitializeComponent();
    
         treeView.ItemsSource = new[] 
         { 
            new TestClass { Title = "Google", Url = "http://www.google.com" }, 
            new TestClass { Title = "Microsoft", Url = "http://www.microsoft.com" },
            new TestClass{ Title="Netflix", Url="http://www.netflix.com" }
         };
      }
    
      private void treeViewItem_DragOver(object sender, DragEventArgs e)
      {
    
      }
    
      private void treeViewItem_Drop(object sender, DragEventArgs e)
      {
    
      }
    
      private void treeViewItem_MouseMove(object sender, MouseEventArgs e)
      {
    
      }
    

相关问题