फ्रैगमेंट के सेटट्रैनइन्स्टेंस (बूलियन) को समझना


341

प्रलेखन के साथ शुरू:

सार्वजनिक शून्य सेटटैनइन इनस्टेंस (बूलियन रिटेन)

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

  • onDestroy () नहीं कहा जाएगा (लेकिन onDetach () अभी भी होगा, क्योंकि टुकड़ा अपनी वर्तमान गतिविधि से अलग हो रहा है)।
  • onCreate (बंडल) को तब से नहीं बुलाया जाएगा क्योंकि टुकड़ा फिर से नहीं बनाया जा रहा है।
  • onAttach (गतिविधि) और onActivityCreated (बंडल) अभी भी कहा जाएगा।

मेरे कुछ सवाल है:

  • क्या टुकड़ा भी अपने दृष्टिकोण को बनाए रखता है, या इसे कॉन्फ़िगरेशन परिवर्तन पर फिर से बनाया जाएगा? वास्तव में "बरकरार" का क्या मतलब है?

  • जब उपयोगकर्ता गतिविधि छोड़ देता है तो क्या टुकड़ा नष्ट हो जाएगा?

  • यह बैक स्टैक पर टुकड़ों के साथ काम क्यों नहीं करता है?

  • वे कौन से उपयोग मामले हैं जहां यह इस पद्धति का उपयोग करने के लिए समझ में आता है?


4
अच्छी जानकारी के साथ इसी तरह का सवाल: क्यों Fragment # setRetainInstance (बूलियन) का उपयोग करें?
रिचर्ड ले मेसियर

जवाबों:


348

सबसे पहले, मेरी पोस्ट की जाँच करें पर बनाए हुए टुकड़े। यह मदद कर सकता है।

अब आपके सवालों के जवाब देने के लिए:

टुकड़ा भी अपने को बनाए रखने करता है दृश्य राज्य, या इस विन्यास परिवर्तन पर निर्मित किया जाएगा - वास्तव में क्या है "को बनाए रखा?"

हां, Fragmentकॉन्फ़िगरेशन परिवर्तन के दौरान राज्य को बरकरार रखा जाएगा। विशेष रूप से, "बरकरार" का अर्थ है कि कॉन्फ़िगरेशन परिवर्तनों पर टुकड़ा नष्ट नहीं होगा । यही कारण है, Fragmentहो जाएगा बनाए रखा , भले ही विन्यास परिवर्तन अंतर्निहित कारणों Activityनष्ट हो।

जब उपयोगकर्ता गतिविधि छोड़ देता है तो क्या टुकड़ा नष्ट हो जाएगा?

स्मृति संसाधन कम होने पर सिस्टम की तरह Activitys Fragmentनष्ट हो सकता है। चाहे आपके पास आपके टुकड़े हों, अपनी आवृत्ति स्थिति को बनाए रखने के लिए कॉन्फ़िगरेशन परिवर्तन भर में कोई प्रभाव नहीं पड़ेगा कि क्या सिस्टम Fragmentआपके द्वारा छोड़ने के बाद एस को नष्ट कर देगा या नहीं Activity। यदि आप Activity(यानी होम बटन दबाकर) छोड़ देते हैं , तो Fragmentएस नष्ट हो सकता है या नहीं। यदि आप Activityबैक बटन दबाकर छोड़ते हैं (इस प्रकार, कॉलिंग finish()और प्रभावी रूप से नष्ट करने के लिए Activity), तो सभी Activityसंलग्न Fragmentएस भी नष्ट हो जाएंगे।

यह बैक स्टैक पर टुकड़ों के साथ काम क्यों नहीं करता है?

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

वे कौन से उपयोग मामले हैं जहां यह इस पद्धति का उपयोग करने के लिए समझ में आता है?

राज्य की सूचनाओं को फैलाने के लिए, विशेष रूप से थ्रेड प्रबंधन - गतिविधि के उदाहरणों में, सेवानिवृत्त टुकड़े काफी उपयोगी हो सकते हैं। उदाहरण के लिए, एक टुकड़ा एक मेजबान के रूप में Threadया AsyncTaskइसके संचालन के प्रबंधन के लिए सेवा कर सकता है । देखें मेरे ब्लॉग पोस्ट में अधिक जानकारी के लिए इस विषय पर।

सामान्य तौर पर, मैं इसके onConfigurationChangedसाथ उपयोग करने के लिए उसी तरह का व्यवहार करूंगा Activity... इसे केवल एक बंद के रूप में उपयोग न करें क्योंकि आप उन्मुखीकरण परिवर्तन को सही ढंग से लागू करने / संभालने के लिए बहुत आलसी हैं। जरूरत पड़ने पर ही इसका इस्तेमाल करें।


37
देखें वस्तुओं को बनाए नहीं रखा जाता है, वे हमेशा कॉन्फ़िगरेशन परिवर्तनों पर नष्ट हो जाते हैं।
मार्कस जुंगिंगर

103
जहां तक ​​मैं बता सकता हूं, यदि आपके पास setRetainInstance(true), Fragmentजावा ऑब्जेक्ट, और इसकी सभी सामग्री रोटेशन पर नष्ट नहीं हुई है , लेकिन दृश्य फिर से बनाया गया है। उसको onCreatedView()फिर कहा जाता है। यह मूल रूप से वह तरीका है जिसके साथ Activitiesएंड्रॉइड 1.0 के बाद से काम करना चाहिए था । मुझे नहीं लगता कि इसका उपयोग करना "आलसी" है, या इसका उपयोग करना "उचित" नहीं है। वास्तव में मैं यह नहीं देख सकता कि यह डिफ़ॉल्ट क्यों नहीं है, या आप इसे कभी क्यों चाहते हैं।
टिम्मम

24
मुझे लगता है कि "यह बैक स्टैक पर टुकड़ों के साथ काम क्यों नहीं करता है?" समझना मुश्किल। लेकिन शायद मैं गूंगा हूं :(
HGPB

13
@ डिएरे एक गतिविधि को कई तरीकों से नष्ट किया जा सकता है। उदाहरण के लिए, यदि आप "बैक" पर क्लिक करते हैं, तो गतिविधि नष्ट हो जाएगी। यदि आप "घर" पर क्लिक करते हैं, तो गतिविधि को रोक दिया जाएगा और मेमोरी कम होने पर भविष्य में कुछ समय नष्ट किया जा सकता है। रिटायर्ड Fragments केवल कॉन्फ़िगरेशन परिवर्तनों के दौरान बनाए रखा जाता है, जहां अंतर्निहित गतिविधि को नष्ट कर दिया जाता है और तुरंत फिर से बनाया जाता है। अन्य सभी मामलों में, जिसमें गतिविधि नष्ट हो जाती है, बरकरार टुकड़ों को भी नष्ट कर दिया जाएगा।
एलेक्स लॉकवुड

3
@AlexLockwood आप निम्नलिखित की पुष्टि कर सकते हैं: भले ही setRetainInstance(true)उपयोग किया जाता है, एक को अभी भी सभी परिदृश्यों को संभालने में सक्षम होने के लिए अपनी खुद की दृढ़ता ( या अन्यथा) को लागू savedInstanceStateकरना होगा: जैसे "घर की चाबी, घुमाएं, वापस ऐप करें" के साथ मेरे टुकड़े को फिर से बनाता है। कॉल, सभी राज्य चर खो। मेरे पास एक AsyncTaskसदस्य के रूप में परिवर्तनशील है, इसीलिए मैं चाहता हूं कि अब, यदि मैं यह काम करना चाहता हूं, तो मुझे उपयोगकर्ता को वापस आने पर कार्य को रोकने, राज्य को बचाने और फिर से शुरू करने के लिए मजबूर किया जाएगा। तो सब के सब, यह रोटेशन के साथ मदद करने के लिए सिर्फ एक त्वरित तरीका है, लेकिन अन्यथा सामान्य रूप से बेकार है।
ट्वीस्टरेब

28

setRetaininstanceकेवल तब उपयोगी होता है जब आपके activityकॉन्फ़िगरेशन में बदलाव के कारण नष्ट हो जाता है और फिर से बनाया जाता है क्योंकि कॉल के दौरान इंस्टेंस सहेजे जाते हैं onRetainNonConfigurationInstance। यही है, यदि आप डिवाइस को घुमाते हैं, तो बनाए हुए टुकड़े वहां बने रहेंगे (वे नष्ट नहीं किए गए और पुनः बनाए गए हैं।) लेकिन जब रनटाइम संसाधनों को पुनः प्राप्त करने के लिए गतिविधि को मारता है, तो कुछ भी नहीं बचा है। जब आप बैक बटन दबाते हैं और गतिविधि से बाहर निकलते हैं, तो सब कुछ नष्ट हो जाता है।

आमतौर पर मैं इस फंक्शन को सेव्ड ओरिएंटेशन चेंजिंग टाइम के लिए उपयोग करता हूं। जब मैंने सर्वर से बिटमैप्स का एक गुच्छा डाउनलोड किया है और प्रत्येक 1MB है, जब उपयोगकर्ता गलती से अपने डिवाइस को घुमाता है, तो मैं निश्चित रूप से फिर से सभी डाउनलोड काम नहीं करना चाहता हूं। मैं Fragmentअपने बिटमैप को एक होल्डिंग बनाता हूं और इसे मैनेजर में जोड़ता हूं और कॉल करता हूं setRetainInstance, सभी बिटमैप अभी भी हैं, भले ही स्क्रीन ओरिएंटेशन बदल जाए।


क्या आप "डेटा-ओनली" अंश (बिना किसी विजेट के) सिर्फ बिटमैप्स के लिए धारक के रूप में बनाते हैं या क्या उन अंशों के विजेट भी हो सकते हैं? मैंने स्मृति लीक के निर्माण के खतरे के बारे में कुछ पढ़ा है जब टुकड़े में संदर्भ / गतिविधि से संबंधित कुछ होता है ...
hgoebl

आपके लिए mActivityसंदर्भ स्पष्ट हो जाएगा । लेकिन मुझे नहीं पता कि क्या रनटाइम इस मामले में भी विखंडन के उदाहरण को स्पष्ट करेगा। कृपया इसे आज़माएं या स्रोत कोड में गोता लगाएँ।
सुइतिषी

जब हम setRainaininstance का उपयोग कर सकते हैं, इसका अच्छा उदाहरण
म्यू Sa

12

SetRetainInstance (सत्य) टुकड़े के जीवित रहने की अनुमति देता है। इसके सदस्यों को रोटेशन की तरह कॉन्फ़िगरेशन परिवर्तन के दौरान बनाए रखा जाएगा। लेकिन यह तब भी मारा जा सकता है जब गतिविधि पृष्ठभूमि में मार दी जाती है। यदि बैकग्राउंड में मौजूद गतिविधि सिस्टम द्वारा मार दी जाती है, तो यह instState को आपके द्वारा onSaveInstanceState को ठीक से संभाले सिस्टम द्वारा सहेजा जाना चाहिए। दूसरे शब्द में onSaveInstanceState को हमेशा कहा जाएगा। हालांकि OnCreateView को कॉल नहीं किया जाएगा, अगर SetRetainInstance सही है और टुकड़ा / गतिविधि अभी तक नहीं मारी गई है, फिर भी यह कहा जाएगा कि अगर इसे मार दिया गया और वापस लाने की कोशिश की जा रही है।

यहाँ Android गतिविधि / टुकड़े की आशा है कि यह मदद करता है के कुछ विश्लेषण हैं http://ideaventure.blogspot.com.au/2014/01/android-activityfragment-life-cycle.html


8
मैं निश्चित रूप से onCreateView को स्क्रीन को घुमाते समय फिर से बनाए गए टुकड़े पर बुलाया जा रहा हूं।
ऐज

क्या यह लिंक आपका अपना ब्लॉग है? यदि ऐसा है तो आपको यह स्पष्ट करना चाहिए।
फ्लेक्सो

4

setRetainInstance () - पदावनत

टुकड़े संस्करण 1.3.0-अल्फा 01 के रूप में

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


2

setRetainInstance (बूलियन) उपयोगी है जब आप कुछ घटक रखना चाहते हैं जो कि गतिविधि जीवनचक्र से बंधा नहीं है। इस तकनीक का उपयोग उदाहरण के लिए rxloader द्वारा "rxjava के ऑब्जर्वेबल के लिए एंड्रॉइड की गतिविधि जीवन शैली को संभालने के लिए किया जाता है" (जो मैंने यहां पाया है )।

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