The forums ran from 2008-2020 and are now closed and viewable here as an archive.

Home Forums JavaScript jQuery -> Native: Select all tags + addEventHandler, can I do more better?

  • This topic is empty.
Viewing 15 posts - 1 through 15 (of 15 total)
  • Author
  • #161867

    So the goal was to remove jQuery dependency from a very small function to pass clicks through to Google Analytics in a more robust nature. This had been working with jQuery without issues, I just hated adding the library in for one function.

    Basically I wanted to change this into native:

    $('a').on('click', function() {

    I have a working example here:

    I’m one of those guys learning native via jQuery, so I’m still adding all the bells and whistles to my bat-belt. Does anyone have suggestions or articles I can read? I’ve been having difficulty finding examples for this type of thing specifically.


    Your example works, what sort of advice are you looking for? Some things to keep in mind:

    addEventListener vs attachEvent (the latter used for IE5-8 compatibility)

    In your sendClick function you’ve named the event parameter ‘a’ which might be confusing; typically ‘e’, ‘evt’, or ‘event’ is used.

    Abstracting your javascript so it is more generalized and less tightly coupled with the specifics of this use case. Seems trivial for this simple example but the more complex a project becomes, the more value there is in keeping things DRY.

    Some nice-ification:

    Instead of

    function sendClick(a) {
      var el =, label = el.getAttribute('href');

    Why not just do…

    function sendClick(event) {

    Also I’ve not seen anyone write a for loop that way but it’s kind of cool!



    Really, I was wondering if this was the best way to do what I wanted (it seems wasteful somehow):

    var a = document.getElementsByTagName('a');
    for (var i=a.length; i--;) {
      a[i].addEventListener('click', sendClick);

    I like your feedback, I’ll definitely update my code to be happier.


    I don’t see anything wrong with that at all. Just keep in mind that addEventListener isn’t truly cross-browser compatible.


    Thanks, I’m lucky enough to not have to worry about <IE8… unless I’m not reading that correctly.

    That, and this is just icing on top to get more data out of a user’s visit.


    One other question if anyone has insight.

    I’ve been reading up on event order (capturing, bubbling) and I’m not 100% sure I get it.

    When an <a> tag has a child element, say an image, my code is returning undefined trying to find href because it wants to push back the <img> as the click event first.

    To get around this, I’ve hacked this:

    var el =;
    if (el.nodeName == 'IMG') {
      el = el.parentNode;

    Of course, this will only work if an <img> tag is the child.

    I tried setting both true and false to the event handler on addEventListener and also stopped the propagation, but it seemed like no matter what I did it would return the children first.

    My desired behavior would be to only return the click event on the <a> ignoring all children elements.

    What am I missing / doing wrong?


    Can you post a PEN with a reduced case?
    (click a link to alert the href)

    Not able to reproduce what you’re saying.


    After viewing yours, I’m clearly doing something wrong, but here’s a pen:

    I’m not sending the href directly, because I need the for information to build a label in case the href fails some parameters.

    Edit – I’ve done some tweaking and now can get the href, but now I get it all the time. I still need access to the target information to be able to get things like the ID, innerText, etc.


    This should help you out. Instead of using “event” just use the “this” reference which refers to the function context (the object that invoked the function) which in our case is the Anchor element that fired the ‘click’ event.

    OPTIONAL: I just built up a little data object and filled it with the properties you want. Then you could access those properties individually using, data.href, or together by referencing the object itself : ‘data’ (remember this will be typeof === object, so treat it as such!)


    Thanks a lot for your guidance, here’s (nearly) the full program:


    Prepare to have your mind blown:

    Everything you wrote to determine the correct label can be summarized in a one-liner!

    As you can see in my example, the label is getting set properly on each of the links.

    Here’s the one-liner:

    function getLabel(context) {
      return isInArray( skipHREF, context.href.toLowerCase() ) ? || context.title || context.innerText : context.href.toLowerCase()

    It’s very similar to what you wrote in so far as we’re passing in the context (“this” from the click handler function) but in this case we’re using a ternary operator which I know you’re familiar with because you used it in your code. However we’re also taking advantage of “lazy evaluation” to return the correct value by chaining a bunch of OR ( || ) operators together.

    From the link:

    “What’s happening here isn’t quite magic—the expression is simply being lazily evaluated. The interpreter checks the value of the first part of the statement, null, establishes that it’s falsy and continues moving forward until a falsy value isn’t found (or if no truthy value is found, returning the last value)”


    return isInArray( skipHREF, context.href.toLowerCase() ) ? || context.title || context.innerText : context.href.toLowerCase() 

    What this is really saying is:

    First check if the context.href is one we should skip.
    If it isn't, then we use context.href.toLowerCase() [ this is the final bit of the line... after the colon ]
    If it's one we should skip, then we'll use
    If is falsey (undefined, '', null) then we'll use context.title
    If context.title is falsey then we'll use context.innerText

    This is such a nice trick and I learned it somewhat recently so I’m glad to be able to pass it along.

    Cheers~ good luck picking up the pieces of your brain off the floor… ewww.


    Beautiful… my bat-belt just got an anti-Joker spray.

    I always thought those lazy or operators were pseudo code.

    You get the Official Medal of Shane. Wear it proudly son.


    Thanks! Happy to help. I’ve been updating my PEN over the last 10 minutes so be sure to take another look.


    Haha, thanks Shane. It was a nice break from what I should be doing today. :)

Viewing 15 posts - 1 through 15 (of 15 total)
  • The forum ‘JavaScript’ is closed to new topics and replies.