Введення на стороні сервера


9

В даний час в моїй грі клієнт - це не що інше, як рендерінг. Коли стан входу змінюється, клієнт відправляє пакет на сервер і переміщує плеєр так, ніби він обробляє вхід, але сервер має остаточне слово на позиції.

Це, як правило, працює дуже добре, за винятком однієї великої проблеми: падіння країв. В основному, якщо гравець йде до краю, скажімо, до скелі, і зупиняється прямо перед відходом від краю, іноді через секунду, він буде телепортуватися з краю. Це тому, що пакет "Я перестав натискати W" надсилається після того, як сервер обробляє інформацію.

Ось схема затримки, яка допоможе вам зрозуміти, що я маю на увазі: http://i.imgur.com/Prr8K.png

Я міг би просто надіслати пакет "W Presssed" кожен кадр для сервера для обробки, але це, здавалося б, було дорогим рішенням пропускної здатності.

Будь-яка допомога вдячна!

Відповіді:


5

Хоча сервер має остаточне слово щодо позиції, він повинен зробити це, перевіривши та перевіривши, чи правильно перевіряє те, що клієнт надсилає як дані та позиції. Я говорю це тому, що те, що ти робиш, - це переміщення гравця негайно, і очікування, яке створюється у вашому коді, - це те, що клієнт - це реальна позиція.

Ви думаєте, що це взагалі добре працює, але це не так. Побічна примітка: ви кажете, що ваш клієнт - це не що інше, як рендерінг, а потім негайно дайте йому місцевий контроль, щоб він рухався без повідомлень сервера. У вас це не може бути обома способами, або зачекайте, поки сервер підкаже вам рухатися, або візьміть на себе деякий контроль над своєю позицією та використовуйте сервер для перевірки читів.

Зауважу, що ваші відповіді сягають однієї цілої секунди? Це затримка в 500 мс, яка смішно велика для будь-яких ігрових дій. Спробуйте з’ясувати, чому цей поворот займає так довго, це може бути що завгодно, від резервних команд, резервного копіювання від того, щоб не отримувати негайно обробку до затопленої пропускної здатності або навіть демонів, викликаючи багато втрачених пакетів.

Я думаю, що це має статися, це те

client sends a move + position update
server gets it t+latency time later
server verifies and sends out info to all clients
client receives this at (t+latency + latency)

Тут складна частина полягає в тому, що якщо клієнт отримує повідомлення про себе, він здебільшого повинен ігнорувати його, якщо це повідомлення є чимось на зразок "недійсний хід, замість цього перейдіть до XYZ". Якщо це повідомлення для кого-небудь іншого клієнта, що ви отримуєте інформацію про нього, тоді вам доведеться вчасно екстраполювати вперед, так що, схоже, буде там, де воно буде.


Клієнт взагалі не надсилає свою позицію; він просто прогнозує / інтерполює. Ось чому воно опадає по краях, коли думає, що на краю. Крім того, я не бачу, де я сказав, що відставання склало 1 секунду, це більше, ніж від 8 мс (локальне тестування) до 100 мс (через Інтернет). Пізніше я сказав, що гравця повертаються назад, оскільки я періодично надсилаю повні оновлення позицій. Чи правильно я розумію, що я повинен надіслати позицію, яку клієнт вважає, що це має бути, разом із натиснутими клавішами, і сервер повинен перевірити, чи це можливо?
Томас

"іноді секунду пізніше він буде телепортуватися" мається на увазі великі затримки, звідки я отримав час. Що стосується грішної дії, так, клієнт грає, а сервер грає позаду та дає можливість клієнту знати, чи було зроблено щось незаконне. Ви помітите в багатокористувацьких іграх в Інтернеті, в основному ви бачите, як інші люди змінюють позиції (ті, що надходять з сервера), тоді як ваша власна позиція змінюється дуже рідко від прямих корекцій сервера. Інші люди бачать, як ти змінюєш посаду тощо ...
Патрік Хьюз

Невже це все ж не може призвести до того, що програвач відвалиться від краю сервера? Якщо я не надсилаю пакет кожен кадр, сервер все ще може думати, що програвач рухається приблизно 32 мс. (Я надсилаю пакети кожні три кадри). Або ви припускаєте, що я взагалі не імітую вхід на сервері, а лише перевіряю, чи позиція знаходиться в межах натиснутого вводу?
Томас

Оскільки сервер виправляє лише недійсний рух, про який повідомляє клієнт, він ніколи не надсилатиме «ти впав зі скелі», якщо сам клієнт не проїхав прямо через край. У цьому циклі зворотного зв’язку саме сервер коригує погляд клієнта на світ і його місце в ньому. Рух почуватиметься чітким та чуйним до гравця. Інші дії, такі як взаємодія зі світовими об'єктами, включатимуть очікування, коли сервер повідомить клієнту, що саме сталося, натисніть поле і чекайте відповіді, але ми тут просто говоримо про рух.
Патрік Хьюз

Це дуже схоже на те, що я зараз роблю; відправлення позиції на сервер і надання сервера перевірки, чи міг гравець перейти на цю позицію. Це, мабуть, є більш евристичним підходом, і, на мою думку, не буде майже ефективним, як прийняття сервера рішення, періоду. Чи надсилає часові позначки з кожним пакетом? Я думаю, що це усуне питання. Я вважаю, що Halo та ігри, що використовують двигун Source, використовують це.
Томас

0

Я розумію, що ви ставите питання:

Сервер отримує пакет, коли я починаю натискати кнопку "вперед" і ще один пакет, коли я нарешті відпустив кнопку "вперед". Тому власне рух на сервері починається і закінчується приблизно 100 мілісекунд «занадто пізно» в реальній грі порівняно з тим, що гравець виражає на стороні клієнта. Отже, якщо гравець хоче рухатися 10 секунд, він може закінчитися переміщенням 10x секунд замість того, де x >= 1онлайн.

Це погана стратегія дизайну, оскільки вона не виражає волі гравця у світі гри, як гравець має намір, створюючи досить поганий досвід користувача.

Я б рекомендував рішення - надіслати пакет (настільки часто, наскільки це можливо), який вказує, скільки кроків зробив гравець і в якому напрямку. Потім сервер оновлює ігровий світ новим розташуванням гравця, якщо він пройде перевірку на правильність. Тому гравець може рухатися з великою точністю і уникати падіння високих уступів.

Альтернативою було б запам’ятати позиції гравця за минулу секунду та виправити позицію заднім числом до моменту відпускання кнопки. Здається, це створило б ефект гумки за старих часів. (Лише з іншої причини)

Тому в основному вам потрібно буде надіслати пакет, яка кнопка натиснута і який був фактичний час гри, на яку була натиснута кнопка, а потім пізніше, яка кнопка була відпущена і в який саме час.


Як я вже сказав Патріку, я думаю, що це рішення буде скоріше евристичним підходом; замість того, щоб сервер був "Людина", замість цього сервер перевіряє дані клієнта на достовірність. Звичайно, доведеться створити деяку свободу, щоб відставання чи інші проблеми з мережею не створювали помилкових позитивних результатів.
Томас
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.