From 8723ce26d487577c74a618c95ce1f262718a7aa7 Mon Sep 17 00:00:00 2001 From: Jan Karger Date: Thu, 25 Sep 2014 21:36:19 +0200 Subject: [PATCH 1/2] try find the SourceGroup for DragInfo --- GongSolutions.Wpf.DragDrop/DragInfo.cs | 7 +++++++ GongSolutions.Wpf.DragDrop/DropInfo.cs | 17 +---------------- GongSolutions.Wpf.DragDrop/IDragInfo.cs | 6 ++++++ .../Utilities/ItemsControlExtensions.cs | 16 ++++++++++++++++ 4 files changed, 30 insertions(+), 16 deletions(-) diff --git a/GongSolutions.Wpf.DragDrop/DragInfo.cs b/GongSolutions.Wpf.DragDrop/DragInfo.cs index fa5a653b..2d790116 100644 --- a/GongSolutions.Wpf.DragDrop/DragInfo.cs +++ b/GongSolutions.Wpf.DragDrop/DragInfo.cs @@ -3,6 +3,7 @@ using System.Linq; using System.Windows; using System.Windows.Controls; +using System.Windows.Data; using System.Windows.Input; using GongSolutions.Wpf.DragDrop.Utilities; @@ -40,6 +41,7 @@ public DragInfo(object sender, MouseButtonEventArgs e) if (sender is ItemsControl) { var itemsControl = (ItemsControl)sender; + this.SourceGroup = itemsControl.FindGroup(this.DragStartPosition); this.VisualSourceFlowDirection = itemsControl.GetItemsPanelFlowDirection(); var sourceItem = e.OriginalSource as UIElement; // If we can't cast object as a UIElement it might be a FrameworkContentElement, if so try and use its parent. @@ -159,6 +161,11 @@ public DragInfo(object sender, MouseButtonEventArgs e) /// public IEnumerable SourceItems { get; private set; } + /// + /// Gets the group from a dragged item if the drag is currently from an ItemsControl with groups. + /// + public CollectionViewGroup SourceGroup { get; private set; } + /// /// Gets the control that initiated the drag. /// diff --git a/GongSolutions.Wpf.DragDrop/DropInfo.cs b/GongSolutions.Wpf.DragDrop/DropInfo.cs index ee09a46a..aabce1c3 100644 --- a/GongSolutions.Wpf.DragDrop/DropInfo.cs +++ b/GongSolutions.Wpf.DragDrop/DropInfo.cs @@ -60,7 +60,7 @@ public DropInfo(object sender, DragEventArgs e, DragInfo dragInfo) var item = itemsControl.GetItemContainerAt(this.DropPosition); var directlyOverItem = item != null; - this.TargetGroup = this.FindGroup(itemsControl, this.DropPosition); + this.TargetGroup = itemsControl.FindGroup(this.DropPosition); this.VisualTargetOrientation = itemsControl.GetItemsPanelOrientation(); this.VisualTargetFlowDirection = itemsControl.GetItemsPanelFlowDirection(); @@ -122,21 +122,6 @@ public DropInfo(object sender, DragEventArgs e, DragInfo dragInfo) } } - private CollectionViewGroup FindGroup(ItemsControl itemsControl, Point position) - { - var element = itemsControl.InputHitTest(position) as DependencyObject; - - if (element != null) { - var groupItem = element.GetVisualAncestor(); - - if (groupItem != null) { - return groupItem.Content as CollectionViewGroup; - } - } - - return null; - } - /// /// Gets the drag data. /// diff --git a/GongSolutions.Wpf.DragDrop/IDragInfo.cs b/GongSolutions.Wpf.DragDrop/IDragInfo.cs index 81111c76..ba67e801 100644 --- a/GongSolutions.Wpf.DragDrop/IDragInfo.cs +++ b/GongSolutions.Wpf.DragDrop/IDragInfo.cs @@ -1,5 +1,6 @@ using System.Collections; using System.Windows; +using System.Windows.Data; using System.Windows.Input; namespace GongSolutions.Wpf.DragDrop @@ -72,6 +73,11 @@ public interface IDragInfo /// IEnumerable SourceItems { get; } + /// + /// Gets the group from a dragged item if the drag is currently from an ItemsControl with groups. + /// + CollectionViewGroup SourceGroup { get; } + /// /// Gets the control that initiated the drag. /// diff --git a/GongSolutions.Wpf.DragDrop/Utilities/ItemsControlExtensions.cs b/GongSolutions.Wpf.DragDrop/Utilities/ItemsControlExtensions.cs index b5cf5fa0..7ed7acc7 100644 --- a/GongSolutions.Wpf.DragDrop/Utilities/ItemsControlExtensions.cs +++ b/GongSolutions.Wpf.DragDrop/Utilities/ItemsControlExtensions.cs @@ -3,6 +3,7 @@ using System.Linq; using System.Windows; using System.Windows.Controls; +using System.Windows.Data; using System.Windows.Media; using System.Reflection; using System.Collections; @@ -17,6 +18,21 @@ namespace GongSolutions.Wpf.DragDrop.Utilities { public static class ItemsControlExtensions { + public static CollectionViewGroup FindGroup(this ItemsControl itemsControl, Point position) + { + var element = itemsControl.InputHitTest(position) as DependencyObject; + + if (element != null) { + var groupItem = element.GetVisualAncestor(); + + if (groupItem != null) { + return groupItem.Content as CollectionViewGroup; + } + } + + return null; + } + public static bool CanSelectMultipleItems(this ItemsControl itemsControl) { if (itemsControl is MultiSelector) { From 806d92d4fe337b132c0f4e50804a45608b808008 Mon Sep 17 00:00:00 2001 From: Jan Karger Date: Thu, 25 Sep 2014 21:36:57 +0200 Subject: [PATCH 2/2] fix the insertion adorner after last grouped item --- .../DropTargetInsertionAdorner.cs | 15 ++++++++++++++- 1 file changed, 14 insertions(+), 1 deletion(-) diff --git a/GongSolutions.Wpf.DragDrop/DropTargetInsertionAdorner.cs b/GongSolutions.Wpf.DragDrop/DropTargetInsertionAdorner.cs index 410f1748..1caf3055 100644 --- a/GongSolutions.Wpf.DragDrop/DropTargetInsertionAdorner.cs +++ b/GongSolutions.Wpf.DragDrop/DropTargetInsertionAdorner.cs @@ -1,8 +1,10 @@ using System; using System.Collections.Generic; +using System.Collections.ObjectModel; using System.Linq; using System.Text; using System.Windows; +using System.Windows.Data; using System.Windows.Media; using System.Windows.Controls; using System.Collections; @@ -33,6 +35,17 @@ protected override void OnRender(DrawingContext drawingContext) } var index = Math.Min(this.DropInfo.InsertIndex, itemParent.Items.Count - 1); + + var lastItemInGroup = false; + var targetGroup = this.DropInfo.TargetGroup; + if (targetGroup != null && targetGroup.IsBottomLevel && this.DropInfo.InsertPosition.HasFlag(RelativeInsertPosition.AfterTargetItem)) { + var indexOf = targetGroup.Items.IndexOf(this.DropInfo.TargetItem); + lastItemInGroup = indexOf == targetGroup.ItemCount - 1; + if (lastItemInGroup) { + index--; + } + } + var itemContainer = (UIElement)itemParent.ItemContainerGenerator.ContainerFromIndex(index); if (itemContainer != null) { @@ -41,7 +54,7 @@ protected override void OnRender(DrawingContext drawingContext) double rotation = 0; if (this.DropInfo.VisualTargetOrientation == Orientation.Vertical) { - if (this.DropInfo.InsertIndex == itemParent.Items.Count) { + if (this.DropInfo.InsertIndex == itemParent.Items.Count || lastItemInGroup) { itemRect.Y += itemContainer.RenderSize.Height; }