2010-12-13 46 views
0

Je crée un programme de répertoire "high-tech", où si je réussis, les utilisateurs pourront glisser et déposer un numéro, ou une personne, ou un emplacement vers la page de profil d'un autre, les reliant ensemble.Problèmes visuels C++ avec glisser déposer

Les éléments (comme les nombres ou les personnes) sont représentés par une classe dérivée de System :: Windows :: Forms :: UserControl (donc essentiellement un panneau avec des étiquettes et des données sur l'élément représenté stocké dans ses variables membres) . Ce panneau est déplacé dans une fenêtre, qui le transmet au constructeur d'une autre fenêtre, qui fait le lien entre les éléments. Si cet élément est cliqué, il affiche sa page de profil dans une fenêtre.

Le code de l'élément, qui fournit le glisser-déposer:

/* PhonebookElement.h */ 
private: 
    System::Void PhonebookElement_Click(System::Object^ sender, 
      System::EventArgs^ e) { 
     doClick(); 
    } 

    System::Void nameLabel_MouseDown(System::Object^ sender, 
      System::Windows::Forms::MouseEventArgs^ e) { 
     DragDropEffects dde = DoDragDrop(this, DragDropEffects::Copy); 
     if(dde == DragDropEffects::None) 
      doClick(); 
    } 

Le code de la fenêtre de page de profil, qui accepte le glisser-déposer:

/* PhonebookInfoWindow.h */ 
private: 
    System::Void PhonebookInfoWindow_DragOver(System::Object^ sender, 
      System::Windows::Forms::DragEventArgs^ e) { 
     e->Effect = DragDropEffects::Copy; 
    } 

    System::Void PhonebookInfoWindow_DragDrop_1(System::Object^ sender, 
      System::Windows::Forms::DragEventArgs^ e) { 
     MakeRelationWindow^ mrw = gcnew MakeRelationWindow(this->m_hparent, 
      (PhonebookElement^)e->Data->GetData(
       System::Windows::Forms::DataFormats::Serializable),this); 
     mrw->Show(); 
    } 

Le constructeur de la fenêtre maker relation:

/* MakeRelationWindow.h */ 
MakeRelationWindow(PhonebookElement^ first, PhonebookElement^ second, Object^ parent) 
{ 
     InitializeComponent(); 
     // 
     //TODO: Add the constructor code here 
     // 
     this->typeBox->MaxLength = LSTRINGLENGTH; 

     this->first = first; 
     this->second = second; 
     this->parent = parent; 

     this->descriptionBox->Text = "Linking together\r\n" + 
      this->first->maindata + "\r\nand\r\n" + this->second->maindata; 
} 

J'ai deux problèmes:
1. Comme j'ai implémenté l'action MouseDown pour PhonebookElement, elle ne reconnaît pas les clics. (J'ai essayé l'action MouseClick, mais cela n'a pas fonctionné non plus.) J'ai mis la partie if(dde == DragDropEffects::None){doClick();} dans l'action MouseDown comme une solution de contournement, mais ce n'est pas parfait, parce que si l'utilisateur traîne le contrôle quelque part il/elle devrait 't, il sera traité comme un clic aussi.
2. Le tout ne fonctionne pas: D
Je ne sais pas ce que je fais mal (probablement c'est mon utilisation de la fonction GetData(), je ne suis pas très familier avec DataFormats), mais le constructeur de la MakeRelationsWindow obtient une "valeur indéfinie" comme deuxième paramètre.

Comment pourrais-je corriger ces deux problèmes?

P.S. Je suivais ce tutoriel: http://www.codeproject.com/KB/dotnet/csdragndrop01.aspx
C'est pour les cordes C# et drag-dropping, mais toujours le meilleur que j'ai pu trouver.

Répondre

2

Cela ne fonctionne pas car le gestionnaire d'événements DragEnter est manquant. Vous devez définir e-> Effect sur l'un des e-> AllowedEffects pour exécuter l'événement DragDrop. DragOver est uniquement destiné à fournir des commentaires.

Si un démarrage de MouseDown interfère effectivement avec l'événement Click, il n'y aura pas d'événement de souris pour déclencher le clic. Si vous voulez prendre en charge les deux, vous devez le rendre plus sélectif et ne lancer le glisser que lorsque l'utilisateur fait un mouvement de déplacement. Cela nécessite de stocker la position de la souris dans l'événement MouseDown. Utilisez l'événement MouseMove pour vérifier si le bouton gauche est toujours enfoncé. Et appelez DoDragDrop() lorsque vous voyez la souris déplacée par plus de SystemInformation :: DoubleClickSize.

En outre, vous devez vérifier dans le gestionnaire d'événements DragEnter qu'un objet est en train d'être déplacé et que vous savez comment gérer. Vous ne voulez pas, par exemple, accepter un glisser un fichier de l'Explorateur.

+1

Vous pouvez également activer la capture de la souris dans 'MouseDown' et appeler' DoDragDrop' à partir de 'MouseMove' si le curseur est en dehors des limites du contrôle. –

+0

Merci pour la réponse.J'ai réussi à résoudre le deuxième problème en changeant MakeRelationWindow (this-> m_hparent, (PhonebookElement ^) e-> Data-> GetData (Système :: Windows :: Formulaires :: DataFormats :: Serializable), ceci); '' '' MakeRelationWindow (this-> m_hparent, (PhonebookElement ^) e-> Data-> GetData (this-> m_hparent-> GetType() -> ToString()), ceci); 'et il fonctionne parfaitement avec le DragOver ; comme pour le premier, j'essaie votre solution, merci encore. edit: 'this-> m_hparent' est bien sûr un objet PhonebookElement ^, donc il peut être utilisé ici pour obtenir les informations de type nécessaires –

+0

Il a fait l'affaire, merci –