2009-05-22 9 views
1

Je tente d'autoriser mes utilisateurs à faire glisser et déposer certaines lignes de données d'un contrôle de liste personnalisé à un autre, où le second contrôle de liste se trouve dans une autre instance de la même application.Glisser des données entre instances

DoDragDrop(parameterTypedListView.SelectedObjects, DragDropEffects.Copy); 

parameterTypedListView.SelectedObjects est un IList générique où T est une classe personnalisée contenant uniquement les champs types de valeur/propriétés.

Dans l'événement OnDragDrop, j'essaie d'extraire ces données mais j'obtiens seulement un objet System.__ComObject ... qui semble hériter de System.MarshalByRefObject. En bref: Comment extraire les données dans un format orienté objet que je peux réellement utiliser? Editer: Définir ma classe personnalisée comme étant sérialisable n'a aucun effet perceptible de quelque manière que ce soit. Je peux énumérer les __ComObject:

foreach (var dataObject in (IEnumerable) e.Data.GetData("System.Collections.ArrayList")) 
{ 
    // this actually enumerates the correct number of times, i.e. as many times as there are items in the list. 
} 

mais chaque dataObject est, en soi, un système .__ ComObject que je ne peux pas jeter à quoi que ce soit utile.

+0

nous parlons du même programme en cours d'exécution deux fois dans 2 cas différents? – Konstantinos

+0

@Konstantinos, Oui, plusieurs instances de la même application. –

Répondre

3

J'ai été capable de répliquer votre problème initial, mais dès que j'ai ajouté l'attribut [Serializable] à la classe dans la liste de tableau, j'ai pu voir les objets comme leur type correct.

Voici un exemple de code, montrant un petit exemple de travail.

public partial class Form1 : Form 
{ 
    public Form1() 
    { 
     InitializeComponent(); 
     this.DragDrop += new System.Windows.Forms.DragEventHandler(this.Form1_DragDrop); 
     this.DragEnter += new System.Windows.Forms.DragEventHandler(this.Form1_DragEnter); 
    } 

    [Serializable] 
    class DragClass 
    { 
     public string Prop1 { get; set; } 
     public int Prop2 { get; set; } 
    } 

    private void label1_MouseDown(object sender, MouseEventArgs e) 
    { 
     System.Collections.ArrayList aDragClasses = new System.Collections.ArrayList(); 
     aDragClasses.Add(new DragClass() { Prop1 = "Test1", Prop2 = 2 }); 
     aDragClasses.Add(new DragClass() { Prop1 = "Test2", Prop2 = 3 }); 
     aDragClasses.Add(new DragClass() { Prop1 = "Test3", Prop2 = 4 }); 

     DoDragDrop(aDragClasses, DragDropEffects.Copy); 
    } 

    private void Form1_DragEnter(object sender, DragEventArgs e) 
    { 
     e.Effect = DragDropEffects.Copy; 
    } 

    private void Form1_DragDrop(object sender, DragEventArgs e) 
    { 
     foreach (var aData in (System.Collections.IEnumerable)e.Data.GetData(typeof(System.Collections.ArrayList))) 
     { 
      System.Diagnostics.Debug.WriteLine(((DragClass)aData).Prop1); 
     } 
    } 



} 
0

Je pense que le problème est que vous utilisez la liste directement pour transmettre les données. Je l'ai essayé de différentes façons pour l'échouer et j'ai trouvé quelques façons que cela ne fonctionne pas.

Si vous ne possédez pas l'attribut [Serializable] sur vos classes personnalisées, cela ne fonctionnera pas correctement car c'est ainsi que les classes sont rassemblées entre les processus. De plus, si j'utilise directement une liste pour transmettre les données, j'obtiens une exception de référence nulle.

Si vous utilisez une classe de transport simple pour transmettre les données (et que tous les types sont sérialisables), tout a bien fonctionné pour moi.

[Serializable] 
class Test 
{ 
    public string Name { get; set; } 
    public string Description { get; set; } 
} 

[Serializable] 
class Transport 
{ 
    public Transport() 
    { 
     this.Items = new List<Test>(); 
    } 
    public IList<Test> Items { get; private set; } 
} 

Je peux le faire sans problème et il fonctionne dans les instances ...

private void Form1_DragDrop(object sender, DragEventArgs e) 
{ 
    foreach (var item in ((Transport)e.Data.GetData(typeof(Transport))).Items) 
    { 
     System.Diagnostics.Debug.WriteLine(item.Name + " " + item.Description); 
    } 
} 
Questions connexes