40
JavascritpCamp 2009 Simone (Demo) Gentili Javascript Camp – 25 Settembre 2009 Listener per eventi

Javascript Camp - Listener Per Eventi

Embed Size (px)

DESCRIPTION

Come funziona il binding degli eventi con il DOM2.

Citation preview

Page 1: Javascript Camp - Listener Per Eventi

JavascritpCamp 2009

Simone (Demo) Gentili

Javascript Camp – 25 Settembre 2009

Listener per eventi

Page 2: Javascript Camp - Listener Per Eventi

DOM Events

DOM Events;DOM Level 2;Gestori di Eventi;Listener per eventi;Azioni predefinite;Propagazione di eventi;

Page 3: Javascript Camp - Listener Per Eventi

DOM Events / (1/2)

I DOM events permettono a linguaggi di programmazione come Javascript, JScript, EcmaScript, Java, VBScript di registrare degli event handler/listener in dei nodi di elementi all'interno do un albero DOM.

Un albero DOM lo possiamo ritrovare all'interno di documenti, per esempio, html, xhtml, xul, svg.

Page 4: Javascript Camp - Listener Per Eventi

DOM Events / (2/2)

L'esecuzione di codice Javascript in risposta ad un evento rimane una delle funzionalità che sono oggetto di implementazioni differenti tra i vari browser.

Per combattere contro queste diversità, il W3C ha provato a standardizzare il modello ad eventi nel DOM Level 2.

Page 5: Javascript Camp - Listener Per Eventi

DOM Level 2

DOM Events;DOM Level 2;Gestori di Eventi;Listener per eventi;Azioni predefinite;Propagazione di eventi;

Page 6: Javascript Camp - Listener Per Eventi

DOM Level 2 / intro / (1/6)

E' interessante notare che anche Microsoft ha partecipato allo sviluppo delle specifiche del DOM Level2;

Al rilascio di Internet Explorer 5.5, Microsoft ha deciso di non supportare le specifiche all'interno del suo Browser.

Lo stesso vale per le release successive ovvero la 6.0 e la 7.0 … 8.0;

Page 7: Javascript Camp - Listener Per Eventi

DOM Level 2 / modello DOM / (2/6)

Quando viene caricato, un documento HTML viene trasformato in una struttura di oggetti javascript chiamata modello DOM;

$(document).ready(); // we love jquery =)

Ogni elemento, compresi gli attributi, diviene un oggetto.

Javascript può accedere a questi oggetti per modificarne la struttura.

Page 8: Javascript Camp - Listener Per Eventi

DOM Level 2 / i nodi / (3/6)

Ciascun elemento viene rappresentato tramite un nodo (tag ...) e ci sono diversi tipi di nodi in base ad alcune semplici caratteristiche;

Il nodo di un elemento si distingue in base al nome (che chiamiamo normalmente tag);

I nomi non devono essere per forza univoci;ES: Due paragrafi (<p>...</p>) saranno identici

fino a che non verranno caratterizzati dall'attributo id.

Page 9: Javascript Camp - Listener Per Eventi

DOM Level 2 / i nodi / (4/6)

document è un nodo sempre presente a prescindere da che cosa contiene il documento stesso. Prende anche il nome di “nodo del documento”;

I nodi degli elementi sono differenti dal nodo del documento e rappresentano gli effettivi elementi, tag, presenti nella pagina;

Il contenuto di un documento si trova nei nodi testuali oppure nei nodi degli attributi.

Page 10: Javascript Camp - Listener Per Eventi

DOM Level 2 – testi – (5/6)Tutto quello che non è compreso tra parentesi

angolari, viene considerato nodo testuale;

I nodi testuali nodo non possono avere figli;

Se si indenta il codice di un documento HTML per renderlo più leggibile all'occhio umano, tra un nodo testuale e l'altro verranno inseriti anche i tab per separare i tag o i testi. I nodi di spaziatura sono gestiti in maniera differente dai vari browser e bisogna fare attenzione quando si conta sul numero o sull'ordine dei nodi presenti nel DOM;

Page 11: Javascript Camp - Listener Per Eventi

DOM Level 2 – attributi – (6/6)

I nodi degli attributi sono sempre associati ad un elemento, è ovvio che non possiamo avere un attributo senza che vi sia un nodo (tag ...);

non fanno parte del DOM ed è per questo motivo che bisogna fare uso di funzioni differenti per operare su di essi, sia in lettura che in scrittura;

Page 12: Javascript Camp - Listener Per Eventi

Gestori di Eventi

DOM Events;DOM Level 2;Gestori di Eventi;Listener per eventi;Azioni predefinite;Propagazione di eventi;

Page 13: Javascript Camp - Listener Per Eventi

Gestori di Eventi - (1/7)Il modo più semplice per gestire gli eventi con del

codice javascript, è quello di usare gli event handler (precedenti al DOM);

Un gestore di eventi, è una funzione javascript contenuta in un nodo del DOM che viene richiamata automaticamente quando si verifica un determianto evento su quel nodo;

Se non attendiamo che il DOM sia stato caricato, non possiamo operare sui suoi nodi. Ecco la soluzione:

$(document).ready(function(){ … });

Page 14: Javascript Camp - Listener Per Eventi

Gestori di Eventi - (2/7)

Quando siamo di fronte ad un codice HTML come mostrato di seguito e facciamo click sul link:

<a href=”http://www.unodeitanti.com”>unodeitanti.com</a>

Come impostazione predefinita, il browser risponde all'evento click richiamando l'indirizzo specificato nell'attributo href, ma prima che ciò avvenga, è possibile predisporre un gestore di eventi che risponda a questo in particolare.

Page 15: Javascript Camp - Listener Per Eventi

Gestori di Eventi - (3/7)

Usare i gestori di eventi è una soluzione pratica e veloce quando si deve programmare. In oltre danno la sicurezza di poter funzionare su tutti i browser;

è possibile assegnare un solo evento ad un singolo gestore di eventi su un determinato elemento HTML;

Significa che non si può associare ad un evento una serie di attività da svolgere (non in modo elegante);

Page 16: Javascript Camp - Listener Per Eventi

Gestori di Eventi - (4/7)

var link = document.getElementById("idlink");

link.onclick = function () { alert("ciao"); }

link.onclick = function () { alert("Io sono ..."); }

Page 17: Javascript Camp - Listener Per Eventi

Gestori di Eventi - (5/7)

Quando usiamo il gestore di eventi per assegnare la seconda alert, in realtà si sovrascrivono quella precedenti;

Domanda: quante volte può capitare che ci siano più script da richiamare al click di un determinato link?

Risposta: forse mai =). Però ci sono molti eventi che possono richiedere l'intervento di più script. Un caso tra i tanti, il submit di un form che dovra controllare tutti i campi;

Page 18: Javascript Camp - Listener Per Eventi

Gestori di Eventi - (6/7)Soluzione generale …

var link = document.getElementById("idlink");link.onclick = function () {

alert("Ciao");alert("Io sono ...");

}

Oppure …

function script1 () { alert("Uno"); }function script2 () { alert("Due"); }

var link = document.getElementById("idlink");link.onclick = function () {

script1();script2();

}

Page 19: Javascript Camp - Listener Per Eventi

Gestori di Eventi - (7/7)

Dentro le funzioni script1 e script2 l'attributo this non farà più riferimento all'elemento che ha generato l'evento;

Se uno dei due eventi restituisce false, non viene bloccata l'azione predefinita dell'elemento;

Page 20: Javascript Camp - Listener Per Eventi

Listener per Eventi

DOM Events;DOM Level 2;Gestori di Eventi;Listener per eventi;Azioni predefinite;Propagazione di eventi;

Page 21: Javascript Camp - Listener Per Eventi

Listener per Eventi - (1/5)Sono come i gestori di eventi, tranne per il fatto

che ad essi si possono assegnre più listenere ad un solo nodo;

Ci consentono l'uso della parola chiave this;Sono una specifica del W3C;

Ma ...

Internet Explorer offre una propria versione completamente differente; (@#&%!$)

Anche Safari usa i listener ma con un meccanismo leggermente diverso;

Page 22: Javascript Camp - Listener Per Eventi

Listener per Eventi - (2/5)

Come i gestori di eventi, i listener sono una funzione javascript che viene connessa ad un nodo del DOM;

Se volessimo fare paragoni, i gestori di eventi sono una porta USB mentre i listener sono come un hub;

Page 23: Javascript Camp - Listener Per Eventi

Listener per Eventi - (3/5)

elemento.addEventListener(“evento”, listenerPerEventi, false);

addEventListener accetta tre argomenti:

evento – l'evento può essere ad esempio click oppure mouseover, senza “on” davanti;

listener – ovvero la funzione listener stessa;

tipo di listener – indica se si tratta di un listener per la cattura di eventi o meno;

Page 24: Javascript Camp - Listener Per Eventi

Listener per Eventi - (4/5)

Per Internet Explorer le cose sono leggermente differenti:

elemento.attachEvent(“onevento”, listenerPerEventi);

AttachEvent anziché addEventListener;

Onevento anziché semplicemente evento;

Non c'è nessun terzo argomento;

Page 25: Javascript Camp - Listener Per Eventi

Listener per Eventi - (5/5)

Come distinguere le due implementazioni

If ( typeof elemento.addEventListener != “undefined” ){

elemento.addEventListener(“evento”, listenerPerEventi, false);}else{

elemento.attachEvent(“onevento”, listenerPerEventi);}

* vedi codice di esempio ...

Page 26: Javascript Camp - Listener Per Eventi

Azioni Predefinite

DOM Events;DOM Level 2;Gestori di Eventi;Listener per eventi;Azioni predefinite;Propagazione di eventi;

Page 27: Javascript Camp - Listener Per Eventi

Azioni predefinite - (1/3)<a href=”...” onclick=”javascript:return false;”>...</a>

Per bloccare l'azione predefinita di un gestore di eventi ed impedirte che il browser la svolga, è sufficente restiture false al gestore dell'evento.

Nel modello per listener, al listenerPerEvento viene passato anche l'oggetto dell'elemento le cui proprietà contengono informazioni riguardanti l'evento generato ed i metodi che consentono di controllare il modo in cui l'evento viene elaborato dal browser.

Page 28: Javascript Camp - Listener Per Eventi

Azioni predefinite - (2/3)Per bloccare l'evento di default basta richiamare

l'evento preventDefault(); sull'elemento:

clickListener: function (event){

if ( confirm (“Sei sicuro di voler aprire il link?”) ){

event.preventDefault();}

}

Basta che un listener richiami questo metodo per evitare che venga eseguita l'operazione di default.

* vedi codice di esempio ...

Page 29: Javascript Camp - Listener Per Eventi

Azioni predefinite - (3/3)In Internet Explorer l'oggetto evento non viene

passato come argomento al listener, ma viene reso disponibile come variabile globale chiamata event;

clickListener: function (event){

if ( confirm (“Sei sicuro di voler aprire il link?”) ){

event.returnValue = false;}

}

La variabile globale ha una proprietà returnValue che si può impostare a false;

Page 30: Javascript Camp - Listener Per Eventi

Propagazione di Eventi

DOM Events;DOM Level 2;Gestori di Eventi;Listener per eventi;Azioni predefinite;Propagazione di eventi;

Page 31: Javascript Camp - Listener Per Eventi

Propagazione di Eventi – (1/5)

Gli eventi, attraversano l'intera struttura del DOM ed il meccanismo si chiama propagazione dell'evento.

Se viene associato un listener ad un link contenuto in un paragrafo, l'evento onclick viene esteso anche al contenitore del link e verrà attivato anche sul paragrafo.

<p><a href=”http://www.example.com”>example.com</a>

</p>

Page 32: Javascript Camp - Listener Per Eventi

Propagazione di Eventi – (2/5)

Nella fase di cattura, l'evento percorre tutto il DOM da document fino all'elemento che ha generato l'evento.

Ogni volta che viene incontrato un elemento, viene controllato se ad esso è associato un listener per la cattura di eventi relativi (ecco a che serve il terzo parametro):

elemento.addEventListener(“evento”, listenerPerEventi, false);

Page 33: Javascript Camp - Listener Per Eventi

Propagazione di Eventi – (3/5)

Il metodo attachEvent di Internet Explorer non prevede il terzo parametro, proprio perchè il modello ad eventi è differente e non prevede i listener per la cattura di eventi;

Molti sviluppatori evitano quindi di sfruttare i listener per la cattura di eventi;

Page 34: Javascript Camp - Listener Per Eventi

Propagazione di Eventi – (4/5)Nella fase di target il browser ha raggiunto il

nodo DOM dell'elemento cui è stato associato il listener;

Al click su un link il target sarà il link stesso mentre ma nel caso di Safari, il target sarà il nodo testuale;

Nella fase di risalita, viene ripercorso tutto il DOM fino a document e vengono eseguiti tutti i listener che non sono listener per la cattura di eventi, ad eccezione degli eventi focus() e blur();

Page 35: Javascript Camp - Listener Per Eventi

Propagazione di Eventi – (5/5)

Per interrompere la propagazione di un evento è sufficente richiamare il metodo stopPropagation;

Nel caso di Internet Explorer dovremo impostare la proprietà cancelBubble a true;

Page 36: Javascript Camp - Listener Per Eventi

I problemi di memoria in IE (1/1)

In internet Explorer, la memoria occupata per un listenere non viene rilasciata nemmeno al cambio della pagina;

I rallentamenti del browser potrebbero costringere l'utente a riavviarlo;

La soluzione consiste nel configurare un listener per l'evento unload dell'oggetto window, ed in questo listener si possono eliminare tutti i listener per eventi definiti per il documento evitando lo spreco di memoria;

Page 37: Javascript Camp - Listener Per Eventi

Riepilogo – (1/2)

Internet Explorer utilizza attachEvent / detachEvent al posto di addEventListener / removeEventListener;

Internet Explorer chiama gli eventi con il prefisso on invece di chiamarli semplicemente evento;

Internet Explorer usa event come variabile globale invece di passarla come parametro al listener;

Page 38: Javascript Camp - Listener Per Eventi

Riepilogo – (2/2)

Per bloccare un evento InternetExplorer richiede di impostare la proprietà cancelBubble mentre invece di richiamare il metodo stopPropagation();

Internet Explorer richiama i listener come funzioni indipendenti e ci costringe, se vogliamo riciclare il codice, ad ottenere un riferimento all'elemento target invece di usare this;

Internet Explorer non si preoccupa di ripulire la memoria automaticamente;

Page 39: Javascript Camp - Listener Per Eventi

I framework javascript

Prototype:

Event.observe(elemento, “evento”, listenerPerEventi);Event.stopObserving(elemento, “evento”, listenerPerEventi);

jQuery:

$(selettore).bind(“evento”, listenerPerEventi);$(selettore).unbind(“evento”, listenerPerEventi);

Oppure ( sempre con jquery ... )

$(selettore).click(listenerPerClick);

Page 40: Javascript Camp - Listener Per Eventi

This is the end: faq?