127 votes

Gestionnaire d'événements Javascript avec paramètres

Je veux faire un eventHandler qui transmet l'événement et certains paramètres. Le problème est que la fonction ne reçoit pas l'élément. Voici un exemple :

doClick = function(func){
    var elem = .. // the element where it is all about
    elem.onclick = function(e){
        func(e, elem);
    }
}
doClick(function(e, element){
    // do stuff with element and the event
});

En elem doit être définie en dehors de la fonction anonyme. Comment puis-je obtenir l'élément passé pour l'utiliser dans la fonction anonyme ? Existe-t-il un moyen de le faire ?

Et qu'en est-il des addEventListener ? Je ne semble pas être en mesure de passer l'événement par le biais d'un addEventListener Je ne suis pas du tout d'accord ?

Mise à jour

Il semble que j'aie résolu le problème avec "ceci

doClick = function(func){
    var that = this;
    this.element.onclick = function(e){
        func(e, that);
    }
}

Où cela se trouve this.element à laquelle je peux accéder dans la fonction.

La fonction addEventListener

Mais je m'interroge sur la addEventListener :

function doClick(elem, func){
    element.addEventListener('click', func(event, elem), false);
}

1voto

Manil Malla Points 69

Essayez,

const handleOnChange = (event, otherParameter) => {
    console.log(`${event.target.value}`);
    console.log(`${otherParameter}`);
}

<Select onchange= (event) => {
    handleOnChange(event, otherParameter);
}>

0voto

jbabey Points 20696

this à l'intérieur de doThings est l'objet de la fenêtre. Essayez plutôt ceci :

var doThings = function (element) {
    var eventHandler = function(ev, func){
        if (element[ev] == undefined) {
            return;
        }

        element[ev] = function(e){
            func(e, element);
        }
    };

    return {
        eventHandler: eventHandler
    };
};

0voto

Teocci Points 1441

Il s'agit d'un vieux sujet et @jfriend00 a fait un très bon travail en expliquant les bases derrière les appels de fonctions de fermeture.

Mettons à jour les snippets en ES6 et utilisons également une autre technique qui pourrait nous aider à surmonter ce genre de scénarios.

Définissons d'abord une fonction handler cette fonction recevra deux paramètres fnc y val où les fnc est la fonction personnalisée qui gérera l'événement ; elle est généralement nommée on + theEventName dans ce cas onClickEvent . Il n'y a rien de nouveau ici. Définissons maintenant le onclick sur l'élément red et il s'appellera clickEventHandler comme ceci :

red.onclick = clickEventHandler

Comme nous l'avons remarqué clickEventHandler n'a pas de paramètre Teo, comment puis-je envoyer le event et le index au gestionnaire ?

Bonne question, appelons d'abord le handler pour créer notre fonction onClickEvent manipulateur comme ceci :

handler(onClickEvent, index)

Mais Teo, onClickEvent n'a pas non plus de paramètres, Comment envoyer la fonction de fermeture onClickEvent , le event produit par onclick y index valeur ?

Patience, mon jeune padawan. Tout d'abord, quelle fonction gérera le event ? Dans notre scénario, il y aura onClickEvent Définissons donc cette fonction pour recevoir le event e et le index valeur v :

function onClickEvent(e, v) {
    console.log(`${e.currentTarget.className} -> [x: ${e.x}, y: ${e.y}] | val: ${v}`)
}

Nous allons maintenant mettre en œuvre notre fonction de traitement. Cette fonction renverra une définition de fonction de fermeture qui exécutera la fonction définie dans la section fnc La fonction de fermeture et la fonction de fermeture sont également fusionnées pour obtenir les paramètres reçus par la fonction de fermeture et la fonction de fermeture. val paramenter comme ceci :

function handler(fnc, val) {
    return (...params) => {
    const ctx = this
    const arg = [...params, val]
    fnc.apply(ctx, arg)
    }
}

Pour appeler le fnc nous avons utilisé apply() . Cette méthode appelle la fonction spécifiée avec un contexte a donné ctx et arg en tant qu'arguments fournis sous la forme d'un tableau. Par conséquent, la fonction fnc est exécuté dans le contexte de la fonction de fermeture ctx .

Il s'agit d'un extrait fonctionnel pour ce scénario.

const red = document.querySelector('.red')
const blue = document.querySelector('.blue')

function handler(fnc, val) {
  return (...params) => {
    const ctx = this
    const arg = [...params, val]
    fnc.apply(ctx, arg)
  }
}

function onClickEvent(e, v) {
  console.log(`${e.currentTarget.className} -> [x: ${e.x}, y: ${e.y}] | val: ${v}`)
}

const index = 50

// Define the handler function
const clickEventHandler = handler(onClickEvent, index)

// Call the debounced function on every mouse move
red.onclick = clickEventHandler

blue.addEventListener('click', clickEventHandler)

.boxes {
  width: 100%;
  height: 120px;
  display: flex;
  flex-flow: row nowrap;
}

.red {
  background: red;
}

.blue {
  background: blue;
}

.box {
  width: 50%;
  display: flex;
  justify-content: center;
  align-items: center;
  color: white;
}

<div class='boxes'>
  <div class='red box'>Click Me</div>
  <div class='blue box'>Not ready</div>
</div>

Maintenant, nous allons appliquer ce concept à votre scénario :

const red = document.querySelector('.red')
const blue = document.querySelector('.blue')
red.clicked = false

let clickEventHandler

function handler(fnc, val) {
  return (...params) => {
    const ctx = this
    const arg = [...params, val]
    fnc.apply(ctx, arg)
  }
}

function onRedClickEvent(e) {
  if (red.clicked) return

  red.clicked = true
  red.textContent = 'Clicked'
  blue.textContent = 'Ready'
  console.log(`${e.currentTarget.className} -> blue is ready`)

  // Define the handler function
  clickEventHandler = handler(onClickEvent, red)

  // Call the debounced function on every mouse move
  blue.addEventListener('click', clickEventHandler)
}

function onClickEvent(e, elem) {
  red.clicked = false
  red.textContent = 'Click Me'
  blue.textContent = 'Not Ready'

  console.log(`${e.currentTarget.className} -> [x: ${e.x}, y: ${e.y}] | elem: ${elem.className}`)

  blue.removeEventListener('click', clickEventHandler)
}

red.onclick = onRedClickEvent

.boxes {
  width: 100%;
  height: 120px;
  display: flex;
  flex-flow: row nowrap;
}

.red {
  background: red;
}

.blue {
  background: blue;
}

.box {
  width: 50%;
  display: flex;
  justify-content: center;
  align-items: center;
  color: white;
  user-select: none;
}

<div class='boxes'>
  <div class='red box'>Click Me</div>
  <div class='blue box'>Not ready</div>
</div>

-2voto

Baznr Points 1
let obj = MyObject();

elem.someEvent( function(){ obj.func(param) } );

//calls the MyObject.func, passing the param.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X