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

JavaScript Discussion :

Event + closure


Sujet :

JavaScript

  1. #1
    Membre régulier
    Profil pro
    Inscrit en
    Juin 2008
    Messages
    155
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2008
    Messages : 155
    Points : 75
    Points
    75
    Par défaut Event + closure
    Bonjour à tous

    J'ai récupéré et adapté le handler suivant qui sert à différencier click/dbleClick.

    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
    25
    var doubleClickCallback = function(e){ console.log('double') },
          singleClickCallback = function(e){ console.log('single') };//e.stopPropagation(); 
     
      var makeDoubleClick = function(e) {
          return (function () {
            var clicks = 0,
                timeout;
     
            return function () {
                var event = e;
                clicks++;
     
                if (clicks == 1) {
                    timeout = setTimeout(function () {
                        singleClickCallback(event);
                        clicks = 0;
                    }, 300);
                } else {
                    clearTimeout(timeout);
                    doubleClickCallback(event);
                    clicks = 0;
                }
            };
        }());
      }
    Cette version me semble préférable à celle qui consiste à utiliser l'event dblclick. On peut toujours discuter de sa pertinence (et si vous avez mieux ça m'intéresse) mais ce n'est pas la question ici.

    Ma question c'est comment récupérer l'event e (pour l'envoyer aux handlers terminaux) sachant que je ne parviens pas à l'envoyer à cette structure, parce que l'affectation se fait de façon inhabituelle, la 1ère fonctionne alors que la 2nde (que je veux utiliser) ne marche pas :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    element.addEventListener('click', makeDoubleClick(), false);
    element.addEventListener('click', makeDoubleClick, false);
    Je sais bien que peux toujours faire ça :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    element.addEventListener('click', function(e){ makeDoubleClick(e) } , false);
    Mais sinon qu'est ce que j'ai pas compris ?

    Merci d'avance

  2. #2
    Expert éminent
    Avatar de Watilin
    Homme Profil pro
    En recherche d'emploi
    Inscrit en
    Juin 2010
    Messages
    3 094
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 35
    Localisation : France, Ille et Vilaine (Bretagne)

    Informations professionnelles :
    Activité : En recherche d'emploi

    Informations forums :
    Inscription : Juin 2010
    Messages : 3 094
    Points : 6 755
    Points
    6 755
    Par défaut
    Une closure dans une closure ?

    Regardons ça en couleurs :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
      var makeDoubleClick = function(e) {
          return (function () {
            var clicks = 0,
                timeout;
     
            return function () {
                var event = e;
                …
            };
          }());
      }
    Tu as trois fonctions imbriquées : makeDoubleClick en rouge, une fonction immédiatement invoquée en bleu (pas forcément utile d'ailleurs), et la fonction retournée par tout ce beau monde en vert.

    C'est cette troisième fonction qui est censée servir de gestionnaire d'évènement. C'est celle-là qui devrait avoir un argument e. Au lieu de ça, elle utilise le e de la fonction makeDoubleClick. Et comme tu ne passes aucun paramètre à makeDoubleClick, le e est simplement undefined.

  3. #3
    Membre régulier
    Profil pro
    Inscrit en
    Juin 2008
    Messages
    155
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2008
    Messages : 155
    Points : 75
    Points
    75
    Par défaut
    Une closure dans une closure ?
    Ah mais oui ... :-(

    Bon, alors voici une version corrigée avec tes indications :
    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
    var makeDoubleClick = function(e) {
     
        var clicks = 0,
            timeout;
     
        return function (e) {
     
          clicks++;
     
          if (clicks == 1) {
            timeout = setTimeout(function () {
            singleClickCallback(e);
            clicks = 0;
            }, 300);
          } else {
            clearTimeout(timeout);
            doubleClickCallback(e);
            clicks = 0;
          }
        };
      }
    Merci bien, ça marche en effet, mais ça marche avec cette affectation :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    input.addEventListener('mousedown' , makeDoubleClick() , false);
    Pour ma comprenette pourquoi est ce qu'une affectation normale sans () ne déclenche pas le truc ?

  4. #4
    Expert éminent
    Avatar de Watilin
    Homme Profil pro
    En recherche d'emploi
    Inscrit en
    Juin 2010
    Messages
    3 094
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 35
    Localisation : France, Ille et Vilaine (Bretagne)

    Informations professionnelles :
    Activité : En recherche d'emploi

    Informations forums :
    Inscription : Juin 2010
    Messages : 3 094
    Points : 6 755
    Points
    6 755
    Par défaut
    Ben vu que ta fonction gestionnaire est générée par makeDoubleClick, il est nécessaire d'appeler cette dernière pour que la génération se fasse. Je ne sais pas si je suis très clair.

    C'est comme si tu faisais :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    var doubleClick = makeDoubleClick();
    input.addEventListener('mousedown', doubleClick, false);

  5. #5
    Membre régulier
    Profil pro
    Inscrit en
    Juin 2008
    Messages
    155
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juin 2008
    Messages : 155
    Points : 75
    Points
    75
    Par défaut
    Je ne sais pas si je suis très clair.
    Il y a truc que je ne percute pas / ne sais pas ... On est bien d'accord que je place la déclaration de la fonction makeDoubleClick AVANT element.addEventListener('click', ..., false), donc la 'génération' se fait dans les 2 cas ...

    Alors je ne comprends pas pourquoi la 1ère fonctionne mais pas la2nde :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    element.addEventListener('click', makeDoubleClick(), false);
    element.addEventListener('click', makeDoubleClick, false);
    Si j'affecte une fonction 'normale' (sans closure) avec la 1ère ça ne marche pas (du moins e n'est pas envoyé), alors ça vient de la closure ?

  6. #6
    Membre confirmé

    Profil pro
    Inscrit en
    Octobre 2010
    Messages
    311
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2010
    Messages : 311
    Points : 545
    Points
    545
    Par défaut
    C’est très simple !

    • Avec la 1ere : la méthode addEventListener reçoit en paramètre le retour d’appel de la fonction makeDoubleClick, se trouvant être la fonction anonyme encapsuler dans la fonction makeDoubleClick
    • Avec la 2eme : la méthode addEventListener reçoit en paramètre, directement la fonction makeDoubleClick qui lorsqu’il est appelé par le gestionnaire d’évènement, ne gère pas l’évènement click, car c’est la fonction anonyme retourné par makeDoubleClick qui gère l’évènement. makeDoubleClick recoit donc l'evement e mais n'en fait rien

Discussions similaires

  1. Réponses: 4
    Dernier message: 05/11/2004, 14h58
  2. Gérer les events d'un tableau de boutons
    Par lord_kalipsy dans le forum wxWidgets
    Réponses: 7
    Dernier message: 20/10/2004, 10h13
  3. Réponses: 4
    Dernier message: 21/05/2004, 09h13
  4. Accès à une case d'un DBGrid dans l'event OnKeyDown
    Par fba dans le forum Bases de données
    Réponses: 2
    Dernier message: 02/03/2004, 12h48
  5. [C++]closure + héritage + transtypage
    Par JEG dans le forum C++Builder
    Réponses: 11
    Dernier message: 30/01/2004, 14h26

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