7

Sto iniziando con un MMORPG javascript che funzionerà senza problemi. Al momento, ho creato una demo per dimostrare che posso spostare i personaggi in giro e farli chattare tra loro, così come vederci spostati in diretta.Informazioni sui problemi del thread timer JavaScript

http://set.rentfox.net/

timer Ora JavaScript sono qualcosa che non ho ampiamente utilizzato, ma da quello che so, mi corregga se sbaglio, è che avere più setIntervals che accadono nello stesso momento in realtà non funziona bene b/c è tutto su un singolo thread.

Diciamo che volevo avere 10 diverse persone che accarezzano palle di fuoco a un mostro usando il posizionamento dello sfondo sprite con setInterval - quell'animazione richiederebbe 10 setIntervals che fanno il ridisegno del DOM per i turni di posizione dello sfondo di sprite. Non sarebbe un grosso buggy?

Mi chiedevo se ci fosse un modo per aggirare tutto questo, magari usando Canvas, in modo che le animazioni possano accadere simultaneamente senza creare una coda di eventi e non devo preoccuparmi dei timer.

Spero che abbia senso, e per favore fatemi sapere se ho bisogno di chiarire ulteriormente.

+2

Mi piacerebbe suggerire di usare solo un setInterval/setTimeout-Loop e gestire tutto ciò che c'è dentro. – RoToRa

risposta

11

Il problema con più setInterval s è duplice. Il primo è come si indica, dal momento che tutti i Javascript sui browser sono (attualmente) single-threaded, l'esecuzione di un timer può ritardare l'esecuzione del timer successivo. (Worker threads stanno arrivando, comunque, Firefox already has them, come Safari 4 [e forse altri]). Il secondo è che il timer si verifica a intervalli regolari, ma se il gestore è ancora in esecuzione quando scade l'intervallo, il secondo intervallo è completamente saltato. Ad esempio, il timer può interferire con se stesso.

L'ultima parte ha bisogno di ulteriori spiegazioni: supponiamo di avere un setInterval a 10 ms (che è il più veloce che si possa ragionevolmente aspettarsi da un'implementazione per farlo, può essere bloccato in modo che non vadano più veloci di così). Se il tuo gestore prende 13ms, l'intervallo che dovrebbe essere successo 10ms dopo che è iniziato sarà completamente saltato.

Io di solito uso setTimeout per questo genere di cose. Quando il mio gestore viene attivato, eseguo il mio lavoro e pianifico il prossimo evento alla fine del gestore. Quindi (entro i limiti di ciò che è possibile che sia), so che il prossimo evento avverrà a quell'intervallo.

Per quello che stai facendo, sembra che un singolo timer "a impulsi" sarebbe il migliore, lavorando su tutto ciò che deve fare sul polso. Se il timer a impulsi utilizza setInterval o setTimeout è una chiamata di giudizio basata su ciò che stai vedendo con il tuo codice reale.

+0

Cosa intendi con timer "pulse", c'è qualche lettura che posso fare su questa tecnica? – resopollution

+1

@risopollution: intendevo solo un singolo timer che utilizzi per fornire all'app un impulso (ad esempio, heartbeat). Quindi un singolo timer che funziona per più caratteri (indipendentemente dal fatto che quel timer usi 'setInterval' o' setTimeout'). –

+0

grazie per il chiarimento – resopollution

3

+1 a T. J. Crowder, la risposta è stata perfetta. Consiglio vivamente di imparare a usare Canvas over DOM per l'animazione del gioco; il secondo è lento e buggato e bloccherà il browser in qualsiasi situazione non banale. OTOH, Canvas è molto più veloce e può essere accelerato via hardware, e ha anche un contesto 3D se ne hai bisogno.