Silverlight 4.0 PanelDragDropTarget和ListBoxDragDropTarget:到底拖动了什么?

Silverlight 4.0 PanelDragDropTarget和ListBoxDragDropTarget:到底拖动了什么?,silverlight-4.0,drag-and-drop,silverlight-toolkit,Silverlight 4.0,Drag And Drop,Silverlight Toolkit,我的Silverlight 4应用程序允许从ListBoxDragDropTarget拖动到PanelDragDropTarget 应用程序有Person对象,这些对象是表示人的模型,以及PersonControl用户控件,这些控件的数据上下文为Person 有关守则如下: <toolkit:ListBoxDragDropTarget x:Name="dtListBox" Grid.Row="2" AllowedSourceEffects="Copy" AllowDrop="True"

我的Silverlight 4应用程序允许从ListBoxDragDropTarget拖动到PanelDragDropTarget

应用程序有
Person
对象,这些对象是表示人的模型,以及
PersonControl
用户控件,这些控件的数据上下文为
Person

有关守则如下:

<toolkit:ListBoxDragDropTarget x:Name="dtListBox" Grid.Row="2" AllowedSourceEffects="Copy" AllowDrop="True" 
                               HorizontalContentAlignment="Stretch" 
                               VerticalAlignment="Top" VerticalContentAlignment="Stretch">
         <!-- FilteredMembers is of type ObservableCollection<Person> -->
    <ListBox ItemsSource="{Binding FilteredMembers}" 
                               MinWidth="42"
                               MinHeight="42">
            <ListBox.ItemTemplate>
                <DataTemplate>
                    <my:PersonControl />
                </DataTemplate>
            </ListBox.ItemTemplate>
        </ListBox>
</toolkit:ListBoxDragDropTarget>


到目前为止,一切顺利。当我拖动到
面板DragDropTarget
时,我得到了一个

但是,我也允许从
PanelDragDropTarget
拖动到另一个
PanelDragDropTarget
。在这种情况下,丢弃的对象不是
,而是
人控件

因此,丢弃的对象可以是
个人
个人控件
,具体取决于它来自何处

我真的想在所有情况下拖放
Person
对象,而不是在
PersonControl
中四处移动。如何修改我的
面板DragDropTarget
,以便拖动时拉动的是
人员
,而不是
人员控件

我已经回顾了这个非常类似的问题:


但我不明白这是如何解决问题的。

关于PanelDragDropTargets和ListBoxDragDropTargets传输丢弃对象的方式之间的差异,您是完全正确的。在2个ListBoxDragDropTargets之间拖动时,您正在传输绑定到控件的数据段,而在2个PanelDragDropTargets之间拖动时,将传输“拾取”的UIElement

我发现解决这个问题的最好方法是从PanelDragDropTarget派生一个新类,该类希望在其上删除一段数据,而不是UIElement。新类将数据对象存储在类“/控件的DataContext中。这允许类似于您的代码工作

班级:

public class ElementDragDropTarget : PanelDragDropTarget
{
    protected override bool CanAddItem(Panel itemsControl, object data)
    {
        return true;
    }

    protected override void InsertItem(Panel itemsControl, int index, object data)
    {
        itemsControl.DataContext = data;
    }

    protected override bool CanRemove(Panel itemsControl)
    {
        return true;
    }

    protected override void RemoveItem(Panel itemsControl, object data)
    {
        itemsControl.DataContext = null;
    }

    protected override void RemoveItemAtIndex(Panel itemsControl, int index)
    {
        itemsControl.DataContext = null;
    }

    protected override object ItemFromContainer(Panel itemsControl, UIElement itemContainer)
    {
        return itemsControl.DataContext;
    }
}
编辑您的代码:

<local:ElementDragDropTarget AllowDrop="True" AllowedSourceEffects="Copy,Move" Drop="PanelDragDropTarget_Current_Drop">
    <Grid>
        <ctl:PersonControl Margin="3,3,3,3" x:Name="pcCurrent"></ctl:PersonControl>
    </Grid>
</local:ElementDragDropTarget >


我意识到这个解决方案只允许将一个项目拖到ElementDragDropTarget中。我假设这就是您想要做的,因为如果您想要将多个数据对象放入其中,您可能只需要使用另一个ListBoxDragDropTarget(特别是因为您只是使用StackPanel)。

您完全正确地理解了PanelDragDropTargets和ListBoxDragDropTargets传输被丢弃对象的方式之间的差异。在2个ListBoxDragDropTargets之间拖动时,您正在传输绑定到控件的数据段,而在2个PanelDragDropTargets之间拖动时,将传输“拾取”的UIElement

我发现解决这个问题的最好方法是从PanelDragDropTarget派生一个新类,该类希望在其上删除一段数据,而不是UIElement。新类将数据对象存储在类“/控件的DataContext中。这允许类似于您的代码工作

班级:

public class ElementDragDropTarget : PanelDragDropTarget
{
    protected override bool CanAddItem(Panel itemsControl, object data)
    {
        return true;
    }

    protected override void InsertItem(Panel itemsControl, int index, object data)
    {
        itemsControl.DataContext = data;
    }

    protected override bool CanRemove(Panel itemsControl)
    {
        return true;
    }

    protected override void RemoveItem(Panel itemsControl, object data)
    {
        itemsControl.DataContext = null;
    }

    protected override void RemoveItemAtIndex(Panel itemsControl, int index)
    {
        itemsControl.DataContext = null;
    }

    protected override object ItemFromContainer(Panel itemsControl, UIElement itemContainer)
    {
        return itemsControl.DataContext;
    }
}
编辑您的代码:

<local:ElementDragDropTarget AllowDrop="True" AllowedSourceEffects="Copy,Move" Drop="PanelDragDropTarget_Current_Drop">
    <Grid>
        <ctl:PersonControl Margin="3,3,3,3" x:Name="pcCurrent"></ctl:PersonControl>
    </Grid>
</local:ElementDragDropTarget >

我意识到这个解决方案只允许将一个项目拖到ElementDragDropTarget中。我假设这就是您想要做的,因为如果您想将多个数据对象放入其中,您可能只需要使用另一个ListBoxDragDropTarget(特别是因为您只使用StackPanel)