jQuery event delegation

So it turns out that I may have blogged a moment too soon over the weekend….

While the following code works

	$('.modal').on('shown.bs.modal', function () {
		$('FORM')
			.append($('.modal-backdrop, .modal-scrollable'));
	})

It only works the FIRST time – and if you had tested your code properly Mark you would have found this out to be the case. Too eager to blog weren’t we Marky……*pouts*

So anyway like all mistakes a good excuse for more learning – and in this case it wasn’t so much learning it was more muscle memory and more (oh duh Marky – which happens a lot)

The problem
What is happening is that the original code above is only binding to the modal once – and once the modal is being shown on the page and then hidden again apparently that event binding is being lost. I have no proof of this but I suspect that the DOM objects are being destroyed and recreated which is what is causing the loss 😦

The solution
Event delegation – oh it is a wonderful thing once you get your head around it and extremely powerful – go read up about it here and check out the last example specifically

What I was doing is binding to the exact element and once that element is gone – no more binding.

What is Event Delegation?
Event delegation is basically the same thing as event binding, but it works on any matching element whether it exists yet or not.
Que?
What I mean to say is that this piece of code REALLY WORKS and I will explain

$('body').on('shown.bs.modal', '.modal', function () {
    $('FORM')
        .append($('.modal-backdrop, .modal-scrollable'));
})

In this example we are:

  • Selecting the Body
  • And then in the shown.bs.modal event of anything matching the .modal selector
  • do stuff as before.

So if you imagine a simple analogy of feeding a dog.

If you have a child – let’s say your son and you tell him that on the “breakfast event” put food in that exact blue dog bowl – he will do that

Being the obedient child that he is he will fill that bowl every day when it appears.

But being the obstinate child he is, when you replace *that* blue bowl with a new one he will not fill it because you told him to fill the old one

A fight ensues and he loses minecraft privileges!

You then change your instructions:  On the “breakfast event” put food in any dog bowl which appears in the Kitchen. So even if you replace it every day he will have to still do as he is told and fill the bowl.

That is what Event Delegation is – telling the DOM to do things to anything which exists now and anything which appears in the future.

The way it works is because of the second selector – you are telling the DOM body to look for anything with a shown.bs.modal and bind to it. So even though my original dialog apparently lost the binding, in the new case it is automatically re-applied because of the delegated event on the Body

If only I had remembered that before blogging earlier…….

Ah well – we all learned something new

I wonder what I missed today………..

Advertisements

4 thoughts on “jQuery event delegation

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s