0

Hi,

I need javascript to click an html element but it doesnt appear in the dom right away so I have this code:

document.addEventListener("DOMContentLoaded", function(event) {
  // Select the node that will be observed for mutations
  var parentOfMyList = document.body;

  // Options for the observer (which mutations to observe)
  var config = {
    attributes: true,
    childList: true,
    subtree: true
  };

  // Callback function to execute when mutations are observed
  var callback = function(mutationsList) {
    for (var mutation of mutationsList) {
      if (mutation.type == 'childList') {
        var elt = document.getElementById("topcmm-123flashchat-main-toolbar-message-type-option");
        if (elt) {
            setTimeout(document.getElementById("topcmm-123flashchat-main-toolbar-message-type-option").click, 6000);

          observer.disconnect();
        }
      }
    }
  };

  // Create an observer instance linked to the callback function
  var observer = new MutationObserver(callback);
  observer.observe(parentOfMyList, config);
});

but I get an error that says 'click' called on an object that does not implement interface HTMLElement. Why is that? The element is supposed to be THERE by the time click() is executed (I am even giving it a 6 second head start to catch up).

Thank you.

Cain Nuke
  • 1,865
  • 4
  • 29
  • 52

1 Answers1

1

This has nothing to do with the mutation observer. The element is there, but you're not calling the click() method on it. Since you didn't bind the method to the element, it's being called on window.

Either pass an anonymous function that calls it on the element:

setTimeout(function() {
    elt.click();
}, 6000);

Or you can bind the method to the element:

setTimeout(elt.click.bind(elt), 6000);
Barmar
  • 596,455
  • 48
  • 393
  • 495
  • Thank heavens you were there. You are always my savior! Thanks once again!! – Cain Nuke May 31 '18 at 23:51
  • Just for shits and giggles. Lets say I dont use a variable but `document.getElementById` instead. What is the syntaxis for that? – Cain Nuke May 31 '18 at 23:52
  • `document.getElementById("topcmm-123flashchat-main-toolbar-message-type-option").click.bind(document.getElementById("topcmm-123flashchat-main-toolbar-message-type-option"))` – Barmar May 31 '18 at 23:56
  • It's the exact same syntax, just replace `elt` with the expression that you assigned to `elt`. – Barmar May 31 '18 at 23:56
  • I've told you before, and I still believe it, that you're probably making things far more complicated than they need to be by using mutation observers. – Barmar May 31 '18 at 23:58
  • Probably, but I really cant figure out anything else. The elements dont appear right away or sometimes they wont appear at all unless the user clicks something. That is making things harder. – Cain Nuke Jun 01 '18 at 00:00
  • I've given you references to the preferred way to bind events to dynamically-created elements. https://stackoverflow.com/questions/203198/event-binding-on-dynamically-created-elements – Barmar Jun 01 '18 at 00:01
  • Not necessarily, it was a relatively minor edit. Different answers are appropriate for different situations, e.g. whether you're using jQuery or not. – Barmar Jun 01 '18 at 00:06
  • Okay, I will read thought it. Basically it is the same thing you did here by using `bind` along with `click`, right? – Cain Nuke Jun 01 '18 at 00:08
  • No, it's completely unrelated. Delegation works by binding a handler to a container that already exists. When the user clicks on the element, the event bubbles up to the container, and it can then use `event.target` to detect which descendant you actually clicked on. – Barmar Jun 01 '18 at 00:10
  • I see. I will give it a try. Thanks for the suggestion. – Cain Nuke Jun 01 '18 at 00:12
  • Hi again, I have been reading the thread you showed me and I still dont quite get it. Basically this is what I should be using? `$(document).on('click', 'elt', function(){ // what you want to happen when mouseover and mouseout // occurs on elements that match '.dosomething' });` – Cain Nuke Jul 23 '18 at 02:23
  • @CainNuke `$(document).on('click', '#topcmm-123flashchat-main-toolbar-message-type-option', function () { ... })` The second argument is the selector for the dynamically-added element. – Barmar Jul 23 '18 at 02:32
  • okay, but `#topcmm-123flashchat-main-toolbar-message-type-option` will only appear in the DOM 3 seconds after the page has loaded. No needed to use something to delay it or so? – Cain Nuke Jul 23 '18 at 02:40
  • No. The whole point of delegation is that you can create the event listener *before* the element appears. – Barmar Jul 23 '18 at 02:45
  • That's the difference between binding the handler directly to the element and delegating it from a container. – Barmar Jul 23 '18 at 02:46
  • So the code will automatically detect when the element appears and click on it right after it appears? – Cain Nuke Jul 23 '18 at 02:49
  • It won't click on it, it will bind an event listener function that runs when the user clicks on it. – Barmar Jul 23 '18 at 02:52
  • I guess I lost track of what you're actually trying to do when the element appears. – Barmar Jul 23 '18 at 02:53
  • Its easy to lose track. I need `#topcmm-123flashchat-sound-messages-contents` to be in the DOM in order to execute my functions. Without that element present I can do nothing. The problem is that it wont be present unless the user clicks on `#topcmm-123flashchat-toolbar-style-send-sound-btn` which wont be present either unless the user clicks on `topcmm-123flashchat-main-toolbar-message-type-option` which will appear 3 seconds after the page has loaded. Since the user may not do the clicks I need to automate them so the needed elements appear whether the user clicks them or not. – Cain Nuke Jul 23 '18 at 03:07
  • None of this delegation stuff is related, it's only for event handling, not event triggering. Your mutation observer method should work. – Barmar Jul 23 '18 at 03:14
  • Not quite. Please take a look at my other thread https://stackoverflow.com/questions/51468755/settimeout-keeps-executing-the-same-function-many-times – Cain Nuke Jul 23 '18 at 03:17
  • Not sure why you say "not quite". That other question has nothing to do with event handling, either, it's about event triggering. I'm trying to say that everything I said about event delegation is not relevant. – Barmar Jul 23 '18 at 03:32