web-dev-qa-db-fra.com

Amener le contrôle Winforms au premier plan

Existe-t-il d'autres méthodes pour amener un contrôle au premier plan que control.BringToFront ()? J'ai des séries d'étiquettes sur un contrôle utilisateur et lorsque j'essaie de les mettre en avant, cela ne fonctionne pas. J'ai même parcouru toutes les commandes et les ai renvoyées, à l'exception de celle qui m'intéresse et cela ne change rien.

Voici la méthode par laquelle une étiquette est ajoutée au contrôle utilisateur

private void AddUserLabel()
{
    UserLabel field = new UserLabel();
    ++fieldNumber;

    field.Name = "field" + fieldNumber.ToString();         

    field.Top = field.FieldTop + fieldNumber;
    field.Left = field.FieldLeft + fieldNumber;
    field.Height = field.FieldHeight;
    field.Width = field.FieldWidth;
    field.RotationAngle = field.FieldRotation;
    field.Barcode = field.BarCoded;
    field.HumanReadable = field.HumanReadable;
    field.Text = field.FieldText;
    field.ForeColor = Color.Black;

    field.MouseDown += new MouseEventHandler(label_MouseDown);
    field.MouseUp += new MouseEventHandler(label_MouseUp);
    field.MouseMove += new MouseEventHandler(label_MouseMove);

    userContainer.Controls.Add(field);

    SendLabelsToBack(); //Send All labels to back

    userContainer.Controls[field.FieldName].BringToFront();
}

Voici la méthode qui les envoie tous à l’arrière.

private void SendLabelsToBack()
{
    foreach (UserLabel lbl in userContainer.Controls)
    {
        lbl.SendToBack();
    }
}
15
Nathan

Oui, il y a un autre moyen. Controls.SetChildIndex() change également l'ordre Z. Celui avec l'indice 0 est celui sur le dessus. Cependant, BringToFront() utilise cette méthode.

Votre méthode SendLabelsToBack() telle que donnée ne peut pas fonctionner, elle enverra également le libellé ajouté à l'arrière. Mais votre prochaine déclaration corrige cela à nouveau.

OK, cela ne fonctionne pas, ce qui signifie que la méthode BringToFront() n'est pas exécutée. Recherchez dans la fenêtre de sortie une notification "Exception de la première chance". Tel qu'écrit, votre SendLabelsToBack() provoquera une exception si le contrôle utilisateur contient un contrôle autre qu'un UserLabel. Définissez également un point d'arrêt après l'appel BringToFront() et vérifiez la valeur de userContainer.Controls[0].Name quand il se produit.

18
Hans Passant

Les z-index des contrôles sont par conteneur. 

Si vous appelez BringToFront sur un contrôle qui se trouve dans un conteneur (par exemple, une Panel), le conteneur ne sera pas placé au premier plan.
Par conséquent, le contrôle ira uniquement devant les autres contrôles de ce conteneur.

Pour voir dans quels conteneurs se trouvent vos contrôles, vous pouvez utiliser le volet Structure du document du menu Affichage.

EDIT: Votre contrôle userContainer est probablement derrière un contrôle différent.

6
SLaks

Avez-vous essayé Invalidate() après BringToFront()? BringToFront ne déclenche pas l'événement Paint

essaye ça:

private void SendLabelsToBack()
{
    foreach (UserLabel lbl in userContainer.Controls)
    {
        lbl.SendToBack();
        lbl.Invalidate();
    }
}
5
Patrick

Je pense que vous avez juste besoin de changer votre dernière ligne:

userContainer.Controls[field.FieldName].BringToFront(); 

pour ça:

userContainer.Controls[field.Name].BringToFront(); 

Lorsque vous utilisez une chaîne en tant qu'indexeur pour la collection Controls, elle utilise la propriété Name du contrôle (et non la propriété FieldName).

Puisque vous essayez simplement de placer le contrôle ajouté le plus récemment au sommet, cela fonctionnerait également:

userContainer.Controls[userContainer.Controls.Count - 1].BringToFront();
2
MusiGenesis

De mon expérience, on dirait que Windows place tous les contrôles appartenant à un conteneur graphique (volet, zone de groupe, etc.) dans une collection de logiciels. La collection est classée par index enfant, qui est une propriété de chaque contrôle de ce conteneur. Le problème est que les enfants avec le même index peuvent exister et existent. Dans ce cas, Windows peindra ces enfants ordonnés par rapport à d'autres, mais entre eux, il les peindra dans l'ordre inverse de leur ajout au conteneur. 

Longue histoire: pour un conteneur, vous devez vous assurer que les contrôles ont des index différents en modifiant TOUT PAS QUELQUES-uns des index lorsque vous souhaitez modifier l'ordre Z Par exemple:

foreach (Control newControl in TopControl.Controls)
{
   TopControl.Controls.SetChildIndex(newControl,indexlogic(newControl));
}

indexLogic(newControl ) est votre méthode de calcul de l'indice de contrôle particulier.

0
Gogu CelMare