2009-09-30 22 views
49

Sono ancora nuovo di JQuery, sulla strada per ottenere il mio esempio ajax per funzionare sono stato bloccato con setTimeout. L'ho suddiviso fino a dove dovrebbe aggiungere "." al div ogni secondo.JQuery, setTimeout non funziona

Il codice pertinente si trova in due file.

index.html

<html><head> 
<script type='text/javascript' src='jquery.js'></script> 
<script type='text/javascript' src='myCode.js'></script> 
</head> 
<body> 
<div id='board'>Text</div> 
</body> 
</html> 

e myCode.js

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

    function update() { 
     $("#board").append("."); 
     setTimeout('update()', 1000);  } 
})(); 

il file myCode.js funziona bene e "update()" viene eseguito la prima volta attraverso, ma mai più .

risposta

110

Hai un paio di problemi qui.

In primo luogo, si sta definendo il codice all'interno di uno anonymous function. Questo costrutto:

(function() { 
    ... 
)(); 

fa due cose. Definisce una funzione anonima e la chiama. Ci sono motivi di ambito per farlo, ma non sono sicuro che sia ciò che realmente desideri.

Stai passando un blocco di codice a setTimeout(). Il problema è che update() non è all'interno dell'ambito quando viene eseguito in questo modo. E se si passa in un puntatore a funzione, invece così questo funziona:

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

    function update() { 
    $("#board").append("."); 
    setTimeout(update, 1000);  } 
    } 
)(); 

perché il puntatore a funzione update è a portata di tale blocco.

Ma come ho detto, non è necessario per la funzione anonima in modo da poter riscrivere in questo modo:

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

function update() { 
    $("#board").append("."); 
    setTimeout(update, 1000);  } 
} 

o

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

function update() { 
    $("#board").append("."); 
    setTimeout('update()', 1000);  } 
} 

ed entrambi questi lavori. Il secondo funziona perché lo update() all'interno del blocco di codice rientra ora nell'ambito.

Anch'io preferisco la forma $(function() { ... } blocco accorciato e invece di chiamare setTimeout() entro update() si può semplicemente utilizzare setInterval() invece:

$(function() { 
    setInterval(update, 1000); 
}); 

function update() { 
    $("#board").append("."); 
} 

speranza che cancella che fino.

+0

Grazie, ha funzionato. Qualcuno può spiegare perché non funziona così com'era? ogni esempio che ho guardato è più simile alla formattazione che ho usato. –

+0

w3schools è davvero la migliore risorsa per fare riferimento a questo? avrebbe fatto lo stesso errore se avesse usato quella pagina come esempio. –

+3

w3schools è corretto in questo caso. Il problema era un problema di ambito. – cletus

19
setInterval(function() { 
    $('#board').append('.'); 
}, 1000); 

È possibile utilizzare clearInterval se si desidera arrestarlo in un punto.

+1

Non ho usato setInverval prima, ma sembra essere una via più diretta per realizzare il mio obiettivo. Grazie –

+0

cleto sembrava averlo aggiunto alla sua soluzione; la cosa importante da imparare è che devi alimentare una funzione reale per impostareIntervallo/setTimeout, non una stringa che verrà valutata ad es. 'update()' –

+2

Il passaggio di un blocco di codice come 'update()' è valido ma non preferito. – cletus

8

SetTimeout viene utilizzato per rendere il set di codice da eseguire dopo un periodo di tempo specificato, quindi per i propri requisiti è preferibile utilizzare setInterval perché chiamerà la funzione ogni volta a un intervallo di tempo specificato.

+3

Non sarei d'accordo, setTimout è una procedura migliore, nel caso in cui la funzione update() abbia impiegato più di 1 secondo per eseguire si potrebbero avere più istanze della stessa funzione in esecuzione allo stesso tempo. se si utilizza setTimeout, la funzione update() deve terminare completamente prima che si verifichi il ciclo successivo, quindi solo 1 istanza verrà eseguita in una sola volta. – kamui

0

Questo compie la stessa cosa, ma è molto più semplice:

$(document).ready(function() { 
    $("#board").delay(1000).append("."); 
}); 

È possibile concatenare un ritardo prima quasi qualsiasi metodo jQuery.