我正在为WPF DatagGrid开发拖放机制。到目前为止,我的工作是这样的:
protected override void OnMouseMove(MouseEventArgs e)
{
base.OnMouseMove(e);
if (e.LeftButton == MouseButtonState.Pressed && Sections.Count > 1)
{
var row = UIHelpers.TryFindFromPoint<DataGridRow>(Dg, e.GetPosition(Dg));
var item = row.Item;
var sourceIndex = Sections.IndexOf((Section) item);
// Package the data.
DataObject data = new DataObject();
data.SetData(typeof(int),sourceIndex);
// Inititate the drag-and-drop operation.
DragDrop.DoDragDrop(this, data, DragDropEffects.Move);
}
}
protected override void OnDrop( DragEventArgs e)
{
base.OnDrop(e);
e.Effects = DragDropEffects.Move;
if (e.Data.GetDataPresent(typeof(int)))
{
var row = UIHelpers.TryFindFromPoint<DataGridRow>(Dg, e.GetPosition(Dg));
if (row == null)
return;
var item = row.Item;
var targetIndex = Sections.IndexOf((Section) item);
var sourceIndex = (int) e.Data.GetData(typeof(int));
if (sourceIndex != targetIndex)
{
var list = (IList<Section>)Dg.ItemsSource;
if (targetIndex == -1)
{
list.Add(list[sourceIndex]);
list.RemoveAt(sourceIndex);
}
else
{
list.Insert(targetIndex, list[sourceIndex]);
if (sourceIndex < targetIndex)
list.RemoveAt(sourceIndex);
else
list.RemoveAt(sourceIndex + 1);
}
}
}
e.Handled = true;
}
部分是数据网格的ItemsSource。
我想使此代码忽略类型,因此我可以将其用于Section以外的其他类型。
这行不通:
var sourceIndex = (int) ((List<object>) Dg.ItemsSource).FindIndex(a => a == item);
会怎样?
答案 0 :(得分:1)
您不能将集合投射到List
中。方便的IEnumerable
有一个Cast<T>
方法,该方法返回一个IEnumerable<T>
集合。并且更方便地从IEnumerable<T>
对象访问 linq 方法。
using System.Linq;
因此,为了使它变得无类型,可以将每个元素都转换为object
类型。
object test = Dg.ItemsSource.Cast<object>().First(a => a == item);
但是只有List
具有IndexOf
方法,因此调用ToList
使我们能够找到项目的索引:
var sourceIndex = Dg.ItemsSource.Cast<object>().ToList().IndexOf(item);