खेल विकास के लिए नेटवर्किंग पर घड़ियों को कैसे सिंक करें?


10

मैं एक खेल लिख रहा हूं जिसमें बहुत समय आधारित पहलू हैं। नेटवर्क स्टॉल और पैकेट के माध्यम से नहीं जा रहे हैं (और पैकेट के प्राप्त होने और नहीं के बीच का समय) होने पर मैं खिलाड़ी की स्थिति का अनुमान लगाने में मदद करने के लिए समय का उपयोग करता हूं। यह इस अर्थ में एक पैशमैन प्रकार का खेल है कि एक खिलाड़ी एक दिशा चुनता है और हिलना बंद नहीं कर सकता है, इसलिए यह सिस्टम समझ में आता है (या कम से कम मुझे लगता है कि यह करता है)।

इसलिए मेरे दो सवाल हैं: 1) मैं नेटवर्क में देरी होने पर गेम की घड़ियों को कैसे सिंक करूं? 2) क्या उन्हें सिंक करना ठीक नहीं है और यह मान लें कि वे समान हैं (मेरा कोड टाइम-ज़ोन इंडिपेंडेंट है)। यह एक सुपर प्रतिस्पर्धी खेल नहीं है जहां लोग अपनी घड़ियों को धोखा देने के लिए बदलेंगे, लेकिन फिर भी।

खेल को जावा और पायथन (एक परियोजना के रूप में समानांतर विकास) में प्रोग्राम किया जा रहा है



5
मुझे यकीन है कि यह प्रश्न पहले से ही gamedev.stackexchange.com पर कवर किया गया है, या कम से कम यह वहां है।
कॉंगसबॉन्गस

1
@ कोंगो: मैं इतना निश्चित नहीं हूं। जबकि यह आमतौर पर खेलों के लिए किया जाने वाला कार्य है, यह स्वाभाविक रूप से खेल के विकास के लिए विशिष्ट नहीं है। कई अन्य वितरित प्रणालियों को सिंक्रनाइज़ घड़ी की आवश्यकता होती है।
जान हुदेक

2
क्या आपने पहले ही IPv4 विकल्प TIMESTAMP का उपयोग करने की कोशिश की है? अधिक जानकारी पर है linux.die.net/man/7/socket वहाँ से करने के लिए linux.die.net/man/3/cmsg पर एक छोटा सा उदाहरण कार्यक्रम और उसके बाद pdbuchan.com/rawsock/rawsock.html से पहले पिछले एक IPv6 अनुभाग।
ott--

2
गेम्स (एप्लिकेशन) को सिस्टम घड़ी को नहीं छूना चाहिए।
मोनिका को बहाल करना - एम। श्रोडर

जवाबों:


9

मुझे लगता है कि सिस्टम में घड़ी को सिंक्रोनाइज़ करना निश्चित रूप से ठीक नहीं है । उपयोगकर्ता आपको सिस्टम सेटिंग्स को छूने की उम्मीद नहीं करता है और कई सिस्टम आपको करने भी नहीं देंगे।

आपको केवल एक पक्ष की घड़ी से दूसरे पक्ष की घड़ी में टाइमस्टैम्प को परिवर्तित करने के लिए सहसंबंध होना चाहिए। दूसरी ओर, आपको इस सहसंबंध की आवश्यकता बल्कि सटीक होना चाहिए, कम से कम एक सैकेंड के सौवें हिस्से तक कहें, यदि आप खिलाड़ी के पदों की भविष्यवाणी के लिए इसका उपयोग करना चाहते हैं। सिस्टम घड़ी कभी भी यादृच्छिक मशीनों के बीच इस अच्छी तरह से सहसंबद्ध नहीं होगी । तो आपको एनटीपी विषय पर कुछ भिन्नता का उपयोग करते हुए, स्वयं को सहसंबंध स्थापित करना चाहिए , संभवतः नेटवर्क बैंडविड्थ के संरक्षण के लिए आपके अन्य संदेशों में एम्बेडेड है।

मूल विचार यह हो सकता है कि जब आप दूसरी तरफ से आखिरी पैकेट प्राप्त करते हैं, तो आपने जो पैकेट भेजा था, उस समय और आपके द्वारा भेजे गए टाइमस्टैम्प के प्रत्येक पैकेट के साथ। इससे आप राउंडट्रिप की गणना करते हैं: उदाहरण के लिए यदि पैकेट क्यू कहता है कि यह 1000 पर भेजा गया था और पैकेट पी 500 पर प्राप्त हुआ था, तो आपको दिए गए पैकेट पी को 0 पर भेजा गया था और 800 पर क्यू प्राप्त कर रहा है, राउंड-ट्रिप है (800 - 0 ) - (१००० - ५००) = ३००. अस्मिता जानने का कोई तरीका नहीं है, इसलिए आप बस मान लेते हैं कि पैकेट दोनों दिशा में आधा (१५०) टिक लेता है। और वह रिमोट टाइमस्टैम्प 1000 से स्थानीय से आगे है - (800 - 150) = 350 टिक। दौर-यात्रा अलग-अलग होगी। यदि आप मानते हैं कि घड़ी यथोचित रूप से सटीक है, तो आपको सह-संबंध के दीर्घकालिक औसत का उपयोग करना चाहिए।

ध्यान दें, कि आप घड़ी के लिए सिस्टम घड़ी का उपयोग नहीं करना चाहते हैं। वे आपको ट्रैक से हटाकर, बीच में पुन: सिंक्रनाइज़ किए जा सकते हैं। आपको clock(CLOCK_MONOTONIC)यूनिक्स या GetTickCountविंडोज पर उपयोग करना चाहिए (यह सुनिश्चित नहीं करना चाहिए कि उन एपीआई को अभी जावा या पायथन में कैसे लपेटा गया है)।


नोट: SO_TIMESTAMPसॉकेट विकल्प (देखें सॉकेट (7) ott-- द्वारा उल्लिखित प्रश्न पर टिप्पणी में) पैकेट प्राप्त करने वाले इवेंट लूप की विलंबता के प्रभाव को अलग करने के लिए उपयोगी होगा। क्या यह प्रयास के लायक है यह सिर्फ इस बात पर निर्भर करता है कि आपको कितनी अच्छी सटीकता की आवश्यकता है।


1

आपको कैसे पता चलेगा कि किस खिलाड़ी की घड़ी सही है? आप नहीं करते हैं, इसलिए एक संदर्भ घड़ी का उपयोग करें ।

NTP यहाँ ओवरकिल है - आपको केवल ~ 1 सेकंड की सटीकता की आवश्यकता है - इसलिए कई घड़ी तुल्यकालन एल्गोरिदम में से किसी एक पर rdate या कुछ का उपयोग करें

आपने एक तरीका चुना है, प्रत्येक खिलाड़ी की मशीन को उस विधि के अनुसार समय लेने के लिए (उनकी प्रणाली घड़ी को बदले बिना) प्राप्त करें। यूटीसी समय और खिलाड़ियों के सिस्टम क्लॉक यूटीसी समय के बीच जो भी अंतर है, वह उनकी प्रभावी भरपाई है। किसी भी समय आप समय-संबंधी गणनाएँ जैसे कि एक्सट्रापोलेट बॉट आंदोलनों या किरण-ट्रेस बुलेट को करते हैं, आप सिस्टम समय मिलने के बाद इस ऑफसेट में कारक हैं। यूटीसी के उपयोग से समयक्षेत्र के कारकों को समाप्त किया जाएगा।


1

मेरा दूसरा कथन है कि आपको NTP का उपयोग नहीं करना चाहिए या इसके लिए सिस्टम क्लॉक के पास नहीं जाना चाहिए। यदि आप वास्तव में इस आवश्यकता की जांच करते हैं, तो आप पाएंगे कि आपको निम्नलिखित आवश्यकताएं हैं:

  • पिछले फ्रेम के बाद से कितना समय बीत चुका है ताकि आप किसी भी समय-आधारित सामान को आगे बढ़ा सकें। यह क्लाइंट और सर्वर पर अलग हो सकता है यदि दोनों अलग-अलग दरों पर टिक करते हैं (जैसे कि आप कभी-कभी सर्वर देख सकते हैं जो एक निश्चित 20 हर्ट्ज (या जो भी) पर चलते हैं लेकिन क्लाइंट को जितनी तेज़ी से चलाने की अनुमति है)।
  • वर्तमान मानचित्र शुरू हुए कितना समय बीत चुका है। यह एक शून्य-आधारित टाइमर है (बस क्लाइंट और सर्वर दोनों पर इसे शुरू करने के लिए इसे init करें) और सर्वर समय को "मास्टर" माना जाता है, इसलिए सर्वर प्रत्येक क्लाइंट के लिए ग्राहक को इस समय का वर्तमान दृश्य भेजता है जो सर्वर पर चलता है। यह वर्तमान सर्वर के समय को लेने या उस समय को घटाकर प्राप्त किया जा सकता है जिस पर सर्वर शुरू हुआ था, या ऊपर के प्रति-फ्रेम को जमा करके। क्लाइंट-साइड प्रति-फ्रेम समय का उपयोग किसी भी दो लगातार सर्वर फ्रेम के बीच प्रक्षेप बिंदु उत्पन्न करने के लिए भी किया जा सकता है।
  • एक संदर्भ "आधार समय" जिसमें से अन्य सभी समय अग्रिम; यह क्लाइंट और सर्वर दोनों पर समान हो सकता है (लेकिन सभी प्रकार के गेम के लिए इसकी आवश्यकता नहीं है) और इसे गेम (या वर्तमान मानचित्र) के प्रारंभ में प्रारंभ किया जाता है, लेकिन बाद में कभी भी नहीं बदला जाता है (जब तक कि कोई नया गेम - या नया नक्शा न हो) - शुरू हो गया)।

यह एक सरलीकृत रूपरेखा है - मैं विलंबता / गिराए गए पैकेट / आदि जैसे मुद्दों से निपटने का प्रयास नहीं करता - लेकिन यह मूल ढांचा है, जिस पर पूरी बात आधारित होनी चाहिए।

इसमें से किसी को सिस्टम घड़ी के पास जाने या अलग-अलग समय क्षेत्र जैसे मामलों से संबंधित होने की आवश्यकता नहीं है, हालांकि अंतिम आइटम वांछित समय क्षेत्र का उपयोग कर सकता है । महत्वपूर्ण बात यह है कि वास्तविक बीता हुआ समय एक उच्च-रिज़ॉल्यूशन शून्य-आधारित टाइमर का उपयोग करके मापा जाता है, इसलिए वे समय-क्षेत्र के अंतर के लिए पूरी तरह से अज्ञेय हैं। सर्वर पर वास्तविक वर्तमान समय खोजना चाहते हैं? बस इसे जोड़ने का समय बीत गया है यह संदर्भ आधार समय है और आपको मिल गया है। इसी तरह क्लाइंट के लिए।

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.