DragDrop between TreeView and GridView

6 posts, 0 answers
  1. Pat
    Pat avatar
    58 posts
    Member since:
    Feb 2005

    Posted 19 May 2011 Link to this post

    I'm trying to setup a FileExplorer like form. I have a treeview on the left for directories and a gridview on the right for JUST files.

    I need to support dragdrop WITHIN just the treeview and also support dragging from the gridview to the treeview.

    This is quite a confusing topic with what seems different ways to handle stuff. Some controls have events and properties, other don't and you have to set these properties via RadDragDropManager. And then in other cases, you seem to be handling dragdrop at the  control level and other samples you are going down into the row and doing stuff on the row.

    I've got the first working and all I needed to do was TreeView's DragOver, PreviewDragEnded, and DragEnded.  The tree view seems to take over and show the appropriate drag indicator with a message like drop before, drop in, etc.

    Now I'm trying to add support for dragging grid rows onto tree nodes.  In this case, following some online samples, I've hooked the Grid's RowLoaded and there in code, I'm hooking DraqQuery and DragInfo. So now I can drag ONE row.  But nothing ever fires when I hover over the tree and I can't drop onto the tree.

    What am I missing?

    It would be nice to see a sample like this

     

  2. Ivan Ivanov
    Admin
    Ivan Ivanov avatar
    1128 posts

    Posted 19 May 2011 Link to this post

    Hi pat,

    You may refer to this demo that demonstrates a very similar scenario to yours. Please, let us know whether this solution works for your case and do not hesitate to contact us immediately if any further inquiries occur.

    Best wishes,
    Ivan Ivanov
    the Telerik team
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items
  3. DevCraft banner
  4. Pat
    Pat avatar
    58 posts
    Member since:
    Feb 2005

    Posted 19 May 2011 Link to this post

    This is just so confusing.

    In that example, you sare displaying the types that can be dragged in all three panes. I do NOT have files in my left tree. Just directories.  I changed one line of code at my end to create the TreeViewDragCue but now all that happens is I have the "can't drop here" icon all over my tree. I need to be able to drop a right pane file item onto a left pane folder item.

    No events fire on my tree when I'm dragging over it.
  5. Ivan Ivanov
    Admin
    Ivan Ivanov avatar
    1128 posts

    Posted 25 May 2011 Link to this post

    Hello pat,

    Well, our demo illustrates a real life example and its only purpose is to work as a starting point for people who want to implement versatile interaction functionalities, utilizing our Drag & Drop manager. I perfectly understand that clients' requirements may be quite different when dealing with such a complex task, so I would kindly ask you to send us your project and some clear guidelines of your requirements, in order to help us provide better support to your case.

    Regards,
    Ivan Ivanov
    the Telerik team
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items
  6. Pat
    Pat avatar
    58 posts
    Member since:
    Feb 2005

    Posted 25 May 2011 Link to this post

    Issues:

    1) When i drag from the grid onto and over the treeview, I can't drop onto the tree
    2) If I drag/drop tree sub22 onto sub12, the tree starts rendering messed up.

    Well, I went through all the time to write a sample app to attach to this forum message, but it won't allow me to attach a zip file. So I tried a support case, but our plan is expired so I can't submit there either.

    Oh well......  here goes.... 
    <UserControl x:Class="FileExplorer.MainPage"
        mc:Ignorable="d"
        d:DesignHeight="300" d:DesignWidth="400" >
      
        <UserControl.Resources>
            <telerik:HierarchicalDataTemplate x:Key="Category"  ItemsSource="{Binding Children}" >
                <TextBlock Text="{Binding Name}" >
                    <telerik:RadContextMenu.ContextMenu>
                       <telerik:RadContextMenu Opened="RadContextMenu_Opened" ItemClick="RadContextMenu_ItemClick">
                           <telerik:RadMenuItem x:Name="MenuAddNewChild" Header="Add New Child" />
                           <telerik:RadMenuItem x:Name="MenuEditCategory" Header="Edit" />
                           <telerik:RadMenuItem x:Name="MenuDeleteCategory" Header="Delete" />
                           <telerik:RadMenuItem x:Name="MenuHideCategory" Header="Hide" />
                           <telerik:RadMenuItem x:Name="MenuShowCategory" Header="Show" />
                       </telerik:RadContextMenu>
                   </telerik:RadContextMenu.ContextMenu>
                </TextBlock>
            </telerik:HierarchicalDataTemplate>
        </UserControl.Resources>
      
        <Grid Background="White" Width="Auto" >
            <Grid.RowDefinitions>
                <RowDefinition Height="*" />
                <RowDefinition Height="205" />
            </Grid.RowDefinitions>
      
            <Grid Grid.Row="0" Grid.Column="0">
                <Grid.ColumnDefinitions>
                    <ColumnDefinition Width=".3*" />
                    <ColumnDefinition Width=".7*" />
                </Grid.ColumnDefinitions>
      
                <Border Grid.Row="0" Grid.Column="0"     >
                    <Grid Background="White"  >
                        <Grid.RowDefinitions>
                            <RowDefinition Height="*" />
                            <RowDefinition Height="20" />
                        </Grid.RowDefinitions>
      
                        <telerik:RadTreeView x:Name="CategoryTree" Grid.Row="0" Grid.Column="0" Margin="0,0,12,0"
                            HorizontalAlignment="Stretch"
                            VerticalAlignment="Stretch"
                            IsLineEnabled="True" SelectionMode="Multiple" IsEditable="False"
                            IsDragDropEnabled="True" IsExpandOnDblClickEnabled="True"
                            ItemTemplate="{StaticResource Category}"                         
                            >
                            <telerik:RadContextMenu.ContextMenu>
                                <telerik:RadContextMenu Opened="RadContextMenu_Opened" ItemClick="RadContextMenu_ItemClick">
                                    <telerik:RadMenuItem x:Name="MenuAddNewRootCategory"  Header="Add New Root" />
                                </telerik:RadContextMenu>
                            </telerik:RadContextMenu.ContextMenu>
      
                        </telerik:RadTreeView>
      
                        <StackPanel Orientation="Horizontal" HorizontalAlignment="Right" Grid.Row="1" Margin="2,2,20,2">
                        </StackPanel>
      
                    </Grid>
                </Border>
      
                <sdk:GridSplitter Grid.Row="0" Grid.Column="0" BorderBrush="Black" BorderThickness="1,0,1,0" Background="LightGray" />
      
                <Border Grid.Row="0" Grid.Column="1" Width="Auto" >
                    <Grid Background="White" Width="Auto" >
                        <Grid.RowDefinitions>
                            <RowDefinition Height="*" />
                            <RowDefinition Height="20" />
                        </Grid.RowDefinitions>
      
                        <telerik:RadGridView x:Name="ProductList" Grid.Row="0" Width="Auto" 
                                IsReadOnly="True" RowIndicatorVisibility="Visible" AutoGenerateColumns="False" CanUserFreezeColumns="False" ShowGroupPanel="false" IsFilteringAllowed="False" >
                            <telerik:RadGridView.Columns>
                                <telerik:GridViewDataColumn UniqueName="SKU" Header="SKU" Width="100" />
                                <telerik:GridViewDataColumn UniqueName="Name" Header="Name" Width="370" />
                            </telerik:RadGridView.Columns>
                        </telerik:RadGridView>
      
                        <StackPanel Orientation="Horizontal" HorizontalAlignment="Right" Grid.Row="1" Margin="2,2,10,2">
                        </StackPanel>
                    </Grid>
                </Border>
            </Grid>
      
            <Border Grid.Row="1" Grid.Column="0"  Grid.ColumnSpan="2" HorizontalAlignment="Stretch" BorderBrush="Black" BorderThickness="0,1,0,0"  >
                <StackPanel HorizontalAlignment="Stretch">
                </StackPanel>
            </Border>
      
        </Grid>
      
    </UserControl>

    using System;
    using System.Collections.Generic;
    using System.Collections.ObjectModel;
    using System.Linq;
    using System.Net;
    using System.Threading;
    using System.Windows;
    using System.Windows.Controls;
    using System.Windows.Documents;
    using System.Windows.Input;
    using System.Windows.Media;
    using System.Windows.Media.Animation;
    using System.Windows.Media.Imaging;
    using System.Windows.Shapes;
      
    using Telerik.Windows.Controls;
    using Telerik.Windows.Controls.DragDrop;
    using Telerik.Windows.Controls.GridView;
    using Telerik.Windows.Controls.TreeView;
      
    namespace FileExplorer
    {
        public partial class MainPage : UserControl
        {
            private List<Category> _rootCategories = new List<Category>();
      
            public MainPage()
            {
                InitializeComponent();
                this.Loaded += new RoutedEventHandler(MainPage_Loaded);
            }
      
            void MainPage_Loaded(object sender, RoutedEventArgs e)
            {
                this.CategoryTree.SelectionChanged += new Telerik.Windows.Controls.SelectionChangedEventHandler(CategoryTree_SelectionChanged);
                this.CategoryTree.ItemPrepared += new EventHandler<RadTreeViewItemPreparedEventArgs>(CategoryTree_ItemPrepared);
                this.CategoryTree.DragOver += new DragEventHandler(CategoryTree_DragOver);
                this.CategoryTree.PreviewDragEnded += new RadTreeViewDragEndedEventHandler(CategoryTree_PreviewDragEnded);
                this.CategoryTree.DragEnded += new RadTreeViewDragEndedEventHandler(CategoryTree_DragEnded);
                RadDragAndDropManager.AddDropInfoHandler(this.CategoryTree, new EventHandler<DragDropEventArgs>(CategoryTree_OnDropInfo));
                RadDragAndDropManager.AddDropQueryHandler(this.CategoryTree, new EventHandler<DragDropQueryEventArgs>(CategoryTree_OnDropQuery));
                  
                this.ProductList.RowLoaded += new EventHandler<Telerik.Windows.Controls.GridView.RowLoadedEventArgs>(ProductList_RowLoaded);
      
                Category root1 = new Category("R1", "Folder1");
                _rootCategories.Add(root1);
                Category sub11 = new Category("S11", "Sub 11");
                root1.Children.Add(sub11);
                Category sub12 = new Category("S12", "Sub 12");
                root1.Children.Add(sub12);
      
      
                Category root2 = new Category("R2", "Folder2");
                _rootCategories.Add(root2);
                Category sub21 = new Category("S21", "Sub 21");
                root2.Children.Add(sub21);
                Category sub22 = new Category("S22", "Sub 22");
                root2.Children.Add(sub22);
      
                this.CategoryTree.ItemsSource = _rootCategories;
      
                sub11.Products.Add(new Product("P1", "Product1"));
                sub11.Products.Add(new Product("P2", "Product2"));
                sub12.Products.Add(new Product("P3", "Product3"));
                sub22.Products.Add(new Product("P4", "Product4"));
                sub22.Products.Add(new Product("P5", "Product5"));
                sub22.Products.Add(new Product("P6", "Product6"));
      
            }
      
            void CategoryTree_ItemPrepared(object sender, RadTreeViewItemPreparedEventArgs e)
            {
            }
      
            void ProductList_RowLoaded(object sender, Telerik.Windows.Controls.GridView.RowLoadedEventArgs e)
            {
                RadDragAndDropManager.SetAllowDrag(e.Row, true);
                RadDragAndDropManager.AddDragQueryHandler(e.Row, ProductList_OnDragQuery);
                RadDragAndDropManager.AddDragInfoHandler(e.Row, ProductList_OnDragInfo);
      
            }
      
            void CategoryTree_SelectionChanged(object sender, Telerik.Windows.Controls.SelectionChangedEventArgs e)
            {
                if (e.AddedItems.Count != 1) return;
                //
                Category category = (Category) e.AddedItems[0];
                //
                this.ProductList.ItemsSource = category.Products;
            }
      
            private void RadContextMenu_ItemClick(object sender, Telerik.Windows.RadRoutedEventArgs e)
            {
                RadMenuItem menuItem = e.OriginalSource as RadMenuItem;
                RadTreeViewItem treeViewItem = FindParentOfType<RadTreeViewItem>((UIElement)sender);
            }
      
            private void RadContextMenu_Opened(object sender, RoutedEventArgs e)
            {
                RadContextMenu contextMenu = sender as RadContextMenu;
                RadTreeViewItem treeViewItem = FindParentOfType<RadTreeViewItem>(contextMenu);
            }
      
            private static T FindParentOfType<T>(UIElement element) where T : UIElement
            {
                if (element == null)
                    return null;
                DependencyObject parent =
                    Telerik.Windows.RoutedEvent.GetLogicalParent(element) ??
                    VisualTreeHelper.GetParent(element);
                while ((parent != null) && !(parent is T))
                {
                    parent =
                        Telerik.Windows.RoutedEvent.GetLogicalParent(parent) ??
                        VisualTreeHelper.GetParent(parent);
                }
                return (T)parent;
            }
      
      
      
      
      
      
      
      
      
      
      
      
      
      
            void CategoryTree_DragOver(object sender, DragEventArgs e)
            {
            }
              
            void CategoryTree_PreviewDragEnded(object sender, RadTreeViewDragEndedEventArgs e)
            {
            }
              
            void CategoryTree_DragEnded(object sender, RadTreeViewDragEndedEventArgs e)
            {
            }
      
            void CategoryTree_OnDropInfo(object sender, DragDropEventArgs e)
            {
            }
      
            void CategoryTree_OnDropQuery(object sender, DragDropQueryEventArgs e)
            {
                e.QueryResult = true;
            }
      
            private void ProductList_OnDragQuery(object sender, DragDropQueryEventArgs e)
            {
                if (e.Options.Source is GridViewRow)
                {
                    e.QueryResult = true;
                    if (e.Options.Status == DragStatus.DragQuery)
                    {
                        e.Options.Payload = ((FrameworkElement)e.Source).DataContext;
                    }
                }
      
            }
      
            private void ProductList_OnDragInfo(object sender, DragDropEventArgs e)
            {
                if (e.Options.Status == DragStatus.DragInProgress)
                {
                    TreeViewDragCue cue = new TreeViewDragCue();
                    //cue.ItemsSource = ((StoreProductSearch)((GridViewRow)args.Source).DataContext);
      
                    //var cue = RadDragAndDropManager.GenerateVisualCue();
                    //cue.Content = "Dragging " + ((StoreProductSearch)((GridViewRow)args.Source).DataContext).Name;
      
                    e.Options.DragCue = cue;
                }
            }
      
      
        }
      
      
        public class Category
        {
            public string ID { get; set; }
            public string Name { get; set; }
            public List<Category> Children { get; set; }
            public List<Product> Products { get; set; }
      
            public Category(string id,string name)
            {
                this.ID = id;
                this.Name = name;
                this.Children = new List<Category>();
                this.Products = new List<Product>();                 
            }
        }
      
        public class Product
        {
            public string SKU { get; set; }
            public string Name { get; set; }
      
            public Product(string sku, string name)
            {
                this.SKU = sku;
                this.Name = name;
            }
        }
    }

  7. Ivan Ivanov
    Admin
    Ivan Ivanov avatar
    1128 posts

    Posted 30 May 2011 Link to this post

    Hello pat,

    When dragging an item over the RadGridView, the DragCue displays an impossible drop operation, because you have never notified it anything else. Please, refer to this demo and see how it is achieved there. As for the second question, such a behavior may occur if you are using a data source that can not notify the TreeView of its changes. I would advise you to use a ObservableCollection<T> instead of List<T>, in order to prevent such issues. 

    Regards,
    Ivan Ivanov
    the Telerik team
    Do you want to have your say when we set our development plans? Do you want to know when a feature you care about is added or when a bug fixed? Explore the Telerik Public Issue Tracking system and vote to affect the priority of the items
Back to Top
DevCraft banner