वेब पर एक टाइल मानचित्र को कुशलतापूर्वक कैसे संग्रहीत और प्रदर्शित करें?


9

के बारे में

ये वास्तव में एक में दो प्रश्न हैं। सबसे पहले मैं बड़ी मात्रा में टाइल डेटा को कुशलतापूर्वक संग्रहीत करने का एक तरीका ढूंढ रहा हूं। अन्य पहलू डेटा सेट की क्वेरी करने और टाइल्स प्रदर्शित करने से संबंधित है। पहले आपको कुछ बैकग्राउंड देता हूं।

हम एक ब्राउज़र आधारित मल्टीप्लेयर टाइकून खेल बना रहे हैं जो कैनवस को प्रस्तुत करने के लिए CraftyJS लाइब्रेरी का उपयोग कर रहा है। GUI की पृष्ठभूमि में हम PHP पर Yii फ्रेमवर्क चला रहे हैं और यह सभी पायथन रैंडम मैप जनरेटर और गेम इंजन से जुड़ता है।

यह पहला रफ़ मैप रेंडर कैसा दिखता है: http://i.imgur.com/khAXtl.png

मानचित्र डेटा संग्रहीत करना

खेल शुरू होने पर हर बार खेल की दुनिया बेतरतीब ढंग से उत्पन्न होती है। प्रत्येक खिलाड़ी के लिए आकार 100x100 हेक्सागोनल टाइल्स है। इसका मतलब है कि तीन खिलाड़ी खेल के लिए, 90.000 टाइल बनाई गई हैं। वर्तमान में मैं सिर्फ एक जावास्क्रिप्ट सरणी बनाता हूं जिससे मैं मानचित्र प्रस्तुत करता हूं।

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

नक्शा प्रदर्शित करना

एक और समस्या जो मुझे दिख रही है वह है मानचित्र के आसपास घूमना। वर्तमान में मैं प्रत्येक टाइल के लिए चालाक इकाइयां बना रहा हूं, भले ही यह व्यूपोर्ट में न हो। यह धीमा है, क्योंकि भले ही Crafty व्यूपोर्ट में केवल रेंडर करता है, यह स्टोर करता है और संभवतः प्रत्येक रेंडर इवेंट पर सभी टाइलों के माध्यम से पुनरावृत्त करता है। वर्तमान में मेरे पास एक खींचा हुआ जेनरेट किया गया नक्शा है, जो जब आप घूमते हैं तो लोड करने और रुकने में बहुत धीमा होता है, अब मैं इसे खेलने योग्य बनाना चाहूंगा।

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

नक्शे से निर्बाध प्रदर्शन प्राप्त करने का तरीका एक बड़ी मात्रा में टाइलों को एक जावास्क्रिप्ट सरणी में प्रीलोड करना और कैश के रूप में उपयोग करना हो सकता है। खिलाड़ी के पास कुछ स्क्रीन "कैश्ड" होती हैं और जब वह व्यूपोर्ट ले जाता है, तो मैं JS "कैश" पर अधिक टाइल लोड करूँगा।

क्या मैं सही दिशा में चल रहा हूं? मैं किसी ऐसे व्यक्ति से कुछ और जानकारी प्राप्त करना पसंद करूँगा जिसने कुछ ऐसा ही किया है। मैं खेल विकास के लिए नया हूं, लेकिन पिछले कुछ हफ्तों से बहुत सारे स्रोतों से गुजर रहा हूं।


1
मुझे आश्चर्य है कि आपने MySQL को एक अड़चन के रूप में पहचाना। आपने इस निष्कर्ष पर पहुंचने के लिए क्या परीक्षण किया कि यह चीजों को धीमा कर रहा है?
बंमज़ैक 8

@bummzack यदि उसके पास प्रति टाइल एक पंक्ति है, तो मैं शायद ही देख सकता हूं कि चीजें कैसे धीमी नहीं हो सकती हैं।
--२

1
@eBusiness एक DB से कुछ हज़ार पंक्तियों को छोड़ना वास्तव में एक समस्या नहीं होनी चाहिए। यह अभी भी कुछ मिलीसेकंड की सीमा में होना चाहिए। इसके अलावा यह 90'000 पंक्तियाँ नहीं होगी, बल्कि 3 खिलाड़ियों (100x100 प्रति खिलाड़ी) के लिए 30'000 पंक्तियाँ होंगी।
बुमज़ैक

भ्रमित करने वाले गणित के लिए खेद है, खिलाड़ी क्षेत्र के अलावा खिलाड़ियों के बीच भी दोगुना स्थान है ताकि वे एक दूसरे से समान दूरी पर हों, जिससे यह 90k हो। क्वेरी करना कोई समस्या नहीं है। 90k टाइलों का चयन करना और एक मानचित्र बनाना है। लेकिन यह एक अच्छा तरीका नहीं है। विस्तृत जानकारी के लिए अनुरोध किए जाने पर मैं मैप डेटा को क्रमबद्ध करूँगा और डीबी में टाइल्स का उपयोग करूंगा।
तत्व

जवाबों:


2

गेमप्ले
सबसे पहले मैं आपसे पूछना चाहता हूं, क्या आपको वास्तव में प्रति खिलाड़ी 10000 टाइल की आवश्यकता है? हालांकि मुझे नहीं पता कि आप किस तरह का खेल बना रहे हैं, यह आमतौर पर सच है कि बड़े नक्शे लंबे खेल बनाते हैं। सिविलाइज़ेशन 5 में सबसे बड़ा नक्शा 10240 टाइलों का है, और यह केवल सॉर्ट काम करता है क्योंकि आपको इसके कुछ अंश से अधिक खेलने की आवश्यकता नहीं है।

डेटाबेस
आपको इस तरह के एक डेटाबेस से गेम चलाने की कोशिश नहीं करनी चाहिए, आपको डेटा को एप्लिकेशन मेमोरी में रखने की आवश्यकता है। आप खेल का बैकअप लेने के लिए डेटाबेस का उपयोग कर सकते हैं। पूर्ण बैकअप के लिए गेम डेटा की एक क्रमबद्धता को सहेजें, और फिर आप दिए गए आदेशों को सहेजकर इसे बढ़ा सकते हैं और फिर यदि बैकअप की आवश्यकता हो तो उन्हें फिर से चलाएँ।

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

जावास्क्रिप्ट विज़ुअलाइज़ेशन
जबकि मैं यह नहीं कहूंगा कि आपको आवश्यक रूप से कैनवास का उपयोग नहीं करना चाहिए, आपको वास्तव में इस तरह से सामान की आवश्यकता नहीं है। इसे सभी img तत्वों के एक समूह के रूप में सेट करें, और नक्शे के विभिन्न हिस्सों को प्रदर्शित करने के लिए src संपत्ति को बदलें।

प्रो टिप
वैसे, कभी-कभी पूरे मानचित्र को साझा करने की तुलना में इसे उत्पन्न करने के लिए उपयोग किए गए बीज को साझा करना आसान होता है।


+1, लेकिन दुख की बात है कि PHP में लिखा गया एक वेब-ऐप आमतौर पर स्मृति में गेम-स्टेट रखने का कोई साधन नहीं है।
बुमज़ैक 8

@bummzack, आह, ठीक है, मुझे लगता है कि मैंने किसी तरह PHP शब्द को छोड़ दिया और सिर्फ पायथन पढ़ा। तब बैकएंड फ्रेमवर्क का एक परिवर्तन क्रम में हो सकता है। Node.js एक विकल्प हो सकता है।
आषाढ़

मैं एक प्रतिस्पर्धी परिवहन टाइकून का निर्माण कर रहा हूं, OpenTTD के बारे में सोचें, 512x512 (262k) के आकार का एक नक्शा कुछ खिलाड़ियों के लिए उतना बड़ा नहीं है। मुझे एहसास है कि यह महत्वाकांक्षी है, लेकिन अगर नक्शा इतना बड़ा नहीं है, तो खेल बहुत जल्द खत्म हो जाएगा। क्योंकि यह एक मल्टीप्लेयर गेम है, मुझे खिलाड़ियों के बीच के नक्शे में बदलाव को सिंक करना होगा। मेरी पहली वृत्ति सिर्फ वेब विकास से जाने वाली अवधारणाओं का उपयोग करने और डेटाबेस के साथ जाने की थी। यह सुपर realtime होने की जरूरत नहीं है। मैं जेएस विज़ुअलाइज़ेशन के साथ जा रहा हूं, क्योंकि मैं नक्शे पर गतिशील सामान रखना चाहता हूं।
तत्व

कुछ बिंदुओं पर मेरे जवाब पर विचार करें, अंत में आपको प्रदर्शन स्वयं करना होगा, यह एक गंभीर मुद्दा है, और आपको कुछ समझौते करने पड़ सकते हैं।
आआआआआ आआआआआआआआआआआ

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

1

MySQL धीमा नहीं है। सबसे अधिक संभावना है कि आप भोले प्रश्नों का प्रदर्शन कर रहे हैं या उप-इष्टतम इंडेक्स हैं। NoSQL दृष्टिकोण MongoDB की तरह तेज हो सकता है, शायद नहीं। आपका एक्सेस पैटर्न और क्वेरी का विकल्प यहां वास्तव में मायने रखता है। प्रदर्शन में सुधार करने के बारे में सलाह देना संभव है, लेकिन यह देखे बिना कि आप पहले से क्या कर रहे हैं।

नक्शे से निर्बाध प्रदर्शन प्राप्त करने का तरीका एक बड़ी मात्रा में टाइलों को एक जावास्क्रिप्ट सरणी में प्रीलोड करना और कैश के रूप में उपयोग करना हो सकता है।

हां बिल्कुल। यहां जोड़ने के लिए बहुत कुछ नहीं है - क्लाइंट सर्वर से टाइल के लिए पूछता है, इसलिए आपको बस यह सुनिश्चित करना होगा कि जो आप पूछते हैं वह स्क्रीन से बड़ा क्षेत्र कवर करता है।

परिशिष्ट:

हम PHP पर Yii फ्रेमवर्क चला रहे हैं और यह सभी पायथन रैंडम मैप जनरेटर और गेम इंजन से जुड़ता है।

यदि आप अजगर के साथ सक्षम हैं तो मैं सलाह दूंगा कि आप PHP बिचौलिए को खाई। यदि आप अपने गेम को पायथन प्रक्रिया के रूप में चलाते हैं तो आप अपने टाइल डेटा को अधिक आसानी से मेमोरी में रख सकते हैं और MySQL एक्सेस को काफी कम कर सकते हैं। यह मदद करता है कि पायथन पीएचपी की तुलना में बहुत अधिक पवित्र भाषा है, भी।

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