How do you make an event listener that detects if a boolean variable becomes true?

前端 未结 7 2000
-上瘾入骨i
-上瘾入骨i 2020-12-31 19:52

For example, I have var menu_ready = false;. I have an ajax function that sets menu_ready to true when the ajax stuff is done:

//se         


        
7条回答
  •  挽巷
    挽巷 (楼主)
    2020-12-31 20:23

    Since this is a pretty old question and many of these answers are out of date, I thought I'd add a more current answer.

    Background

    Javascript is an event driven language. So, any change that occurs in the environment at any time other than when the page is first loaded is caused by some sort of event. As such, the best way to communicate changes is to use events. You either listen for the same event that caused the change you want to watch or you create a new event to let people know when something specifically has changed.

    Node.js has an eventEmitter object that is very useful and is pure Javascript (no DOM involved). That same code can also be used in the browser if one wants a general purpose event mechanism that is independent of the DOM.

    The browser DOM has it's own event notification system where you can create events, trigger events and listen for events.

    Polling for changes (as the accepted answer here shows) is generally a "hack" that is inefficient, can miss changes, is not necessarily timely, wastes battery and CPU, etc... If you control the code, there is always a better way to design it than polling.

    The OP's Actual Problem

    There still is not efficient mechanism of monitoring a variable change, but the OP's problem was actually that someone wants to know when this code gets triggered:

    $(...).load(..., function() {
        ...
        menu_ready = true;
    }
    

    Of course, one simple answer is that anyone who wants to know when that is ready could also just monitor the same thing this is with $(...).load(), but that would somewhat tie their notification to how this was specifically implemented.

    Creating Our Own Event Notification That Anyone Can Listen For

    Instead, what would be better would be to create our own event and when we know the menu is ready, we trigger that event. Then anyone, anywhere in the code can listen for that same event.

    The browser already has an extensible event system built in as described here. So, we can use that here. You need to pick some well-known object to trigger the event on that exists at the time any listener would want to register to know about this. Since the OP didn't show any specific context, I'll just pick the window object.

    $(...).load(..., function() {
        ...
        menu_ready = true;
    
        // create new event
        var event = new Event('menu_ready');
    
        // Dispatch the event.
        window.dispatchEvent(event);        
     }
    

    Note, you can use any DOM object as the source of the event (whatever makes the most sense for your application) as long as it exists at both the time someone wants to register for the event and the time at which the event occurs.

    Then, a listener anywhere in your code can listen for this event:

     window.addEventListener("menu_ready", function() {
         console.log("menu is now ready");
     });
    

    Working Demo

    Here's an actual working implementation that triggers the event upon a button press.

    let button = document.getElementById("pressme");
    
    button.addEventListener("click", function() {
        // create new event
        var event = new Event('menu_ready');
    
        // Dispatch the event.
        window.dispatchEvent(event);        
    
    });
    
    function log(x) {
        var div = document.createElement("div");
        div.innerHTML = x;
        document.getElementById("log").appendChild(div);
    }
    
    
    // then create a listener
    window.addEventListener("menu_ready", function() {
        log("Got menu_ready event");
    });
    #log {margin-top: 50px;}
    
    


    I crafted this answer to match the original problem illustrated in the question here. For reference, there are several other useful mechanisms of seeing changes, but they generally rely on properties of an object, not just a simple variable.

    See all the answers on this question: Listening for variable changes. But specifically make sure you read these two:

    Using a proxy object to track changes

    Using getters and setters to track changes

提交回复
热议问题