La fisica non si sincronizza correttamente sulla rete quando si utilizza Bullet


11

Sto cercando di implementare un sistema fisico client / server utilizzando Bullet, tuttavia ho problemi a sincronizzare le cose.

Ho implementato uno stato di movimento personalizzato che legge e scrive la trasformazione dai miei oggetti di gioco e funziona localmente ma ho provato due approcci diversi per i giochi in rete:

  1. Gli oggetti dinamici sul client che si trovano anche sul server (ad es. Detriti non casuali e altre cose non importanti) vengono resi cinematici. Funziona correttamente ma gli oggetti non si muovono molto bene
  2. Gli oggetti sono dinamici su entrambi, ma dopo ogni messaggio dal server che l'oggetto si è spostato ho impostato la velocità lineare e angolare sui valori dal server e chiamo btRigidBody ::ceedToTransform con la trasformazione sul server. Chiamo anche btCollisionObject :: activ (true); per forzare l'aggiornamento dell'oggetto.

Il mio intento con il metodo 2 era fondamentalmente di fare il metodo 1 ma dirottare Bullet per fare la previsione di un uomo povero invece di fare il mio per appianare il metodo 1, ma questo non sembra funzionare (per motivi che non sono chiari al 100% anche se passo attraverso Bullet) e gli oggetti a volte finiscono in posti diversi.

Sto andando nella giusta direzione? Bullet sembra avere il proprio codice di interpolazione incorporato. Può aiutarmi a far funzionare meglio il metodo 1? O il mio codice metodo 2 non funziona perché lo sto calpestando accidentalmente?

EDIT: Un altro problema con il metodo 1 che ho appena notato è che la risposta alla collisione sarà molto lontana per le collisioni contro oggetti non sincronizzati. I corpi cinetici in qualche modo sparano all'infinito a volte poiché non possono essere respinti.


Alcune cose che potrebbero aiutarti a ottenere una risposta: che lingua / motore stai usando? Che tipo di connessione è? Quanto è grave il deficit di sincronizzazione, rispetto al ping al server?
Fibericon,

2
La seconda opzione non funziona perché si impostano le velocità sui valori del server solo dopo alcuni frame, quindi tra ogni pacchetto ci sono alcuni frame in cui le cose possono andare alla deriva. Consiglierei di leggere tutti i post di Gaffer sulla fisica dei giochi, probabilmente dovresti prima leggere "correggi il tuo timestep" ma ecco l'articolo finale che parla della fisica in rete gafferongames.com/game-physics/networked-physics
Roy T.

Sto usando un motore auto-sviluppato in C ++. Tuttavia sono abbastanza sicuro che il deficit di sincronizzazione non sia poi così grave, probabilmente 1 frame over ping se dovessi indovinare, ma sto ancora facendo principalmente test solo su LAN. Controllerò quegli articoli e sì, hai ragione, le velocità sono disattivate. Tuttavia le cose sono via via, come la cassa è in tutta la mappa. L'impostazione esplicita della trasformazione non dovrebbe rendere le cose generalmente conformi alla fine? (anche se non è ancora carino, jiggles, ecc.)
Lucas,

Ho letto il post di Gaffer ed è stato informativo, ma sembrava riguardare principalmente i movimenti dei giocatori, che è già qualcosa su cui lavoro. Ho letto e sembra che il mio codice del metodo 2 sia praticamente identico al metodo utilizzato nel motore Unreal . Non forniscono molti dettagli, ma mi chiedo se l'idea sia valida ma il mio uso di Bullet non è corretto.
Lucas,

Una lettura interessante, in parte correlata al tuo argomento: gamasutra.com/view/feature/3094/… . Riguarda un RT e non riguarda la fisica, ma arrivano al punto in cui devono sincronizzare una simulazione su server e client. Il modo in cui lo fanno? Eseguono simulazioni indipendenti sia su client che su server, ma il server invia pacchetti che assicurano che la simulazione client non diverga e venga corretta, se succede ...
tom van green

Risposte:


4

È necessaria una corretta previsione sul lato client .

Dovresti davvero leggere in dettaglio il link che Roy T. ti ha fornito nel suo commento . Descrive cosa fare con l'input del giocatore e la fisica dei personaggi, ma il principio rimane lo stesso per la "fisica guidata dal server".

Questo non è banale da implementare, ma in poche parole, per gli oggetti di gioco che devono essere sincronizzati:

  • Esegui la fisica sia sul server che sul client;
  • Il server invia aggiornamenti regolarmente;
  • Il client adegua continuamente e senza intoppi il proprio mondo fisico ai valori del server.

Quindi sì, stai andando nella giusta direzione con il tuo metodo 2. Tuttavia, non è sufficiente sovrascrivere i valori, otterrai salti sul client, ciò che devi fare è interpolare uniformemente e continuamente ai valori del server.

Per il tuo vero bug, non ho familiarità con Bullet, ma probabilmente ti mancano alcuni valori, ad esempio hai impostato le velocità lineari e angolari, ma hai impostato le accelerazioni?


Grazie! Questo mi fa sentire meglio di essere sulla strada giusta. Esaminerò il mio codice con un pettine a denti fini ora. Forse alcune notifiche non vengono attivate o come dici tu mi manca un valore poiché il metodo 2 dovrebbe funzionare (a scatti).
Lucas,

3

Quello che faccio personalmente è chi ospita il gioco crea il mondo della fisica e sincronizza gli oggetti con i clienti. Anche se è uno schema di rete p2p, continuo a basare il motore fisico su uno dei client dei giocatori.

L'altra fisica che uso che è puramente piacere per gli occhi non ha nemmeno bisogno di essere sincronizzata.

In un prototipo di un tempo fa chiamato "boilerzerker", gestivo la fisica sull'host e gli effetti particellari (anche usando la fisica) non erano sincronizzati attraverso una rete ma indipendenti per ogni cliente perché erano accattivanti.


Grazie, sì, è un modo per farlo. Tuttavia, ciò non porta a buone risposte di collisione sul client a cose che il client fa e anche le cose accattivanti non interagiranno sempre correttamente poiché non possono respingere le cose del server (almeno in quel momento). Penso che questo debba essere possibile poiché motori come Unreal e Source sembrano farlo.
Lucas,

eye candy non deve essere sincronizzato, può essere calcolato per cliente. la risposta sul client viene calcolata sul server, le coordinate per il client vengono appena calcolate e rispedite, non si invia una richiamata al client dicendo che si è scontrato, che probabilmente sembrerebbe orribile.
tsturzl,

2

È impossibile implementare mondi fisici sincroni della rete. Piccola differenza nel passaggio N ovviamente differenza molto più grande nel passaggio N + 1 Non è possibile applicare forze o impulsi per mantenerlo sincronizzato e apparire realistico.

Soluzioni: -

  1. Puoi considerare di sincronizzare solo pochi oggetti come personaggi o macchine da corsa, soprattutto se sono cinematici. Ma la maggior parte del mondo non sarebbe sincronizzata per apparire realistica.

  2. Puoi avere un mondo di fisica sul server e trasmettere posizioni e velocità degli oggetti ai client.


Puoi provare a giocare a qualche gioco di rete con la fisica per vedere che i mondi non sono sincronizzati. es. Need For Speed ​​World è gratuito e ha multiplayer e fisica di base. (scatole sulla strada e oggetti distruttibili)
Max

Non sono sicuro di seguirti esattamente. Sono abbastanza sicuro che ciò sia possibile poiché molti giochi consentono ai giocatori di lanciare casse (ad esempio). Sembra che la tua opzione 2 sia simile alla mia opzione 2, ma non riesco a far sì che Bullet agganci in modo pulito gli oggetti alle loro posizioni del server. Forse è questo il mio problema alla radice?
Lucas,

1
No. Di solito è un'illusione di sincrono. Se confronti le schermate, vedrai che quando rimbalzi nelle caselle, le caselle volano in direzioni diverse. o le caselle non sono affatto fisica (solo animazioni edite). Il numero di caselle è diverso. Quando dico animazione intendo che non c'è animazione fisica dietro i movimenti. Non fanno vari trucchi per rendere l'immagine in qualche modo sincronizzata, ma non sono mondi di fisica sincrona. Dovresti guardare e confrontare come si muovono in diversi giochi.
Max
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.