วิธีจัดการกับคอมพิวเตอร์ที่เร็วขึ้นในวิดีโอเกมไคลเอนต์ / เซิร์ฟเวอร์แบบเรียลไทม์


15

ฉันกำลังสร้างเกมออนไลน์ครั้งแรกโดยใช้ socket.io และฉันต้องการให้เป็นเกมแบบผู้เล่นหลายคนแบบเรียลไทม์เช่น agar.io หรือ diep.io

แต่ฉันพบปัญหาในการพยายามหาวิธีที่จะทำให้คอมพิวเตอร์ทั้งหมดทำงานด้วยความเร็วเดียวกัน

ฉันมีสามแนวคิดสำหรับแบบจำลอง แต่ไม่มีแนวคิดใดที่ถูกต้องและฉันสงสัยว่าวิดีโอเกมปกติทำได้อย่างไร (คุณสามารถข้ามอ่านความคิดของฉันพวกเขาเพียงให้วิธีการดูปัญหาที่ฉันมี)

  1. เซิร์ฟเวอร์อนุญาตให้ไคลเอนต์ทำงานด้วยตนเองและส่งต่อการอัปเดตไปยังเซิร์ฟเวอร์ซึ่งจะส่งต่อไปยังไคลเอนต์ที่เหลือ นี่เป็นปัญหาที่คอมพิวเตอร์บางเครื่องทำงานได้เร็วกว่าเครื่องอื่น ๆ ทำให้พวกเขาอัปเดตเร็วขึ้นและเคลื่อนที่ข้ามหน้าจอเร็วขึ้น

  2. ให้เซิร์ฟเวอร์แจ้งให้ลูกค้าทราบเมื่อมีการอัปเดต ฉันสามารถรอจนกว่าลูกค้าคนสุดท้ายจะตอบสนอง (เป็นความคิดที่แย่มากในกรณีที่คนคนหนึ่งมีคอมพิวเตอร์ช้า) รอจนกว่าลูกค้าคนแรกจะตอบสนอง (อีกครั้งรอการสื่อสารก่อนแต่ละเฟรม) หรือเพียงแค่ส่งพวกเขาให้เร็วที่สุด ดูเหมือนว่าจะพบปัญหาเดียวกันกับหมายเลข 1)

  3. ที่จุดเริ่มต้นของเกมให้เซิร์ฟเวอร์บอกกับลูกค้าถึงวิธีการอัปเดตอย่างรวดเร็ว นี่หมายความว่าลูกค้าจะต้องรับผิดชอบในการ จำกัด การเคลื่อนไหวในช่วงเวลานั้น ตัวอย่างเช่นหากมีคนจัดการกดปุ่มสองครั้งภายในช่วงเวลานั้นก็จะส่งเหตุการณ์กดปุ่มเพียงปุ่มเดียว นี่เป็นปัญหาที่การดำเนินการบางอย่างอาจถูกเพิกเฉย (เช่นการกดปุ่มสองครั้ง) และการโต้ตอบจะขึ้นอยู่กับนาฬิกาของลูกค้าซึ่งอาจไม่ตรงกับนาฬิกาของเซิร์ฟเวอร์ เซิร์ฟเวอร์จะต้องติดตามลูกค้าแต่ละรายและตรวจสอบให้แน่ใจว่ามีการส่งการอัปเดตในเวลาที่ถูกต้อง

ฉันได้ทำการค้นคว้าแล้ว แต่บทความที่ฉันอ่านดูเหมือนจะไม่เจาะจงว่าจะทำอย่างไรถ้าลูกค้าส่งการอัพเดตเร็วกว่าไคลเอนต์อื่น ๆ

ในกรณีของฉันฉันกำลังติดต่อกับคนที่มีความเร็วแป้นพิมพ์เร็วกว่า (คอมพิวเตอร์จะส่งการอัปเดตแป้นพิมพ์มากกว่าคอมพิวเตอร์เครื่องอื่น)

โปรแกรมเมอร์มักจะจัดการกับเรื่องนี้อย่างไร


1
จากประสบการณ์ของฉันพวกเขาทำไม่ได้ นี่คือสาเหตุที่เครื่องเล่นเกมมีอยู่ ผู้ที่จ่าย 5 แกรนด์สำหรับนักโยนเปลวไฟที่ทันสมัยจะได้รับประโยชน์จากผู้ที่ยังใช้ Commodore 64 โดยอัตโนมัติ
Robert Harvey

1
ดังนั้นการเล่นเกมของฉันจะดูช้าเพราะเราต้องเล่นกับตัวหารธรรมดาที่สุด? ดูเหมือนว่าเซิร์ฟเวอร์เกมควรตั้งค่าจังหวะและมันก็ขึ้นอยู่กับลูกค้าที่จะติดตามหรือคุณจะต้องล่าช้า
JeffO

3
ฉันอาจจะเข้าใจผิดคำถาม แต่การใช้ไคลเอนต์และเซิร์ฟเวอร์แบบติ๊กอาจเป็นสิ่งที่คุณต้องการ gamedev.stackexchange.com/questions/81608/ โดยทั่วไปคุณเพียงประมวลผลอินพุตและลอจิกทุกๆระยะเวลา X (ปกติ 1 / N วินาทีเช่น 1/60 สำหรับตรรกะ 60Hz)
Christopher Wirt

4
หลังจากอ่านคำถามนี้ไปอีกซักพักดูเหมือนว่าคุณให้ความสำคัญกับลักษณะลูกค้าของเกมมากเกินไป หากคุณต้องการเกมที่มีผู้เล่นหลายคน "ยุติธรรม" เซิร์ฟเวอร์ของคุณจะต้องมีสิทธิ์ หมายความว่าทุกอย่างที่เกิดขึ้นกับลูกค้าได้รับการตรวจสอบหรือทำโดยเซิร์ฟเวอร์ จากนั้นคุณ จำกัด สิ่งต่าง ๆ จากที่นี่อาจผ่านระบบที่ใช้เห็บดังกล่าวข้างต้น
Christopher Wirt

1
อ๊ะรหัสเรียลไทม์ สถานที่พัฒนาเกมที่ลึกที่สุดและมืดที่สุด ยินดีต้อนรับสู่เรือคู่!
T. Sar - Reinstate Monica

คำตอบ:


8

ความคิดที่สามของคุณน่าจะใกล้เคียงที่สุดกับที่ฉันคิดว่าเป็นวิธีแก้ปัญหาอุตสาหกรรมสำหรับปัญหาประเภทนี้

สิ่งที่คุณอธิบายมักจะเรียกว่าเป็นเห็บ ในแต่ละเห็บจะมีการดำเนินการตามจำนวนที่แน่นอนสำหรับแต่ละไคลเอ็นต์ในอนุกรม บ่อยครั้งเซิร์ฟเวอร์เกมจะมีการกระทำแบบขนานเมื่อสามารถทำได้ แต่ปัญหานี้ซับซ้อนกว่ามาก

เห็บมีแนวโน้มว่าจะอยู่ในรูปแบบของ 1 / N วินาที, N เป็นจำนวนของเห็บต่อวินาทีหรือ Tickrate tickrate นี้อาจบ่อยมากหรือไม่บ่อยนักขึ้นอยู่กับการใช้งานของคุณ ข้อเสนอแนะส่วนบุคคลของฉันคือการหลีกเลี่ยงเห็บมากกว่า 60 เห็บ / วินาทีเว้นแต่คุณจะแน่ใจว่าคุณต้องการมากขึ้น คุณอาจจะไม่ :)

การกระทำควรเป็นอะตอม ตัวอย่างเช่นใน slither.io การกระทำเช่นการเคลื่อนไหวไม่ควรดำเนินการบางอย่างเช่นการทำลายโซ่ของคุณในทันทีเว้นแต่ผู้เล่นที่คุณกดได้ทำการเคลื่อนไหวแล้ว สิ่งนี้อาจดูเล็กน้อยสำหรับบางสิ่งบางอย่างในระดับพิกเซล แต่ถ้าคุณกำลังรับมือกับการเคลื่อนไหวแบบเรียงต่อกันมันจะชัดเจนมากขึ้นและรับประกันความเป็นธรรม หากผู้เล่น A ย้ายไปที่ไทล์ X, Y และผู้เล่น B อยู่บนไทล์นั้นคุณต้องให้แน่ใจว่าในตอนท้ายของติ๊กผู้เล่น B จะยังคงอยู่บนไทล์นั้นสำหรับการกระทำใด ๆ ที่จะเกิดขึ้นระหว่างพวกเขา

นอกจากนี้ฉันจะบอกว่าหลีกเลี่ยงการคำนวณใด ๆ ของคุณที่ทำในฝั่งไคลเอ็นต์เว้นแต่ว่าพวกเขาจะทำอย่างเป็นอิสระในฝั่งเซิร์ฟเวอร์ สิ่งนี้มีความซับซ้อนและมีค่าใช้จ่ายสูงในวิชาฟิสิกส์ (หลายเกมเลือกใช้อัตราการติ๊กต่ำกว่าฟิสิกส์มากกว่าการกระทำและกิจกรรมอื่น ๆ ด้วยเหตุนี้)

สำหรับการอ้างอิงนี่คือการเชื่อมโยงที่ดีเพื่อเสริมความเข้าใจของตัวเองของเซิร์ฟเวอร์เกมและระบบเครือข่ายหลายคน

สุดท้ายนี้ฉันจะบอกว่าอย่าปล่อยให้ความยุติธรรมทำลายเซิร์ฟเวอร์ของคุณ หากมีการหาช่องโหว่ที่ทำให้เกมของคุณไม่ยุติธรรมให้แก้ไขเกมเหล่านั้น หากเป็นเรื่องของคอมพิวเตอร์ที่ดีกว่าที่มีข้อได้เปรียบเล็กน้อยฉันจะบอกว่ามันอาจไม่ใช่เรื่องใหญ่


3
@ProQ มันคุ้มค่าที่จะต้องทราบว่าการเขียน netcode ที่ดีนั้นไม่สำคัญเลย! หากแอปของคุณใช้งานไม่ได้ตั้งแต่เริ่มต้นและดูเหมือนว่ารหัสเครือข่ายของคุณจะดูดอย่ายอมแพ้ แม้แต่คนที่ทำเพื่อชีวิตประจำวันก็มีปัญหา มันเป็นเพียงที่ยาก!
T. Sar - Reinstate Monica

0

ระบบต่อไปนี้ทำให้แน่ใจว่าไคลเอนต์และเซิร์ฟเวอร์ทั้งหมดแชร์เกมสถานะเดียวกันเกือบตลอดเวลา

มีสถานะของเกมบนไคลเอนต์และเซิร์ฟเวอร์

เมื่อไคลเอนต์พยายามใช้คำสั่ง (เมาส์แป้นพิมพ์และอินพุตอื่น ๆ ) ให้ดูสถานะของเกมถ้ามันถูกต้อง

หากเป็นเช่นนั้นให้ส่งคำสั่งไปยังเซิร์ฟเวอร์โดยไม่ต้องดำเนินการบนไคลเอ็นต์ที่ส่ง

เมื่อเซิร์ฟเวอร์ได้รับคำสั่งให้ดูสถานะของเกมถ้ามันถูกต้อง

หากเป็นเช่นนั้นให้ส่งคำสั่งกลับไปยังไคลเอนต์ทั้งหมดพร้อมกับวันที่ในอนาคตที่แน่นอนหลังจากสิ่งที่ควรจะถูกดำเนินการบนเซิร์ฟเวอร์จากนั้นดำเนินการตามคำสั่งที่ร้องขอหลังจากการหน่วงเวลาเท่ากับเวลาต่ำสุดเพื่อส่งคำสั่ง . จากนั้นบันทึกวันที่ซึ่งจะช่วยในการทำนายอนาคต หากเวลาแตกต่างกันมากเกินไปทำให้ระบบเกมของคุณมีเวลามากขึ้น

เมื่อลูกค้าได้รับคำสั่งจากเซิร์ฟเวอร์ให้ดูสถานะของเกมหากถูกต้องดำเนินการตามคำสั่งที่ร้องขอโดยทันทีจากนั้นดูที่วันที่ปัจจุบันและเปรียบเทียบกับการคาดการณ์วันที่ที่ได้รับ หากไม่ถูกต้องไคลเอ็นต์จะไม่ซิงค์กัน (ลูกค้าทั้งหมดที่มีการเชื่อมต่อที่คล้ายกันได้รับพร้อมกัน)

หากวันที่ก่อนหน้านี้คุณมีปัญหาในขั้นตอนก่อนหน้าให้แก้ไข หากวันที่เล็กน้อยหลังจากไม่ทำอะไรเลยหากวันที่หลังจากนั้นนานไคลเอนต์จะไม่ซิงค์เช่นไคลเอ็นต์ล่าช้าหลังมากเกินไป

เมื่อไคลเอนต์ไม่ซิงค์ให้ขอสำเนาสถานะเกมทั้งหมดของเซิร์ฟเวอร์และใช้รายการนั้น หากเกิดขึ้นบ่อยเกินไปแก้ไขได้เพราะมันแพงกว่าการส่งคำสั่ง

บนไคลเอนต์ให้เรนเดอร์สิ่งต่าง ๆ บนหน้าจอเฉพาะเมื่อไม่มีสิ่งอื่นเหลือให้ทำ ในสถานการณ์ง่าย ๆ ฟังก์ชั่นการเรนเดอร์จะใช้สถานะเกมปัจจุบันเป็นอินพุตเท่านั้น

ยิ่งไปกว่านั้นคุณสามารถเพิ่มประสิทธิภาพได้มากโดยใช้ระบบการทำนายการจัดกลุ่มคำสั่งการเรนเดอร์แตกต่างกันเท่านั้น ...

การตรวจสอบควรแตกต่างกันไปขึ้นอยู่กับเซิร์ฟเวอร์เพื่อ จำกัด การร้องขอคำสั่ง / หน่วยเวลา


0

ฉันไม่รู้ว่านี่เป็นปัญหาของห้องสมุดหรือสภาพแวดล้อมที่คุณใช้หรือไม่ แต่ฉันคิดว่าคุณกำลังเข้าใกล้มันผิดทั้งหมด

ในเกมที่มีผู้เล่นหลายคนส่วนใหญ่เป็นเพียงเซิร์ฟเวอร์ที่ทำการคำนวณจริง ๆ เท่านั้น ลูกค้าเป็นเพียงเครื่องใบ้ของ IO เท่านั้นที่ปัญหาด้านประสิทธิภาพที่แท้จริงคือการวาดกราฟิก 3D และในกรณีนี้มันไม่สำคัญว่าลูกค้าจะสามารถทำงานที่ 20 หรือ 200 FPS ได้หรือไม่เพราะมันมีผลกับภาพเท่านั้น นั่นหมายถึง "การอัพเดทไคลเอ็นต์" ไม่มีความหมายอย่างแน่นอน ลูกค้าอาจลอง "คาดการณ์" ว่าเซิร์ฟเวอร์ใดที่อาจคำนวณ แต่นั่นเป็นเพียงการทำให้เกมเพลย์ราบรื่นและไม่มีผลกระทบต่อการเล่นเกมอย่างแท้จริง

ความเร็วแป้นพิมพ์เร็วขึ้น

ฉันไม่รู้ด้วยซ้ำว่าอะไร คนส่วนใหญ่ไม่สามารถรักษาความเร็วของคีย์บอร์ดต่ำได้ดังนั้นสิ่งนั้นจะส่งผลต่อประสิทธิภาพของผู้เล่นอย่างไร

มิฉะนั้นคำถามนั้นค่อนข้างกว้างเกินไปและคุณควรมุ่งเน้นที่ปัญหาที่เกิดขึ้นจริงเพียงครั้งเดียวแทนที่จะพยายามสร้างปัญหา "ทั่วไป" ที่คุณอาจไม่มี


ความเร็วแป้นพิมพ์ที่เร็วขึ้นไม่ได้เกี่ยวกับการพิมพ์ แต่จะมีคำสั่งกี่คำที่สามารถส่งหากคุณกดปุ่ม "ก้าวไปข้างหน้า" หรือกดปุ่ม "ยิง"
gbjbaanb

@gbjbaanb และนั่นเป็นปัญหาได้อย่างไร คุณควรใส่ใจกับคำสั่งที่กดและปล่อยเท่านั้น คุณไม่ควรสนใจที่จะทำการอัพเดท
ร่าเริง

คุณสนใจว่าคุณจัดการเหตุการณ์ทั้งหมดเช่น OP ที่คาดไว้ - บนไคลเอนต์ดังนั้นหากการกด w ทำให้คุณเดินหน้าต่อไปได้ไกลและแป้นพิมพ์ของคุณเร็วกว่าคนอื่น สิ่งสุดท้ายที่คุณต้องการคือการสร้างเกมแข่งรถที่คุณต้องกดปุ่มเพื่อเดินหน้าต่อไป!
gbjbaanb

@gbjbaanb ไม่ถูกต้อง เซิร์ฟเวอร์รู้ว่า "ผู้เล่นกำลังก้าวไปข้างหน้า" และทุกๆ 1 ใน 60 ของวินาทีจะอัพเดทตำแหน่งของผู้เล่นทุกคนโดยขึ้นอยู่กับว่าพวกเขากำลังเดินหน้า นี่คือการทำงานของเกมทั้งหมด ลูปการอัปเดตเหมือนกันสำหรับเอนทิตีทั้งหมดในเกมและการอัปเดตไม่ได้ขึ้นอยู่กับเหตุการณ์จาก UI
ร่าเริง

1
ไม่นั่นไม่ใช่ความเข้าใจของ OP ซึ่งเป็นเหตุผลที่เขาถามและนั่นคือสาเหตุที่คุณพูดว่า "ฉันไม่รู้ด้วยซ้ำว่าอะไร" หากคุณเข้าใจตำแหน่ง OPs คำถามของเขาก็สมเหตุสมผล หาก OP กำหนดรหัสเกมของเขาให้ทำงานร่วมกับลูปเกมโดยสิ้นเชิงจากการส่งมอบเหตุการณ์ที่รวดเร็วจากลูกค้านั่นคือสิ่งที่เขาถามเกี่ยวกับ - คุณผิดที่จะใช้การออกแบบเกมสมมุติกับสิ่งที่ OP ถามจริง ๆ ไม่ว่าการออกแบบของเขาจะผิดไปจากมาตรฐานส่วนใหญ่ก็ตาม
gbjbaanb
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.