Over Event-bubbling
Als je "iets" doet op een webpagina, dat ontstaan er in de browser allerlei 'gebeurtenissen'. Scrollen, de muis klikken, de muis bewegen, de pagina is geladen, enz., zijn gebeurtenissen in de browser. De gebruikelijke term voor een gebeurtenis is event. Het optreden van een event kun je detecteren en er op laten reageren met bijv. JavaScript. Zo'n script (of beter: de JavaScript function) heet event handler. Dat is dus de code die wordt uitgevoerd als een gebeurtenis optreedt.
Een overzicht van de bestaande event handlers vind je HIER.
Soms hoor je de term "Event-bubbling", vooral in relatie tot JavaScript-platforms zoals jQuery of Modernizr.
Daar komt het voor dat events moeten worden omgeleid, zodat de 'gewone' programmeurs (lees: wij) er zeker van kunnen zijn dat
events worden behandeld zoals wij dat willen.
Als 'gewone' programmeur zul je dus weinig meemaken dat je op deze manier moet ingrijpen in het afhandelen van events.
Op deze pagina wordt beschreven wat event-bubbling is.
Het woord bubbling betekent (omhoog-)borrelen, net zoals de belletjes in een glas bier. Bij event-bubbling 'borrelen' de events omhoog in de DOM-structuur, totdat er een actie kan/moet plaatsvinden.
Een en ander wordt uitgelegd aan de hand van een click-event, dus als er ergens met de muis op wordt geklikt.
Hieronder staat wat HTML-code. Drie van de tags in de structuur hebben een onclick-attribuut:
<html>
<head>
.
.
</head>
<body>
<h1>Kop1</h1>
<div onclick="DoeIets()">
<p>Tekst 1</p>
<p>Tekst 2<br>
<img src="plaatje.jpg" onclick="PlaatjeGeklikt()">
</p>
</div>
<h1>Kop2</h1>
<p onclick="DoeIetsAnders()">Tekst 3</p>
<p>Tekst 4</p>
</body>
</html>
Op het scherm zie je iets wat lijkt op:
Kop1
Tekst 1
Tekst 2
Kop2
Tekst 3
Tekst 4
- Als je op Kop1 klikt, gebeurt er niets. Het click-event gaat nu naar boven (borrelt omhoog) en komt in de <body>-tag terecht. Daar is ook geen event-handler voor click gedefinieerd, dus het event borrelt verder omhoog en komt bij <html> terecht. Binnen de <html>-tag is onclick niet mogelijk, dus het event borrelt verder omhoog en verdwijnt uit het HTML-document.
- Als je op de paragraaf Tekst 1 klikt, gebeurt er niets voor de betreffende paragraaf. Het click-event borrelt omhoog en komt in de <div>-tag terecht. Daar staat een handler voor click: De JavaScript-function DoeIets() wordt aangeroepen.
- Als je op de tekst in de paragraaf Tekst 2 klikt, gebeurt er niets voor de betreffende paragraaf. Het click-event borrelt omhoog en komt in de <div>-tag terecht. Daar staat een handler voor click: De JavaScript-function DoeIets() wordt aangeroepen.
- Als je echter op het 'Plaatje' klikt, wordt direct de function PlaatjeGeklikt() aangeroepen. De function DoeIets() wordt niet meer aangeroepen, want het event is afgehandeld na de aanroep van PlaatjeGeklikt().
- Als je op Kop2 klikt, gebeurt er niets. Het click-event volgt dezelfde weg als bij Kop1.
- Als je op Tekst 3 klikt, wordt DoeIetsAnders() aangeroepen, waarna het event is afgehandeld.
- Als je op Tekst 4 klikt, gebeurt er hetzelfde als bij Kop1 en Kop2.
Opmerking: Sommige HTML-elementen hebben een ingebouwde event-handler, bijvoorbeeld <a>.
Als je op een <a>-tag klikt wordt de pagina geopend die in het href-attribuut staat. Daar hoef je verder
zelf niets aan te programmeren.
Iets dergelijks vind je bij een submit-knop in een formulier. Het is echter mogelijk om zo'n standaard event handler
te overrulen. Dat doe je door een onclick-attribuut op te nemen in de betreffende tag.
Bubbling beïnvloeden:
Niet alle events bubbelen. Voorbeelden van events die niet bubbelen zijn onder andere:
• mouseover, mouseout, unload, focus, blur, change, reset en scroll.
Je kunt onderzoeken of een event bubbelt of niet. Dat doe je door een event handler te schrijven en die op te nemen bij het
event dat je wilt onderzoeken:
(zet dit in de <HEAD>)
<script type="text/javascript>
function mijnFunction(e) {
window.alert(e.bubbles);
}
</script>
In de <BODY> zet je dan bijvoorbeeld:
<p onfocus="mijnFunction(event)">Bla bla bla etc.</p>
De alert geef terug: false
.
Als je onfocus zou vervangen door onclick, geeft mijnFunction true
terug.
Je kunt standaard events tegenhouden. Dat doe je door voor dat standaard event een handler te schrijven.
Voorbeeld: Als je op een <a>-tag klikt, word je naar een andere pagina gebracht. Dat kun je uitschakelen met
de function:
function doeNiets(e) {
e.preventDefault()
}
Als de code van de <a>-tag luidt:
<a href="https://www.google.com" onclick="doeNiets(event)">Google</a>
zie je een prachtige hyperlink, maar als je er op klikt gebeurt er niets!
Je kunt ook 'gewone' events tegenhouden. Dat doe je met de function:
function doeOokNiets(e) {
e.stopPropagation()
}
Met event.stopPropagation() voorkom je dat een event omhoog kan bubbelen in de documentstructuur.
Opmerking:
De noodzaak om event bubbling te beïnvloeden ontstaat eigenlijk alleen bij heel ingewikkelde scripts, zoals
jQuery en Modernizr.
Een uitzondering is als je een formulier wilt valideren voordat het wordt verstuurd. Om te voorkomen dat een formulier wordt
verstuurd als de ingevulde gegevens incompleet of fout zijn, kun je ook de methode gebruiken van het item
Geldigheid testen van formulier-velden. Dat werkt stukken eenvoudiger.