2012-02-17 7 views
0

ドラッグ&ドロップで別のキャンバスにしたいボタンがあるキャンバスがあります。ボタンを他のキャンバスにコピーしたいと思います。ここで私が使用していたコードされています。私はボタンをドロップすると、私は追加しているとき、私は次の例外を取得し同じアプリケーションのドラッグアンドドロップボタンで例外をスローする

public partial class MainWindow : Window 
{ 
    private Point startPoint; 

    public MainWindow() 
    { 
     InitializeComponent(); 
    } 

    private void Button_PreviewMouseLeftButtonDown(object sender, MouseButtonEventArgs e) 
    { 
     startPoint = e.GetPosition(null); 
    } 

    private void Button_PreviewMouseMove(object sender, MouseEventArgs e) 
    { 
     Point currentPosition = e.GetPosition(null); 
     Vector diff = startPoint - currentPosition; 

     if (e.LeftButton == MouseButtonState.Pressed && 
      (Math.Abs(diff.X) > SystemParameters.MinimumHorizontalDragDistance || 
      Math.Abs(diff.Y) > SystemParameters.MinimumVerticalDragDistance)) 
     { 
      Button button = sender as Button; 

      DataObject dragData = new DataObject("myFormat", button); 
      DragDrop.DoDragDrop(button, dragData, DragDropEffects.Copy); 
     } 
    } 

    private void Canvas_DragEnter(object sender, DragEventArgs e) 
    { 
     if (!e.Data.GetDataPresent("myFormat") || sender == e.Source) 
     { 
      e.Effects = DragDropEffects.None; 
     } 
    } 

    private void Canvas_Drop(object sender, DragEventArgs e) 
    { 
     if (e.Data.GetDataPresent("myFormat")) 
     { 
      Button button = e.Data.GetData("myFormat") as Button; 

      Canvas canvas = sender as Canvas; 
      canvas.Children.Add(button); 

     } 
    } 
} 

XAML:ここでは、コードの後ろに

<Window> 
    <Grid> 
     <Canvas 
      Height="300" 
      Width="500" 
      Background="Gray"> 
      <Canvas 
       Name="cnvToolBox" 
       Canvas.Left="10" 
       Canvas.Top="10" 
       Background="AliceBlue" 
       Width="100" 
       Height="200"> 
       <Button 
        Content="Drag Me!" 
        PreviewMouseLeftButtonDown="Button_PreviewMouseLeftButtonDown" 
        PreviewMouseMove="Button_PreviewMouseMove"></Button> 
      </Canvas> 
      <Rectangle 
       Canvas.Left="119" 
       Canvas.Top="9" 
       Width="102" 
       Height="202" 
       StrokeDashArray="0.5 1.0 0.3" 
       Stroke="Black" 
       StrokeThickness="2"/> 
      <Canvas  
       Name="cnvButtonDropZone" 
       Canvas.Left="120" 
       Canvas.Top="10" 
       Width="100" 
       Height="200" 
       Background="LightGreen" 
       AllowDrop="True" 
       DragEnter="Canvas_DragEnter" 
       Drop="Canvas_Drop"> 
      </Canvas> 
     </Canvas> 
    </Grid> 
</Window> 

をですボタンをキャンバスに追加します。

指定された要素は既に別の要素の論理的な子です。最初に切断します。

私はコントロールをドラッグアンドドロップする方法を勉強しようとしていますが、そのエラーの意味と解決方法については実際には分かりません。私はどこが間違っているのか分かりません。どんな提案も大歓迎です。

ありがとうございます!

答えて

2

このボタンは、親のcnvToolBoxによって所有されています。キャンバスに追加する前にcnvToolBoxからそれを削除する必要があります。

  cnvToolBox.Children.Remove(button); 
      var canvas = sender as Canvas; 
      canvas.Children.Add(button); 

ボタンをツールボックスからキャンバスに移動します。あなたが実際にアイテムのクローンを作成したい場合はあなたのような何かをしたい:

 if (e.Data.GetDataPresent("myFormat")) 
     { 
      var contentControl = (ContentControl)e.Data.GetData("myFormat"); 

      var constructorInfo = contentControl.GetType().GetConstructor(new Type[] {}); 
      if (constructorInfo != null) 
      { 
       var newElement = (UIElement)constructorInfo.Invoke(new object[]{}); 

       var newContentControl = newElement as ContentControl; 
       if(newContentControl != null) 
       { 
        newContentControl.Content = contentControl.Content; 
       } 

       ((Panel)sender).Children.Add(newElement); 
      } 
     } 
+0

キャンバス(パネル)がStackPanelに変更されたので、複数のアイテムを追加できました。 – Phil

+2

また、直後にnullをテストしない限り、Button Button = sender from Buttonのようなステートメントは使用しません。あなたがボタンでなければならないことがわかっている場合、それをボタンにキャストします。 – Phil

+0

Worked!乾杯! –

1

それButtonに、すでに関連付けられている親を持っているためです。前のCanvas

ボタンの親をnullに設定できます。基本的に論理関係から削除されます。

button.Parent = null; 

あなたは、あなたの後ろにあなたのコード内で行ったように、別のCanvasにそのボタンを追加することができます。

ChildrenのプロパティからButtonを直接削除し、新しいCanvasに追加することもできます。

Canvas.Children.Remove(button); 
関連する問題