Jak zrekompensować ruchome obiekty z prognozą po stronie klienta?

11

Wdrażam serwer gry, który obsługuje walkę wręcz podobną do Star Control . Więc masz statki latające i strzelające, z super prostą fizyką prędkości / przyspieszenia / tłumienia, która napędza ruch.

wprowadź opis zdjęcia tutaj

Przeczytałem Valve, Gafferon i Gambetta i zaimplementowałem algorytm Gambetta do przewidywania klientów:

wprowadź opis zdjęcia tutaj

Prognozowanie klienta działa na statku gracza, aktualizując jego pozycję z serwera w momencie jego dostarczenia, a następnie stosując ponownie nieprzetworzone dane wejściowe serwera na statku gracza.

Niestety nie działa dobrze w mojej grze. Uważam, że ma to związek z faktem, że przykład Gambetty nie uwzględnia obiektów, które już się poruszają, ani poleceń, które są aktualizowane krok po kroku. („krok” mam na myśli ramkę). Tak więc w mojej grze gracz naciska, aby przyspieszyć (już poruszający się) statek, który kontynuuje ruch na kliencie, wysyła polecenie do serwera i zwykle otrzymuje migawkę świata z serwera w następnym kroku. Dostaję coś więcej:

wprowadź opis zdjęcia tutaj

Polecenie odtwarzacza jest uruchamiane w kroku 3 klienta , ale na serwerze działa tylko w kroku 5 serwera . Zanim klient otrzyma migawkę świata w kroku 6 klienta , przewidywanie jest dalekie, szczególnie przy większych prędkościach.

Sedno problemu polega na tym, że klient uruchamia polecenie w kroku 5 , ale serwer uruchamia je w kroku 6 . Pomyślałem o wysłaniu kroku klienta z poleceniem, a serwer powinien wycofać się i ponownie uruchomić polecenie z krokiem czasu klienta. Może to jednak prowadzić do wielu innych problemów - takich jak to, co dzieje się z poleceniami otrzymanymi od wycofania, lub w jaki sposób oszukiwani klienci mogą wykorzystać, zmieniając wysłany krok.

Czytanie i oglądanie filmów takich jak ten z Google wspomina o innym podejściu, w którym stopniowo zmieniasz pozycję gracza, aby dopasować się do migawki w kilku krokach.

Moje pytania:

  • Czy potrafisz sprawić, by algorytm Gambetty działał przy stałym ruchu krokowym? Czy jest to koncepcyjnie niezgodne z moją grą?

  • Czy zatem stopniowa interpolacja kroków jest właściwą drogą? Jeśli tak, to w jaki sposób interpolujesz już poruszający się obiekt z pozycji klienta, aby dopasować go do tego, co właśnie otrzymał z serwera?

  • Czy te metody, stopniowa interpolacja i algorytm Gambetty mogą działać w tandemie, czy też wykluczają się wzajemnie?

OpherV
źródło
Robiłem to samo i napotkałem dokładnie ten sam problem. Gdy tylko dodałem prędkości, stosując stan serwera i ponownie stosując dane wejściowe, pozbyłem się już obsługiwanych zmian prędkości. Próbowałem ponownie zastosować wszystkie aktualizacje od czasu ostatniego otrzymania wiadomości, ale nie jest to jeszcze zbyt płynne. Czy kiedykolwiek znalazłeś rozwiązanie tego problemu?
MakuraYami,
@MakuraYami Tak - zacząłem pisać artykuł opisujący rozwiązanie. Wkrótce się zaktualizuje!
OpherV
Pracowałem więcej nad moim projektem i znalazłem użyteczne rozwiązanie oraz kilka innych dobrych zasobów na ten temat. Chcę dalej omawiać, porównywać rozwiązania itp. Daj mi znać, gdzie mogę się z Tobą skontaktować :)
MakuraYami
@makurayami moja nazwa użytkownika w Gmailu
OpherV

Odpowiedzi:

5

W ciągu 6 miesięcy, odkąd zadałem to pytanie, ostatecznie opracowałem kompletny serwer gier typu open source, aby poradzić sobie z tym dokładnie problemem (i wieloma innymi!): Http://lance.gg

wprowadź opis zdjęcia tutaj

Zaangażowane prace badawczo-rozwojowe pozwalają mi teraz odpowiedzieć na własne pytania:

  • Czy potrafisz sprawić, by algorytm Gambetty działał przy stałym ruchu krokowym? Czy jest to koncepcyjnie niezgodne z moją grą?

    Algorytm Gambetty nie będzie działał, gdy ruch bytu nie jest deterministyczny (z POV klienta). Jeśli na istotę można wpływać bez udziału fizyki lub innych graczy, należy na przykład zastosować bardziej skomplikowane podejście.

  • Czy zatem stopniowa interpolacja kroków jest właściwą drogą? Jeśli tak, to w jaki sposób interpolujesz już poruszający się obiekt z pozycji klienta, aby dopasować go do tego, co właśnie otrzymał z serwera?

    Dotyczy to innego tematu, którym jest uzgadnianie przez klienta aktualizacji serwera. Stopniowa interpolacja działa, ale w przypadku bardzo szybkich gier, takich jak ta w pytaniu, lepiej jest zastosować ekstrapolację

  • Czy te metody, stopniowa interpolacja i algorytm Gambetty mogą działać w tandemie, czy też wykluczają się wzajemnie?

    Mogą współpracować, ale tylko wtedy, gdy ruch jednostki jest deterministyczny na podstawie POV klienta. Więc to nie zadziała, jeśli na istotę wpływa fizyka lub fizyka fizyczna, taka jak wstawianie, przeciąganie itp.

OpherV
źródło
1

Twoja gra wydaje się być zbyt „w czasie rzeczywistym”, aby myśleć w kategoriach czasu. Pomyślę tylko w kategoriach „tur”, jeśli grę można uznać za „turową”. W przeciwnym razie po prostu porzuć ideę zakrętów lub kroków. Wszystko staje się łatwiejsze :)

Pamiętaj, że przewidujesz lokalnie dla swojego gracza i interpolujesz tylko dla innych bytów (jak wyjaśniono w trzecim artykule z serii). Sposobem radzenia sobie z aktualizacjami serwera dla obiektów, które już się poruszały, jest uzgadnianie po stronie serwera, wyjaśnione w dolnej połowie drugiego artykułu (tego, do którego się łączyłeś).

Mam nadzieję że to pomoże :)

ggambett
źródło
Żeby wyjaśnić - „krok” mam na myśli „klatkę”, która działa 60 razy na sekundę. Nazywam to krokiem (a nie klatką), aby odróżnić rzeczywisty postęp gry od renderowania, a idealnie oba są synchronizowane z prędkością 60 na sekundę. Wdrożyłem już twoją wersję uzgadniania po stronie serwera, która działa doskonale. To pytanie dotyczy tylko statku gracza - który ciągle się porusza bez względu na polecenie gracza (z powodu bezwładności). Tam właśnie leży moja trudność. Masz jakieś przemyślenia na ten temat? :)
OpherV
Ramki różnią się od kroków. Kroki poruszają się w stałej, przewidywalnej kolejności. Ramki zmieniają się w różnym czasie, więc wszelkie postępy należy pomnożyć przez czas delta dla tej ramki.
Tealr
@Tealr rzeczywiście, dlatego na początku użyłem terminu „krok” - chciałem tylko wyjaśnić, że użycie „kroku” nie ogranicza się do gier turowych, aw mojej grze krok zajmuje dokładnie 1 / 60 sekund niezależnie od renderowania.
OpherV
Po prostu coś, co zauważam do własnych eksperymentów: 1/60. jest niezwykle szybki i założę się, że większość gier online z udziałem więcej niż 1x1 działa w 1/10 sekundy. aktualizacje lub o nich.
Patrick Hughes,