IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

C# Discussion :

Désabonner un évènement _Leave ne fonctionne pas


Sujet :

C#

  1. #1
    Membre éclairé
    Homme Profil pro
    autre
    Inscrit en
    Janvier 2015
    Messages
    240
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : autre

    Informations forums :
    Inscription : Janvier 2015
    Messages : 240
    Par défaut Désabonner un évènement _Leave ne fonctionne pas
    Bonjour,

    C'est un problème tout bête mais un peu délicat à expliquer (d'où les dessins).

    J'ai une ListView. Un clique sur un élément rafraîchit un Panel avec les données de l'élément cliqué.
    Chaque élément possède une propriété 1 ou 2.
    Je veux que dans le Panel suivant la valeur 1 ou 2, l'onglet d'un TabControl soit sélectionné.

    Nom : LeavePB1.jpg
Affichages : 196
Taille : 17,6 Ko

    Le Panel possède un évènement Leave.
    Afin qu'un enregistrement automatique des données soit effectué avant d'afficher l'élément suivant de ListView qui aurait été cliqué.

    Quand les éléments successifs de Listview cliqués possèdent la même propriété (1 ou 2), le TabControl n'est pas modifié.

    Nom : LeavePB2.jpg
Affichages : 186
Taille : 20,2 Ko

    Le problème survient quand TabControl doit changer (de 1 à 2 ou inversement).

    Nom : LeavePB3.jpg
Affichages : 186
Taille : 17,5 Ko

    Leave est déclenché, alors même que la souris ne survole pas le Panel.
    Des enregistrement intempestifs de l'élément de ListView à peine cliqué se produisent, en cours d'affichage, avec des effets de bords et perte de données.

    Ma première idée a été d'empêcher l'évenement Leave du Panel de se produire pendant le rafraîchissement de Panel :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    DonneesPanel.Leave -= DonneesPanel_Leave;
    puis, après l'affichage :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    DonneesPanel.Leave += DonneesPanel_Leave;
    Ça ne fonctionne pas. Je ne comprends pas pourquoi, alors que :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    DonneesPanel.Enter -= DonneesPanel_Enter;
    DonneesPanel.Enter += DonneesPanel_Enter;
    Fonctionne !

    Dès que TabControl doit changer, l'évènement _Leave de Panel est déclenché.
    Un enregistrement de la fiche qui est en train de se charger se produit, sans que je puisse l'empêcher.

    Merci pour votre aide

  2. #2
    Membre Expert
    Profil pro
    Inscrit en
    Septembre 2010
    Messages
    1 689
    Détails du profil
    Informations personnelles :
    Âge : 47
    Localisation : France

    Informations forums :
    Inscription : Septembre 2010
    Messages : 1 689
    Par défaut
    la propriété 1 ou 2 appartient à l'élément dans le listview, pourquoi donc ce ne serait pas une propriété de celui-ci, qui est mis à jour quand tu changes son tabcontrol (= propriété);
    et quand tu cliques sur l'élément dans le listview, cette propriété détermine le tabcontrol actif
    c'est l'élément qui détermine l'affichage, pas le contraire

  3. #3
    Membre éclairé
    Homme Profil pro
    autre
    Inscrit en
    Janvier 2015
    Messages
    240
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : autre

    Informations forums :
    Inscription : Janvier 2015
    Messages : 240
    Par défaut
    Affichage : Tout ce qu'il y a dans le Panel est mis à jour par les propriétés (champs de BdD) de l'élément cliqué dans la listview.
    Modification : Si l'utilisateur ne clique pas sur le bouton "enregistrer" en quittant le Panel un enregistrement automatique se produit (évènement Leave). S'il y a des modifs faites dans le Panel, elles sont ainsi enregistrées en BdD.

    Il n'y a pas là, je crois, d'erreur logique.

    À l'affichage (élément de ListView cliqué), je peux rafraîchir tout ce qu'il y a dans le Panel, y compris dans le TabControl.
    C'est uniquement quand les propriétés de l'élément cliqué nécessite de changer l'onglet du TabControl qu'un événement Leave du Panel est déclenché après l'affichage.
    Ce que je voudrais éviter.

    Je soupçonne ce comportement d'engendrer des enregistrements avec des valeurs erronées.

  4. #4
    Membre Expert
    Profil pro
    Inscrit en
    Septembre 2010
    Messages
    1 689
    Détails du profil
    Informations personnelles :
    Âge : 47
    Localisation : France

    Informations forums :
    Inscription : Septembre 2010
    Messages : 1 689
    Par défaut
    L'événement Leave se produit quand le contrôle perd le focus d'entrée, donc lors du clic sur un élément du listview (ou ailleurs).
    Donc est-ce que c'est vraiment le bon événement? et est-ce qu'il est mis sur le bon contrôle?
    Est-ce que tu as d'autres événements Leave pour d'autres contrôles ?

    https://learn.microsoft.com/en-us/do....control.enter
    The Enter and Leave events are hierarchical and will cascade up and down the parent chain until the appropriate control is reached. For example, assume you have a Form with two GroupBox controls, and each GroupBox control has one TextBox control. When the caret is moved from one TextBox to the other, the Leave event is raised for the TextBox and GroupBox, and the Enter event is raised for the other GroupBox and TextBox.

  5. #5
    Membre éclairé
    Homme Profil pro
    autre
    Inscrit en
    Janvier 2015
    Messages
    240
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : autre

    Informations forums :
    Inscription : Janvier 2015
    Messages : 240
    Par défaut
    En fait je ne fais que cliquer d'un élément du ListView à un autre.
    À aucun moment la souris ne quitte la ListView.

    Un point d'arrêt dans l'évènement _Leave du Panel m'indique que c'est cet évènement qui est déclenché quand l'onglet du TabControl change.

    Quand, dans la méthode qui affiche les infos de l'élément cliqué, je mets en commentaire la ligne qui change l'onglet du TabControl, l'évènement Leave du Panel n'est pas déclenché.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
     
                if (ArticleRow["Vendu"].ToString() == "1")
                {
                    VenduCheck.Checked = true;
                    VenduLabel.Text = "VENDU";
                    VenduLabel.ForeColor = Color.DarkCyan;
                    VenduLabel.Font = fBold;
                    DateSortie.Visible = true;
     
                    //ElemCommerceTab.SelectedTab = ElemCommerceTab.TabPages[0]; // --------------- En attendant de trouver une solution : Pb donneesPanel_Leave() ------------------
                }
                else
                {
                    VenduCheck.Checked = false;
                    VenduLabel.Text = "En vente";
                    VenduLabel.ForeColor = Color.DarkGray;
                    VenduLabel.Font = fregular;
                    DateSortie.Visible = false;
     
                    //ElemCommerceTab.SelectedTab = ElemCommerceTab.TabPages[1]; // --------------- En attendant de trouver une solution : Pb donneesPanel_Leave() ------------------
                }
    À noter que l'évènement _Enter du Panel se produit aussi lors de l'affichage s'il y a changement de l'onglet du TabControl.
    Mais, celui-là, j'arrive à le désabonner avec :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    DonneesPanel.Enter -= DonneesPanel_Enter;
    ...
    DonneesPanel.Enter += DonneesPanel_Enter;
    Mais jamais _leave.
    Je reste très perplexe quant à ce problème.

    TabControl doit certainement prendre le focus quand l'onglet à afficher est changé.
    Et par effet de "cascade up", comme tu l'as expliqué, c'est l'évènement _Leave du panel qui le contient qui est déclenché.

    Je vais essayer un truc.
    Désabonner l'évènement _Enter du TabControl (qui n'a pour l'instant, pas de méthode associée. Je vais en créer une vide).

  6. #6
    Membre éclairé
    Homme Profil pro
    autre
    Inscrit en
    Janvier 2015
    Messages
    240
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : autre

    Informations forums :
    Inscription : Janvier 2015
    Messages : 240
    Par défaut
    Désabonner TabControl _Enter, qui est effectivement déclenché, idem Panel_Enter quand l'onglet est modifié, ne résout pas le problème.

    Je précise que je n'utilise pas de contrôle personnalisé.
    TabControl est celui de Windows.Forms.

    J'ai aussi essayé d'utiliser
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    ElemCommerceTab.SelectedIndex = 0;
    ...
    ElemCommerceTab.SelectedIndex = 1;
    au lieu de
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    ElemCommerceTab.SelectedTab = ElemCommerceTab.TabPages[0];
    ...
    ElemCommerceTab.SelectedTab = ElemCommerceTab.TabPages[1];
    Aucun changement.

    Le TabControl étant momentanément "disabled" durant le changement d'élément ListView cliqué (effacement des données de Panel), je l'ai remis "Enabled" après le changement d'onglet.
    Aucun effet.


    C'est un curieux problème.

  7. #7
    Membre Expert
    Profil pro
    Inscrit en
    Octobre 2006
    Messages
    704
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2006
    Messages : 704
    Par défaut
    IA nous dit :
    Le désabonnement d'un événement Leave peut ne pas être immédiat car le système peut encore traiter les actions en cours ou les événements en attente.

    Exemple typique :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    public partial class MyForm : Form
    {
        public MyForm()
        {
            InitializeComponent();
            panel1.Leave += Panel1_Leave;
        }
     
        private void Panel1_Leave(object? sender, EventArgs e)
        {
            // Désabonnement dans le même gestionnaire
            panel1.Leave -= Panel1_Leave;   // ← ne retire pas l’appel en cours
            MessageBox.Show("Leave exécuté");
        }
    }
    Le message « Leave exécuté » apparaît même si le désabonnement a eu lieu, car le gestionnaire était déjà dans la liste copiée.

    Si vous maintenez cette voie, il faudra peut-être désabonner Panel_Leave plus en amont?

  8. #8
    Membre éclairé
    Homme Profil pro
    autre
    Inscrit en
    Janvier 2015
    Messages
    240
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : autre

    Informations forums :
    Inscription : Janvier 2015
    Messages : 240
    Par défaut
    Si vous maintenez cette voie, il faudra peut-être désabonner Panel_Leave plus en amont?
    Oui, je viens de tenter ça. Merci.
    Le plus en amont possible c'est dans la méthode "ListView_SelectedIndexChanged()"

    Si je désabonne en première instruction, et réabonne en dernière instruction : Aucun effet.
    Panel_Leave est toujours déclenché.

    Après j'ai mis en commentaire le réabonnement et je l'ai placé dans un bouton_click().
    Cette fois le Panel_Leave n'est plus déclenché durant l'affichage avec changement de Tab de TabControl.
    Donc, à cette place le désabonnement fonctionne.

    Lorsque je clique sur le bouton, Panel_Leave est bien réabonné.
    Mais je n'ai aucun moyen de réabonner Panel_Leave automatiquement après l'affichage.
    C'est comme si, un réabonnement n'importe où dans la procédure déclenchée par "ListView_SelectedIndexChanged()" annulait le désabonnement.

    J'ai aussi essayé de trouver une différence dans l'objet "sender" transmis à Panel_Leave, entre le cas "procédure d'affichage normale" et "perte de focus suite à action de l'utilisateur", mais je n'ai absolument rien trouvé. Les deux "sender" semblent identiques.

  9. #9
    Membre Expert
    Profil pro
    Inscrit en
    Octobre 2006
    Messages
    704
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2006
    Messages : 704
    Par défaut
    Bonjour
    je serais plutôt remonté en restant au niveau du Panel, genre :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
            private void tabControl1_Leave(object sender, EventArgs e)
            {
                panel1.Leave -= panel1_Leave;
            }
     
            private void panel1_Enter(object sender, EventArgs e)
            {
                panel1.Leave += panel1_Leave;
            }
    Après il y a peut-être possibilité de placer dans ces deux routines une sorte d'observateur qui commandera l'exécution ou non des actions de Panel_Leave en remplacement des abonnements et désabonnements.

  10. #10
    Membre éclairé
    Homme Profil pro
    autre
    Inscrit en
    Janvier 2015
    Messages
    240
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : autre

    Informations forums :
    Inscription : Janvier 2015
    Messages : 240
    Par défaut
    Je viens de tester l'emplacement que tu proposes.
    Aucun effet.

    Après il y a peut-être possibilité de placer dans ces deux routines une sorte d'observateur qui commandera l'exécution ou non des actions de Panel_Leave en remplacement des abonnements et désabonnements.
    C'était mon idée quand j'ai analysé l'objet "sender" de Panel_Leave.
    Écrire une condition quelconque qui empêche l'écriture dans la BdD suivant le cas.
    Mais je ne trouve rien qui me permette de déterminer dans la méthode _Leave du Panel si la modification du Tab de TabControl provient d'un clique dans ListView (changement d'élément) ou d'une action/modification réelle des données du Panel de la part de l'utilisateur.
    La hiérarchie des appels est identique.

  11. #11
    Membre éclairé
    Homme Profil pro
    autre
    Inscrit en
    Janvier 2015
    Messages
    240
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : autre

    Informations forums :
    Inscription : Janvier 2015
    Messages : 240
    Par défaut
    J'ai tenté d'introduire une variable globale booléenne (FlagDisplayTAB 'false' par défaut) afin de définir le comportement au sein de la méthode Panel_Leave.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
     
            private void ArticlesListView_SelectedIndexChanged(object sender, EventArgs e)
            {
                FlagDisplayTAB = true;
                ...
            }
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
            private void DonneesPanel_Leave(object sender, EventArgs e)
            {
                if (FlagDisplayTAB == true)
                {
                    FlagDisplayTAB = false;
                    return;
                }
            }
    Mais, il semble qu'il y ait une impossibilité logique de faire ainsi.
    Durant l'affichage, lors du comportement non désiré Panel_Leave, FlagDisplayTAB est rendu 'false'.
    Mais FlagDisplayTAB reste 'false' quand Panel_Leave devrait fonctionner, c'est à dire en cas de modification de la fiche par l'utilisateur. Les modification ne sont donc pas enregistrées automatiquement.

    Je ne peux pas placer
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    FlagDisplayTAB = false;
    ailleurs que dans Panel_Leave, car Panel_Leave s'exécute après toute la procédure d'affichage, il serait toujours 'false' sinon.
    Bref, mauvaise piste.

  12. #12
    Membre Expert
    Profil pro
    Inscrit en
    Octobre 2006
    Messages
    704
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2006
    Messages : 704
    Par défaut
    bonjour
    Y a t'il beaucoup de contrôles dont le contenu peut être modifié par l'utilisateur et justifier une écriture dans la BdD ?
    Ne serait t'il pas plus facile de surveiller d'éventuelles modifications de ces contenus et de décider de l'écriture au Leave du Panel?

  13. #13
    Membre éclairé
    Homme Profil pro
    autre
    Inscrit en
    Janvier 2015
    Messages
    240
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : autre

    Informations forums :
    Inscription : Janvier 2015
    Messages : 240
    Par défaut
    Bonjour,

    Il y a une trentaine de contrôle modifiables.
    Utiliser donc une variable globale pour 'flagger' toute modification de l'un de ces contrôles.
    Ça peut être une solution.
    Merci

    Voici à quoi ressemble le Panel "en vrai" :

    Nom : DonneesPanel_annoté.jpg
Affichages : 97
Taille : 86,3 Ko
    Si l'article est vendu l'onglet "Statut" se rempli d'une quantité d'informations sur la vente.
    S'il n'est pas vendu, c'est l'onglet "Offres" qu'il est plus intéressant d'afficher.

  14. #14
    Membre éclairé
    Homme Profil pro
    autre
    Inscrit en
    Janvier 2015
    Messages
    240
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : autre

    Informations forums :
    Inscription : Janvier 2015
    Messages : 240
    Par défaut
    J'ai trouvé le moyen de contourner le problème.

    Puisque je m'étais rendu compte qu'un désabonnement de Panel_Leave fonctionnait placé le plus en amont possible, dans ListView_SelectedIndexChanged(), je le conserve à cet endroit.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
     
            private void ArticlesListView_SelectedIndexChanged(object sender, EventArgs e)
            {
                DonneesPanel.Leave -= DonneesPanel_Leave; // Fonctionne ici
                ...
            }
    Mon problème était de me réabonner.
    Je ne pouvais le faire nulle part dans la procédure d'affichage.

    J'utilise pour cela un timer de 1000 ms.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
     
                if (ArticleRow["Vendu"].ToString() == "1")
                {
                    VenduCheck.Checked = true;
                    VenduLabel.Text = "VENDU";
                    VenduLabel.ForeColor = Color.DarkCyan;
                    VenduLabel.Font = fBold;
                    DateSortie.Visible = true;
     
                    ElemCommerceTab.SelectedTab = ElemCommerceTab.TabPages[0]; // <--------------- Pb donneesPanel_Leave() ------------------
     
                }
                else
                {
                    VenduCheck.Checked = false;
                    VenduLabel.Text = "En vente";
                    VenduLabel.ForeColor = Color.DarkGray;
                    VenduLabel.Font = fregular;
                    DateSortie.Visible = false;
     
                    ElemCommerceTab.SelectedTab = ElemCommerceTab.TabPages[1]; // <--------------- Pb donneesPanel_Leave() ------------------
                }
     
                PanelLeaveTimer.Start(); //ElemCommerceTab.Enabled = true; ----> Placé dans PanelLeaveTimer.Tick()
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
            private void PanelLeaveTimer_Tick(object sender, EventArgs e)
            {
                DonneesPanel.Leave += DonneesPanel_Leave;
                ElemCommerceTab.Enabled = true;
                PanelLeaveTimer.Stop();
            }
    À présent tout fonctionne correctement.
    Les données sont enregistrées si Panel prend et perd le focus uniquement par action de l'utilisateur, et c'est l'article consulté et totalement affiché que l'utilisateur quitte qui est enregistré, pas le suivant que l'utilisateur souhaite afficher par son clic dans la ListView.

    Néanmoins, le comportement de TabControl, qui, contrairement à tous les autres contrôles du Panel (et il y en a presque de toutes sortes), prend le focus quand son onglet affiché change, me surprend beaucoup.
    Mon problème démontre que ce comportement est piégeux.

    Merci à tous pour votre aide précieuse

  15. #15
    Expert confirmé
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Février 2005
    Messages
    5 604
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 54
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Conseil

    Informations forums :
    Inscription : Février 2005
    Messages : 5 604
    Par défaut
    Je suis assez surpris que personne ne l'est proposé avant, mais pourquoi n'avez vous pas une architecture type Document/Vue , MCV, MVP, etc... pour simplifier toute cette logique d'affichage ?
    (J'ai pas tout compris à vous problématique de dynamique d'affichage)

  16. #16
    Membre éclairé
    Homme Profil pro
    autre
    Inscrit en
    Janvier 2015
    Messages
    240
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : autre

    Informations forums :
    Inscription : Janvier 2015
    Messages : 240
    Par défaut
    Je ne suis pas sûr qu'une architecture quelconque m'aurait évité ce problème.
    C'est un comportement curieux de TabControl qui le provoque, en prenant le focus de manière inattendue pour moi.

    Il s'agit d'une appli de bureau, Winforms.
    Dataset, Dataview etc...
    Elle mériterait certainement une refonte en profondeur.
    Avec ses 36000 lignes, ça deviendrait un chantier

    Quand je l'ai commencée en 2020, je n'avais pas de notions en MVC.
    Pour un autre projet, un site web, je suis en MVC, mais pour une appli de bureau je ne comprends pas bien comment je pourrais faire.

  17. #17
    Membre Expert
    Profil pro
    Inscrit en
    Septembre 2010
    Messages
    1 689
    Détails du profil
    Informations personnelles :
    Âge : 47
    Localisation : France

    Informations forums :
    Inscription : Septembre 2010
    Messages : 1 689
    Par défaut
    Citation Envoyé par AMP29 Voir le message
    J'ai trouvé le moyen de contourner le problème.

    Puisque je m'étais rendu compte qu'un désabonnement de Panel_Leave fonctionnait placé le plus en amont possible, dans ListView_SelectedIndexChanged(), je le conserve à cet endroit.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
     
            private void ArticlesListView_SelectedIndexChanged(object sender, EventArgs e)
            {
                DonneesPanel.Leave -= DonneesPanel_Leave; // Fonctionne ici
                ...
            }
    Mon problème était de me réabonner.
    Je ne pouvais le faire nulle part dans la procédure d'affichage.

    J'utilise pour cela un timer de 1000 ms.

    À présent tout fonctionne correctement.
    Les données sont enregistrées si Panel prend et perd le focus uniquement par action de l'utilisateur, et c'est l'article consulté et totalement affiché que l'utilisateur quitte qui est enregistré, pas le suivant que l'utilisateur souhaite afficher par son clic dans la ListView.

    Néanmoins, le comportement de TabControl, qui, contrairement à tous les autres contrôles du Panel (et il y en a presque de toutes sortes), prend le focus quand son onglet affiché change, me surprend beaucoup.
    Mon problème démontre que ce comportement est piégeux.

    Merci à tous pour votre aide précieuse
    j'allais dire, en relisant ton #10, désinscrit le leave quand tu cliques sur le Listview, et réinscrit toi une fois le panel chargé (ça pourrait peut-être être à la fin du même événement, après avoir forcer l'affichage)

    Si tu changes l'onglet visible du tabcontrol, celui-ci a forcément le focus à un moment donné puisqu'il passe devant les autres, rien d'étrange selon moi.

  18. #18
    Membre éclairé
    Homme Profil pro
    autre
    Inscrit en
    Janvier 2015
    Messages
    240
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : autre

    Informations forums :
    Inscription : Janvier 2015
    Messages : 240
    Par défaut
    désinscrit le leave quand tu cliques sur le Listview, et réinscrit toi une fois le panel chargé
    Pour le désabonnement, c'est ce que je fais maintenant.
    C'est la première instruction de ma méthode 'ArticlesListView_SelectedIndexChanged()'.
    Mais, comme je le dis dans mon #8, un réabonnement en dernière instruction de la même méthode, et a fortiori n'importe où entre le clic dans ListView et la fin de l'affichage de Panel, annule le désabonnement et déclenche l'évènement _Leave de Panel à la fin de l'affichage.
    Rien ne suit l'affichage du Panel, je ne fais plus rien.
    D'où le timer, seule façon que j'ai trouvé d'exécuter du code après.

    Si tu changes l'onglet visible du tabcontrol, celui-ci a forcément le focus
    Ok, je peux comprendre la logique, mais pourquoi est-elle si différente sur ce point de celle d'un bouton toggle, d'un ComboBox ou d'une CheckBox ?
    Contrôles dont je modifie aussi la valeur affichée dans ma procédure.
    Par exemple, "Catégorie" possède une action "TextChanged", et "Taxonomie" "SelectedIndexChanged".
    Cela doit souvent arriver d'avoir besoin de modifier par programmation l'onglet affiché d'un TabControl, sans souhaiter que le TabControl, ce faisant, prenne le focus.

    Et enfin, ce qui m'intrigue aussi, c'est de ne pas réussir à désabonner et réabonner aussi simplement que je le fais à de nombreux moments de mon appli quand j'affiche des données.
    En fait, à tous les endroits où un contrôle possède du code lié à une de ses propriétés de changement (_enter, _leave, ToutTrucChanged etc...).
    Le désabonnement et le réabonnement encadrent souvent, au sein de la même méthode, juste les quelques lignes nécessaires à la modification d'un contrôle.
    Le titre de cette discussion devrait être : "Réabonner un évènement _Leave ne fonctionne pas"

  19. #19
    Expert confirmé
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Février 2005
    Messages
    5 604
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 54
    Localisation : France, Val de Marne (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Conseil

    Informations forums :
    Inscription : Février 2005
    Messages : 5 604
    Par défaut
    Par exemple, avec une approche MVC, vous n'avez pas à vous abonner, désabonner, etc... en fonction de l'affichage.
    Les interactions génèrent des commandes qui changent le modèle, l'affichage n'a qu'à réafficher le modèle mis jour.
    Etc...
    Le cas d'usage habituel de ce type d'architecture.

  20. #20
    Membre éclairé
    Homme Profil pro
    autre
    Inscrit en
    Janvier 2015
    Messages
    240
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : autre

    Informations forums :
    Inscription : Janvier 2015
    Messages : 240
    Par défaut
    Citation Envoyé par bacelar Voir le message
    Par exemple, avec une approche MVC, vous n'avez pas à vous abonner, désabonner, etc... en fonction de l'affichage.
    Les interactions génèrent des commandes qui changent le modèle, l'affichage n'a qu'à réafficher le modèle mis jour.
    Etc...
    Le cas d'usage habituel de ce type d'architecture.
    Je vais creuser le sujet.
    Merci

+ Répondre à la discussion
Cette discussion est résolue.
Page 1 sur 2 12 DernièreDernière

Discussions similaires

  1. Réponses: 6
    Dernier message: 27/01/2004, 12h14
  2. [FP]Writeln ne fonctionne pas !
    Par néo333 dans le forum Turbo Pascal
    Réponses: 4
    Dernier message: 02/11/2003, 00h47
  3. UNION qui ne fonctionne pas
    Par r-zo dans le forum Langage SQL
    Réponses: 7
    Dernier message: 21/07/2003, 11h04
  4. Un Hint sur un PopupMenu ne fonctionne pas !!??
    Par momox dans le forum C++Builder
    Réponses: 6
    Dernier message: 26/05/2003, 17h48
  5. ca ne fonctionne pas (generateur auto-incrémentant)
    Par tripper.dim dans le forum SQL
    Réponses: 7
    Dernier message: 26/11/2002, 01h10

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo