2012-02-06 13 views
9

cssCome passare 'questo' in un callback setTimeout

.item { 
    display: none; 
} 

html

<div> 
    <div class="item">machin</div> 
    <div class="item">chose</div> 
    <div class="item">chouette</div> 
    <div class="item">prout</div> 
</div> 

sto usando jQuery e mi piacerebbe rendere ogni .item compaiono dopo un piccolo timer casuale come:

javascript

$('.item').each(function() { 
    itm = $(this); 
    setTimeout(function() { 
    itm.fadeIn(1000); 
    }, Math.floor(Math.random() * 1000)); 
}) 

Qui itm conterrà sempre l'ultima voce, perché la funzione è valutata dopo tutte le assegnazioni.
Non riesco a utilizzare il 3 ° parametro di setTimeout() perché non funzionerà su IE.
Non è consigliabile utilizzare setTimeout() con il metodo eval per motivi di sicurezza.

Quindi, come posso accedere al mio oggetto tramite setTimeout()?


Modifica

so che questa domanda è già stato pubblicato.
Ma ho pensato che fosse leggermente specifico con il contesto each().
Ora qualcuno hanno completamente cambiato il titolo della mia domanda, che in origine era qualcosa come 'setTimeout() - jQuery.each() questo parametro oggetto'

+0

'this' all'interno di' setTimeout() 'fa riferimento all'oggetto globale. Il tuo codice sopra non dovrebbe nemmeno funzionare per l'ultimo elemento. –

+0

Scusa, stavo effettivamente facendo 'itm = $ (this)' nel mio codice invece di 'var itm = $ (this)', ho aggiornato la mia domanda. Quindi ora non so quale risposta accettare :) –

+3

@PierredeLESPINAY Aha. La differenza tra 'var itm' e' itm' è che senza 'var' è una singola variabile globale, invece di una variabile locale per ogni chiamata della funzione di inclusione. Ecco perché setTimeout ha visto solo l'ultimo elemento nell'elenco. – Izkata

risposta

2

è necessario memorizzare this in una variabile indipendente:

$('.item').each(function() { 
    var me = $(this); 
    setTimeout(function() { 
    me.fadeIn(1000); 
    }, Math.floor(Math.random() * 1000)); 
}) 
2

Il trucco è quello di salvare this in un locale che può essere valutata in modo sicuro nel setTimeout callback

$('.item').each(function() { 
    var self = this; 
    setTimeout(function() { 
    $(self).fadeIn(1000); 
    }, Math.floor(Math.random() * 1000)); 
}); 
2

Prova questo:

$('.item').each(function() { 
var myVar = $(this); 
setTimeout(function() { 
myVar.fadeIn(1000); 
}, Math.floor(Math.random() * 1000)); 
}) 
2

Prova questo insteed:

$('.item').each(function() { 
     var elm = this; 
     setTimeout(function() { 
     $(elm).fadeIn(1000); 
     }, Math.floor(Math.random() * 1000)); 
    }) 

Non riesco a spiegare perché funzioni, ma penso che questo sia un riferimento ad un altro "questo" nel tuo setTimeout.

http://jsfiddle.net/Pdrfz/

2

Prova questo:

$('.item').each(function() { 
    var item =$(this); 
    setTimeout(function() { 
      item.fadeIn(1000); 
     }, 
     Math.floor(Math.random() * 1000)); 
    }); 
3

Prima setTimeout esegue each ciclo avrebbe terminato l'esecuzione, non aspetterà. Anche all'interno della funzione setTimeout, this non si riferirà all'elemento DOM.

Prova qualcosa del genere.

function fadeItem(item){ 
    item.fadeIn(1000); 
} 

$('.item').each(function() { 
    var $item = $(this); 
    setTimeout(function() { 
    fadeItem($item); 
    }, Math.floor(Math.random() * 1000)); 
}); 

Si può anche provare qualcosa di simile.

var $items = $('.item'), count = 0; 

function fadeItem(item){ 
    item.fadeIn(1000); 
    if(count < $items.length){ 
     setTimeout(function(){ 
      fadeItem($items.eq(count++)); 
     }, Math.floor(Math.random() * 1000)); 
    } 
} 
setTimeout(function(){ 
    fadeItem($items.eq(count++)); 
}, Math.floor(Math.random() * 1000)); 
Problemi correlati