How to manipulate the order of Event Listeners of a DOM element

2

I have a link:

<a href="foo" class="foo">go to foo</a>

First event handler ( main.js )

document.querySelector('.foo').addEventListener('click', function( event ) {
   console.log(1);
});

In another script, I add the second event handler ( script.js )

document.querySelector('.foo').addEventListener('click', function( event ) {
  console.log(2);
});

When run, I have the following log:

1 (main.js)

2 (script.js)

In this regard, I have two doubts:

  • How to handle this order?
  • How to freeze all event listeners from the link and fire them only if any conditions are met?
  • asked by anonymous 07.08.2015 / 21:58

    2 answers

    1

    Question 1.

    Events will be triggered by order of declaration. Events declared first execute first, because in this way the second click event overrides the first, concatenating the methods as if they were one.

    Question 2.

    The simplest way is to create an auxiliary variable and execute the function if it is true, so you can flex the code

    //main.js
    var executar1;
    //atribuir true à variável executar1 para a condição desejada
    if (true)
       executar1 = true;
    document.querySelector('.foo').addEventListener('click', function( event ) {
       if(executar1)
       console.log(1);
    });
    
    //script.js
    var executar2;
    //Não quero executar a dois, então vou deixá-la nula, valendo como false
    
    document.querySelector('.foo').addEventListener('click', function( event ) {
       if (executar2)
         console.log(2);
       else
         console.log("não quis executar o 2");
    });
    

    If you want to permanently remove events, use the $ (). off () method to remove this function

        
    07.08.2015 / 22:16
    1

    You can not manipulate the order as far as I know, what you can do is create an array with all functions, it would look something like:

    var funcoes = [
        function() {
            console.log("foo");
        },
        function() {
            console.log("Oi");
        },
        function() {
            console.log("Olá mundo!");
        },
        function() {
            console.log("Stack Overflow");
        },
        function() {
            console.log(1);
        },
        function() {
            console.log(2);
        }
    ];
    
    /*
     * Reordenamento da array, coloquei uma ordem aleatória
     * Fonte: http://stackoverflow.com/a/2450976/1518921
     */
    
    function shuffle(array) {
      var currentIndex = array.length, temporaryValue, randomIndex ;
    
      // While there remain elements to shuffle...
      while (0 !== currentIndex) {
    
        // Pick a remaining element...
        randomIndex = Math.floor(Math.random() * currentIndex);
        currentIndex -= 1;
    
        // And swap it with the current element.
        temporaryValue = array[currentIndex];
        array[currentIndex] = array[randomIndex];
        array[randomIndex] = temporaryValue;
      }
    
      return array;
    }
    
    shuffle(funcoes);
    
    var foo = document.getElementById("foo");
    var j = funcoes.length;
    
    for (var i = 0; i < j; i++) {
        foo.addEventListener('click', funcoes[i]);
    }
    <button id="foo">Testar</button>
      

    How to freeze all event listeners in the link and fire them only if any conditions are met?

    To "freeze" you will have to create a separate event that is triggered at the desired time, it would look something like:

    var emEspera = [];
    
    function AdicionarEspera(callback) {
        emEspera.push(callback);
    }
    
    var funcoes = [...];
    
    shuffle(funcoes);
    
    var foo = document.getElementById("foo");
    var j = funcoes.length;
    
    for (var i = 0; i < j; i++) {
        foo.addEventListener('click', function() {
            AdicionarEspera(funcoes[i])
        });
    }
    
    foo.addEventListener('click', function() {
        var copia = emEspera, j = emEspera.length;
    
        emEspera = [];//Limpa eventos em espera
    
        for (var i = 0; i < j; i++) {
            copia[i]();
        }
    });
    
    var test = document.getElementById("test");
    

    html:

    <button id="foo">Adicionar a lista</button>
    <button id="test">Executar eventos em espera</button>
    

    At the moment you click on test then it will execute all waiting events, after clicking it clears the events

        
    07.08.2015 / 22:24