54

sparkline

Thursday, October 12th, 2023

event.target.closest

Eric mentioned the JavaScript closest method. I use it all the time.

When I wrote the book DOM Scripting back in 2005, I’d estimate that 90% of the JavaScript I was writing boiled down to:

  1. Find these particular elements in the DOM and
  2. When the user clicks on one of them, do something.

It wasn’t just me either. I reckon that was 90% of most JavaScript on the web: progressive disclosure widgets, accordions, carousels, and so on.

That’s one of the reasons why jQuery became so popular. That first step (“find these particular elements in the DOM”) used to be a finicky affair involving getElementsByTagName, getElementById, and other long-winded DOM methods. jQuery came along and allowed us to use CSS selectors.

These days, we don’t need jQuery for that because we’ve got querySelector and querySelectorAll (and we can thank jQuery for their existence).

Let’s say you want to add some behaviour to every button element with a class of special. Or maybe you use a data- attribute instead of the class attribute; the same principle applies. You want something special to happen when the user clicks on one of those buttons.

  1. Use querySelectorAll('button.special') to get a list of all the right elements,
  2. Loop through the list, and
  3. Attach addEventListener('click') to each element.

That’s fine for a while. But if you’ve got a lot of special buttons, you’ve now got a lot of event listeners. You might be asking the browser to do a lot of work.

There’s another complication. The code you’ve written runs once, when the page loads. Suppose the contents of the page have changed in the meantime. Maybe elements are swapped in and out using Ajax. If a new special button shows up on the page, it won’t have an event handler attached to it.

You can switch things around. Instead of adding lots of event handlers to lots of elements, you can add one event handler to the root element. Then figure out whether the element that just got clicked is special or not.

That’s where closest comes in. It makes this kind of event handling pretty straightforward.

To start with, attach the event listener to the document:

document.addEventListener('click', doSomethingSpecial, false);

That function doSomethingSpecial will be executed whenever the user clicks on anything. Meanwhile, if the contents of the document are updated via Ajax, no problem!

Use the closest method in combination with the target property of the event to figure out whether that click was something you’re interested in:

function doSomethingSpecial(event) {
  if (event.target.closest('button.special')) {
    // do something
  }
}

There you go. Like querySelectorAll, the closest method takes a CSS selector—thanks again, jQuery!

Oh, and if you want to reduce the nesting inside that function, you can reverse the logic and return early like this:

function doSomethingSpecial(event) {
  if (!event.target.closest('button.special')) return;
  // do something
}

There’s a similar method to closest called matches. But that will only work if the user clicks directly on the element you’re interested in. If the element is nested within other elements, matches might not work, but closest will.

Like Eric said:

Very nice.

Monday, July 1st, 2019

8 DOM features you didn’t know existed - LogRocket Blog

If you ignore the slightly insulting and condescending clickbaity title, this is a handy run-down of eight browser features with good support:

  1. extra arguments in addEventListener(),
  2. scrollTo(),
  3. extra arguments in setTimeout() and setInterval(),
  4. the defaultChecked property for checkboxes,
  5. normalize() and wholeText for strings of text,
  6. insertAdjacentElement() and insertAdjacentText(),
  7. event.detail, and
  8. scrollHeight and scrollWidth.

Thursday, February 21st, 2019

A tiny lesson in query selection

We have a saying at Clearleft:

Everything is a tiny lesson.

I bet you learn something new every day, even if it’s something small. These small tips and techniques can easily get lost. They seem almost not worth sharing. But it’s the small stuff that takes the least effort to share, and often provides the most reward for someone else out there. Take for example, this great tip for getting assets out of Sketch that Cassie shared with me.

Cassie was working on a piece of JavaScript yesterday when we spotted a tiny lesson that tripped up both of us. The script was a fairly straightforward piece of DOM scripting. As a general rule, we do a sort of feature detection near the start of the script. Let’s say you’re using querySelector to get a reference to an element in the DOM:

var someElement = document.querySelector('.someClass');

Before going any further, check to make sure that the reference isn’t falsey (in other words, make sure that DOM node actually exists):

if (!someElement) return;

That will exit the script if there’s no element with a class of someClass on the page.

The situation that tripped us up was like this:

var myLinks = document.querySelectorAll('a.someClass');

if (!myLinks) return;

That should exit the script if there are no A elements with a class of someClass, right?

As it turns out, querySelectorAll is subtly different to querySelector. If you give querySelector a reference to non-existent element, it will return a value of null (I think). But querySelectorAll always returns an array (well, technically it’s a NodeList but same difference mostly). So if the selector you pass to querySelectorAll doesn’t match anything, it still returns an array, but the array is empty. That means instead of just testing for its existence, you need to test that it’s not empty by checking its length property:

if (!myLinks.length) return;

That’s a tiny lesson.

Sunday, September 9th, 2018

Removing jQuery from GitHub.com frontend | GitHub Engineering

You really don’t need jQuery any more …and that’s thanks to jQuery.

Here, the Github team talk through their process of swapping out jQuery for vanilla JavaScript, as well as their forays into web components (or at least the custom elements bit).

Friday, November 25th, 2016

Hey designers, if you only know one thing about JavaScript, this is what I would recommend | CSS-Tricks

This is a really great short explanation by Chris. I think it shows that the really power of JavaScript in the browser isn’t so much the language itself, but the DOM—the glue that ties the JavaScript to the HTML.

It reminds me of the old jQuery philosophy: find something and do stuff to it.

Thursday, September 20th, 2012

DOM Enlightenment

This looks great! It’s a CC-licensed book by Cody Lindley (whose work I’ve admired for many years) aimed at teaching DOM Scripting for modern browsers. You can read the whole thing online or wait for the paper version from O’Reilly.

If all your JavaScript currently consists of writing jQuery plugins, I highly recommend you read this.

Monday, January 3rd, 2011

DOM Scripting, second edition

You may have noticed that there’s a second edition of DOM Scripting out. I can’t take any credit for it; I had very little to do with it. But I’m happy to report that the additions meet with my approval.

I’ve written about it on the DOM Scripting blog if you want all the details on what’s new. In short, all the updates are good ones for a book that’s now five years old.

If you’ve already got the first edition, you probably don’t need this update, but if you’re looking for a good introduction to JavaScript with a good smattering of Ajax and HTML5, and an additional dollop of jQuery, the second edition of DOM Scripting will serve you well.

The cover of the second edition, alas, is considerably shittier than the first edition. So don’t judge the second edition of a book by its cover.

Friday, December 10th, 2010

You Must Learn JavaScript — Article — The Nerdary

Kenny Meyers on the ubiquity of JavaScript.

Wednesday, July 8th, 2009

BBC - Glow JavaScript Library

The BBC have released their JavaScript library. This one is worth paying attention to for its wide browser support base.

Tuesday, May 19th, 2009

Monday, January 21st, 2008

Easy as Pie Ajax Requests - Create compelling ajax in minutes with simple examples. | Notes from Phazm

This is a good straightforward hands-on explanation of Ajax: succinct and clear.

Monday, September 17th, 2007

jQuery UI: Widgets, Components, and Interactions

From the people who brought you jQuery comes a set of widgets built using jQuery complete with documentation and tutorials.

Friday, August 24th, 2007

UT| Event delegation without a JavaScript library

A nice succinct explanation of how to roll your own JavaScript event delegation from Andy Hume.

Tuesday, July 24th, 2007

dpaste: #15223: LOLDOM, by Jeremy Keith

Okay, this started as a joke but then I couldn't resist writing a bit of code. Usage: OH_HAI.I_CAN_HAS_ELEMENT_BY_ID("Id") and OH_HAI.I_CAN_HAS_ELEMENTS_BY_TAG_NAME("tag").

Monday, July 16th, 2007

Channy’s Blog - » 『DOM 스크립트』 출간 이벤트!

DOM Scripting... now also available in Korean.

Wednesday, July 4th, 2007

Viget Labs Is Hiring - Join Our Design Team

What excellent taste this web design shop has. I don't mean the fancy scrolling—I'm talking about what's on the bookshelf.

Sunday, March 4th, 2007

MiniAjax.com / A showroom of nice looking simple downloadable DHTML and AJAX scripts

A collection of scripts. There might be some good stuff here but use with care and discretion.

Monday, December 11th, 2006

Dear JavaScript Library Developers… - Wait till I come!

Christian's wish list for JavaScript libraries.

Thursday, December 7th, 2006

rikrikrik: Wasted Javascript

How much page weight is being wasted on JavaScript. It's time to shed those pounds.

Friday, September 22nd, 2006

danwebb.net - RailsConf Presentation Slides and Example Code

A PDF of Dan's slides from RailsConf. Looks like it was an excellent presentation.