Mouseenter sur un panel contenant pleins de controls

Résolu
stormz23 Messages postés 4 Date d'inscription mardi 31 mai 2005 Statut Membre Dernière intervention 10 avril 2006 - 2 juin 2005 à 19:39
stormz23 Messages postés 4 Date d'inscription mardi 31 mai 2005 Statut Membre Dernière intervention 10 avril 2006 - 3 juin 2005 à 13:11
Bonjour.

J'ai un panel auquel j'ajoute dynamiquement des controls. Ces controls ont eux meme des controls.

J'aimerai pouvoir changer l'opacite de mon control principal (et donc des controls fils) sur un mouseenter/mouseleave. Pour cela je m'abonne aux evenements mouseenter/mouseleave de mon control principal.

Le probleme c'est que mes controls fils prennent toute la largeur de mon control principal. Lorsque je met ma souris dans mon control principal l'evenement mouseenter n'est pas declenche car ma souris est directement dans un contorl fils.

J'aimerai trouver une autre methode que d'abonner tous mes controls, et sous controls aux evenements mouseenter/mouseleave.

Quelqu'un sait comment faire?

Merci.

2 réponses

cs_coq Messages postés 6351 Date d'inscription samedi 1 juin 2002 Statut Membre Dernière intervention 2 août 2014 99
3 juin 2005 à 00:38
Salut,

Une "bidouille" est possible en utilisant un filtre de messages (cf /library/fre/cpref/html/frlrfSystemWindowsFormsIMessageFilterClassTopic.asp IMessageFilter)

La classe implémentant =/library/fre/cpref/html/frlrfSystemWindowsFormsIMessageFilterClassTopic.asp IMessageFilter :
class MouseEnterLeaveMessageFilter : IMessageFilter
{
private const int WM_MOUSEHOVER = 0x02A1;
private const int WM_MOUSELEAVE = 0x02A3;

public MouseEnterLeaveMessageFilter ( Control mainCtrl )
{
m_mainCtrl = mainCtrl;
}

private Control m_mainCtrl;
// sera utilisé pour determiner si on est resorti du controle precedent afin d'eviter une rafale de "Hover"
private bool m_leaved = true;

public bool PreFilterMessage(ref Message m)
{
// récupération du controle (si c'est est un)
Control ctrl = Control.FromHandle(m.HWnd);

if ( ctrl == null )
return false; // pas un controle, fin du traitement

// si le controle est notre conteneur ou un de ses enfants
if ( ctrl.Handle == m_mainCtrl.Handle || m_mainCtrl.Controls.Contains(ctrl))
{
switch ( m.Msg )
{
case WM_MOUSEHOVER:
if ( m_leaved )
{
MessageBox.Show("Enter " + ctrl.Name);
m_leaved = false;
}
break;

case WM_MOUSELEAVE:
MessageBox.Show("Leave " + ctrl.Name);
m_leaved = true;
break;
}
}

return false;
}

private void m_mainCtrl_Disposed(object sender, EventArgs e)
{
// si notre controle à surveiller est detruit, on "auto supprime" le filtre
Application.RemoveMessageFilter(this);
}
}

Exemple d'ajout :
private void Form1_Load(object sender, System.EventArgs e)
{
Application.AddMessageFilter(new MouseEnterLeaveMessageFilter(panel1));
}

Il reste probablement de l'optimisation à faire mais je pense que li'dée générale y est :-)

Cocoricoooooooo !!!!
coq
MVP Visual C#
3
stormz23 Messages postés 4 Date d'inscription mardi 31 mai 2005 Statut Membre Dernière intervention 10 avril 2006
3 juin 2005 à 13:11
Hello.



merci pour ton aide!!!



Seul petit soucis, mon sous-control contient lui-meme des controls. De ce cote pas de soucis, je remplace "if
( ctrl.Handle == m_mainCtrl.Handle ||
m_mainCtrl.Controls.Contains(ctrl))" par quelque chose de plus
generique (une fonction recursive). J'ai juste un peu peur des
perfomances. A chaque deplacement de la souris, checker tous les
controls de mon application me semble assez enorme.
0