ऑब्जेक्टिव-सी के साथ iPhone पर बाहर निकलने की अवस्था में स्टोरिंग गेम स्टेट


10

ऑब्जेक्टिव-सी में लिखे गए आईफोन गेम के लिए आप अपने गेम स्टेट को बाहर कैसे स्टोर करेंगे?

जवाबों:


7

यहाँ मैं अपने खेल में इस्तेमाल किया विधि है।

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

दूसरा, सुनिश्चित करें कि आपके सभी गेम ऑब्जेक्ट को एक रूट ऑब्जेक्ट के माध्यम से एक्सेस किया जा सकता है। यह ऑब्जेक्ट पूरे खेल राज्य के लिए एक मास्टर ऑब्जेक्ट हो सकता है, उदाहरण के लिए। एक और संभावना यह है कि आप उन्हें फाउंडेशन संग्रह कक्षाओं (NSMutableArray, NSMutableSet, NSMutableDictionary) में से एक में संग्रहीत कर सकते हैं।

जब आपको सूचित किया जाता है कि आपका एप्लिकेशन पृष्ठभूमि (ApplicationDidEnterBackground) में जा रहा है, तो आपको पूरे राज्य को एक फ़ाइल में सहेजने के लिए NSKeyedArchiver का उपयोग करना होगा। वह फ़ाइल आपके आवेदन के लिए दस्तावेज़ निर्देशिका में होनी चाहिए। यहाँ यह दिखाया गया है कि कैसे किया जाता है, इसका एक सा कोड है:

NSArray *docDirectories = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *docsPath = [docDirectories objectAtIndex:0];
NSString *saveFile = [docsPath stringByAppendingPathComponent:SAVE_STATE_FILENAME];
[NSKeyedArchiver archiveRootObject:gameState toFile:saveFile;

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

एप्लिकेशन स्टार्ट अप पर, आपको फ़ाइल सहेजने के अस्तित्व की जांच करनी होगी। यदि आपके पास एक है, तो आप इसे इस तरह से लोड करते हैं:

NSArray *docDirectories = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *docsPath = [docDirectories objectAtIndex:0];
NSString *saveFile = [docsPath stringByAppendingPathComponent:SAVE_STATE_FILENAME];
[gameState release];
gameState = [[NSKeyedArchiver unarchiveObjectWithFile:saveFile] retain];

अपने डिजाइन के आधार पर, आपको गेम स्टेट के माध्यम से चलने और किसी भी संसाधन को फिर से कनेक्ट करने की आवश्यकता हो सकती है जिसे आप जारी नहीं रख सकते। यह वास्तव में इस बात पर निर्भर करता है कि आपके मॉडल कोड को कितनी सफाई से अपने रेंडरिंग कोड से अलग किया गया है।

इस बिंदु पर, आप अपने गेम को एक रुकी हुई अवस्था में रखना चाहते हैं, जो इस बात पर निर्भर करता है कि आप किस तरह का गेम बना रहे हैं।

उम्मीद है कि यह किसी और को मदद करता है जो iPhone पर गेम की बचत को लागू करने की कोशिश कर रहा है।


2

गेम स्टेट को कैसे स्टोर किया जाए यह एक जटिल सवाल है जो इस बात पर बहुत निर्भर करता है कि आप अपने गेम को कैसे सेट करते हैं।

IPhone पर विशेष रूप से, आपको उपयोगकर्ता को कार्रवाई से या अन्यथा, जब एप्लिकेशन से बाहर निकलेगा, तो पकड़ने के लिए बस -(void)applicationWillTerminate:अपने हुक में रखना UIApplicationDelegateहोगा। ओएस के पास अपना काम करने से पहले आपके पास अपना काम करने के लिए कम समय होगा, हालांकि।


2
applicationWillTerminate केवल उन अनुप्रयोगों के लिए काम करता है जो मल्टीटास्किंग या पूर्व 4.0 SDK के लिए समर्थन नहीं करते हैं। 4.0-पोस्ट कोड के साथ ApplicationDidEnterBackground का उपयोग करना बेहतर है।
डेनिस मुंसी

1

यह काफी हद तक इस बात पर निर्भर करेगा कि आपके खेल को कैसे कोडित किया गया था। क्या आप कुछ आइवर या कुछ और पर्याप्त का ट्रैक रख रहे हैं?

यदि यह सिर्फ कुछ ivars है, तो मैं शायद उन्हें पृष्ठभूमि पर एक plist लिखूंगा और स्टार्टअप पर लोड करूंगा।

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


ओएस को बंद करने के समय के साथ आप वास्तव में बहुत कुछ कर सकते हैं। मैं उस समय मेरे उत्तर में वर्णित विधि का उपयोग करके कुछ गेम ऑब्जेक्ट्स (कुछ सौ कम से कम) को जारी रखने में सक्षम था। यहां तक ​​कि धीमी 1G आइपॉड टच पर भी। खेल के प्रकार पर निर्भर करते हुए, जब एप्लिकेशन क्विट कर रहा है, लेकिन धीमी गेम खेलने की कीमत पर, CoreData समाधान बेहतर काम कर सकता है।
डेनिस मुंसी

1

ठीक उसी तरह जब आप इसे सहेजते हैं, जब उपयोगकर्ता एक गेम को बचाए बिना बाहर निकलता है।

क्या यह सवाल है कि खेल राज्य को कैसे बचाया जाए? या ऐप-एग्जिट में कुछ कैसे करें?

बाद के लिए, उत्तर है: appWillTerminate (या appWillResignActive।) iOS4 में या बाद में, आप अतिरिक्त समय (Google "iOS-4 अनुरोध अतिरिक्त समय") का अनुरोध कर सकते हैं यदि आपका सेव-गेम थोड़ी देर लेता है।

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

NSMutableDictionary *saveDict = [NSMutableDictionary dictionary];
[saveDict setValue: [NSNumber numberWithInt: currentScore] forKey: @"currentScore"];
// etc...
[saveDict writeToFile: saveFilePath atomically: YES];

यदि आप चाहते हैं, तो आप खेल पर सत्यापित करने के लिए "हस्ताक्षर" ( जैसे , md5 या समान) जोड़ सकते हैं , यह सुनिश्चित करने के लिए जारी रखें कि किसी ने धोखा देने की कोशिश करने के लिए फ़ाइल के साथ कोई छेड़छाड़ नहीं की है।


1

मैं कहूंगा कि नहीं। इसे बचाएं जब यह गेम के लिए समझ में आता है, न कि जब ऐप से बाहर निकल रहा हो। उदाहरण के लिए, यदि यह एक बारी आधारित खेल है, तो प्रत्येक मोड़ के अंत में सहेजें। यदि यह एक स्तर आधारित खेल है, तो प्रत्येक स्तर के अंत में सहेजें। इसके कुछ कारण हैं:

  • मोबाइल का उपयोग बहुत अप्रत्याशित है। हां, आप ऐप बंद होने पर iPhone एसडीके द्वारा अधिसूचित हो जाते हैं, लेकिन यह किसी भी चीज़ के बीच में हो सकता है, और संक्रमण सिर्फ "बाहर" नहीं है यह एक कॉल प्राप्त कर रहा है, एक पाठ प्राप्त कर रहा है, आदि।
  • ऐप से बाहर निकलने पर अपने गेम को बंद करने के लिए आपके पास बहुत सीमित समय और संसाधन हैं। अपने खेल को विराम देने और स्मृति को साफ करने के साथ ही इसका अधिकांश भाग संभवतः उपभोग किया जाएगा। खेल स्थिति को सहेजकर उस लोड में जोड़ने की आवश्यकता नहीं है।
  • अधिकांश खेलों में प्राकृतिक ठहराव होते हैं जो बचत के लिए मायने रखते हैं। आप गेम स्टेट को स्टोर करने के लिए इन पॉज़ का लाभ उठा सकते हैं, और उपयोगकर्ता कभी भी ध्यान नहीं देंगे कि आप अतिरिक्त संसाधनों का उपभोग कर रहे हैं।
  • खेल खेलने के दौरान आकस्मिक रूप से बचत करके, सहेजे जाने वाले डेटा की मात्रा प्रति बचत से छोटी होगी।

1

यहाँ कुछ उदाहरण "मानचित्र" और "खिलाड़ी" कक्षाओं के लिए NSCoding प्रोटोकॉल को लागू करने का एक उदाहरण दिया गया है:

http://deadpanic.com/howtosave

तब आप डेनिस 'NSKeyedArchiver विधि का उपयोग करके ऑब्जेक्ट्स को बचा सकते हैं।

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