राज्य के मालिक और यूज़र इंटरफ़ेस (यूआई) की स्थिति

यूज़र इंटरफ़ेस (यूआई) लेयर गाइड में, यूनिडायरेक्शनल डेटा फ़्लो (यूडीएफ़) के बारे में बताया गया है. यूज़र इंटरफ़ेस (यूआई) लेयर के लिए, यूज़र इंटरफ़ेस (यूआई) की स्थिति बनाना और उसे मैनेज करना.

डेटा, डेटा लेयर से यूज़र इंटरफ़ेस (यूआई) पर एकतरफ़ा तरीके से फ़्लो करता है.
पहली इमेज: एकतरफ़ा डेटा फ़्लो

इसमें यह भी बताया गया है कि यूडीएफ़ मैनेजमेंट की सेवा किसी खास क्लास को देने के क्या फ़ायदे हैं स्टेट होल्डर कहा जाता है. राज्य धारक को इनमें से किसी एक के ज़रिए लागू किया जा सकता है ViewModel या सादा क्लास. इस दस्तावेज़ में, मौजूदा स्थिति की बारीकी से जांच की गई है धारक और यूज़र इंटरफ़ेस (यूआई) लेयर में उनकी भूमिका.

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

  • यूज़र इंटरफ़ेस (यूआई) लेयर में मौजूद यूआई स्टेट के टाइप को समझना.
  • यूज़र इंटरफ़ेस (यूआई) लेयर में, उन यूज़र इंटरफ़ेस (यूआई) स्थितियों पर काम करने वाले लॉजिक के टाइप को समझें.
  • यह जानें कि राज्य धारक के उचित कार्यान्वयन को कैसे चुना जाए, जैसे कि ViewModel या सामान्य क्लास.

यूज़र इंटरफ़ेस (यूआई) स्टेट प्रोडक्शन पाइपलाइन के एलिमेंट

यूज़र इंटरफ़ेस (यूआई) की स्थिति और इसे बनाने वाला लॉजिक, यूज़र इंटरफ़ेस (यूआई) लेयर को तय करता है.

यूज़र इंटरफ़ेस (यूआई) की स्थिति

यूज़र इंटरफ़ेस (यूआई) की स्थिति वह प्रॉपर्टी है जो यूज़र इंटरफ़ेस (यूआई) की जानकारी देती है. यूज़र इंटरफ़ेस (यूआई) दो तरह के होते हैं राज्य:

  • स्क्रीन के यूज़र इंटरफ़ेस (यूआई) की स्थिति: इसका मतलब है कि आपको स्क्रीन पर क्या दिखाना है. उदाहरण के लिए, NewsUiState क्लास में ज़रूरी समाचार और अन्य जानकारी शामिल हो सकती है का इस्तेमाल करें. यह स्थिति आम तौर पर क्योंकि इसमें ऐप्लिकेशन का डेटा शामिल है.
  • यूज़र इंटरफ़ेस (यूआई) एलिमेंट की स्थिति, यूज़र इंटरफ़ेस (यूआई) एलिमेंट से जुड़ी प्रॉपर्टी के बारे में बताती है और उन्हें रेंडर करने के तरीके पर असर डाल सकते हैं. यूज़र इंटरफ़ेस (यूआई) एलिमेंट दिखाया या छिपाया जा सकता है और फ़ॉन्ट, साइज़ या फ़ॉन्ट के लिए एक तय रंग होना चाहिए. Android व्यू में, व्यू इस स्थिति को खुद प्रबंधित करती है, क्योंकि यह स्वाभाविक रूप से राज्य से जुड़ी होती है. साथ ही, इसकी स्थिति में बदलाव करें या उसके बारे में क्वेरी करें. उदाहरण के लिए, get और TextView क्लास के टेक्स्ट के लिए set तरीके. Jetpack में कंपोज़ेबल में कंपोज़ की गई स्थिति से बाहर का रास्ता होता है और उसे इधर-उधर ले जाया जा सकता है यह कॉम्पोनेंट, कंपोज़ेबल के आस-पास मौजूद नहीं है फ़ंक्शन या स्टेट होल्डर के रूप में दी जाती है. इसका एक उदाहरण ScaffoldState है, जिसमें Scaffold कंपोज़ेबल.

तर्क वाले गेम

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

लॉजिक, यूज़र इंटरफ़ेस (यूआई) स्टेट जनरेट करता है
दूसरी इमेज: यूज़र इंटरफ़ेस (यूआई) स्टेट के प्रोड्यूसर के तौर पर लॉजिक

किसी ऐप्लिकेशन में लॉजिक, बिज़नेस लॉजिक या यूज़र इंटरफ़ेस (यूआई) लॉजिक हो सकता है:

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

Android लाइफ़साइकल और यूज़र इंटरफ़ेस (यूआई) की स्थिति और लॉजिक

यूज़र इंटरफ़ेस (यूआई) लेयर के दो हिस्से होते हैं: एक डिपेंडेंट और दूसरा यूज़र इंटरफ़ेस (यूआई) से अलग लाइफ़साइकल. डेटा सोर्स को अलग-अलग करने से, हर पार्ट के लिए उपलब्ध डेटा सोर्स तय होते हैं, और इसलिए, अलग-अलग तरह के यूज़र इंटरफ़ेस (यूआई) की स्थिति और लॉजिक की ज़रूरत होती है.

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

ऊपर दी गई टेबल की मदद से, इस बारे में खास जानकारी दी जा सकती है:

यूज़र इंटरफ़ेस (यूआई) अलग-अलग लाइफ़साइकल यूज़र इंटरफ़ेस (यूआई) लाइफ़साइकल डिपेंडेंट
बिज़नेस लॉजिक यूज़र इंटरफ़ेस (यूआई) लॉजिक
स्क्रीन यूज़र इंटरफ़ेस (यूआई) की स्थिति

यूज़र इंटरफ़ेस (यूआई) स्टेट प्रोडक्शन पाइपलाइन

यूज़र इंटरफ़ेस (यूआई) स्टेट प्रोडक्शन पाइपलाइन से, यूज़र इंटरफ़ेस (यूआई) बनाने के चरणों के बारे में पता चलता है राज्य. इन चरणों में, अलग-अलग तरह के लॉजिक को लागू किया जाता है और पूरी तरह से आपके यूज़र इंटरफ़ेस (यूआई) की ज़रूरतों पर निर्भर करते हैं. कुछ यूज़र इंटरफ़ेस (यूआई) यूआई लाइफ़साइकल इंडिपेंडेंट और यूज़र इंटरफ़ेस (यूआई) लाइफ़साइकल डिपेंडेंट, दोनों हिस्सों का फ़ायदा पाएं को भी शामिल कर सकता है.

इसका मतलब है कि यूज़र इंटरफ़ेस (यूआई) लेयर पाइपलाइन के नीचे दिए गए क्रमचय मान्य हैं:

  • यूज़र इंटरफ़ेस (यूआई) की स्थिति, जिसे यूज़र इंटरफ़ेस (यूआई) से ही बनाया और मैनेज किया जाता है. उदाहरण के लिए, आसान, फिर से इस्तेमाल किया जा सकने वाला बेसिक काउंटर:

    @Composable
    fun Counter() {
        // The UI state is managed by the UI itself
        var count by remember { mutableStateOf(0) }
        Row {
            Button(onClick = { ++count }) {
                Text(text = "Increment")
            }
            Button(onClick = { --count }) {
                Text(text = "Decrement")
            }
        }
    }
    
  • यूज़र इंटरफ़ेस (यूआई) लॉजिक → यूज़र इंटरफ़ेस (यूआई). उदाहरण के लिए, ऐसा बटन दिखाना या छिपाना जिसकी मदद से उपयोगकर्ता सूची में सबसे ऊपर जाने के लिए.

    @Composable
    fun ContactsList(contacts: List<Contact>) {
        val listState = rememberLazyListState()
        val isAtTopOfList by remember {
            derivedStateOf {
                listState.firstVisibleItemIndex < 3
            }
        }
    
        // Create the LazyColumn with the lazyListState
        ...
    
        // Show or hide the button (UI logic) based on the list scroll position
        AnimatedVisibility(visible = !isAtTopOfList) {
            ScrollToTopButton()
        }
    }
    
  • बिज़नेस लॉजिक → यूज़र इंटरफ़ेस (यूआई). यूज़र इंटरफ़ेस (यूआई) एलिमेंट, जिसमें मौजूदा उपयोगकर्ता की फ़ोटो दिख रही है स्क्रीन.

    @Composable
    fun UserProfileScreen(viewModel: UserProfileViewModel = hiltViewModel()) {
        // Read screen UI state from the business logic state holder
        val uiState by viewModel.uiState.collectAsStateWithLifecycle()
    
        // Call on the UserAvatar Composable to display the photo
        UserAvatar(picture = uiState.profilePicture)
    }
    
  • बिज़नेस लॉजिक → यूज़र इंटरफ़ेस (यूआई) लॉजिक → यूज़र इंटरफ़ेस (यूआई). एक यूज़र इंटरफ़ेस (यूआई) एलिमेंट जो दी गई यूज़र इंटरफ़ेस (यूआई) स्थिति के लिए, स्क्रीन पर सही जानकारी दिखाता है.

    @Composable
    fun ContactsList(viewModel: ContactsViewModel = hiltViewModel()) {
        // Read screen UI state from the business logic state holder
        val uiState by viewModel.uiState.collectAsStateWithLifecycle()
        val contacts = uiState.contacts
        val deepLinkedContact = uiState.deepLinkedContact
    
        val listState = rememberLazyListState()
    
        // Create the LazyColumn with the lazyListState
        ...
    
        // Perform UI logic that depends on information from business logic
        if (deepLinkedContact != null && contacts.isNotEmpty()) {
            LaunchedEffect(listState, deepLinkedContact, contacts) {
                val deepLinkedContactIndex = contacts.indexOf(deepLinkedContact)
                if (deepLinkedContactIndex >= 0) {
                  // Scroll to deep linked item
                  listState.animateScrollToItem(deepLinkedContactIndex)
                }
            }
        }
    }
    

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

डेटा बनाने वाली लेयर से यूज़र इंटरफ़ेस (यूआई) में डेटा फ़्लो
तीसरी इमेज: यूज़र इंटरफ़ेस (यूआई) लेयर में लॉजिक का इस्तेमाल करना

राज्य के मालिक और उनकी ज़िम्मेदारियां

राज्य के मालिक की ज़िम्मेदारी है कि वह राज्य को सेव करे, ताकि ऐप्लिकेशन उसे पढ़ सके. ऐसे मामलों में जहां तर्क की ज़रूरत होती है, यह एक मध्यस्थ के तौर पर काम करता है और सभी ज़रूरी लॉजिक को होस्ट करने वाले डेटा सोर्स से लिंक किए जा सकते हैं. इस तरह, राज्य धारक सही डेटा सोर्स को लॉजिक असाइन करता है.

इससे ये फ़ायदे मिलते हैं:

  • सरल यूज़र इंटरफ़ेस (यूआई): यूज़र इंटरफ़ेस (यूआई) सिर्फ़ अपनी स्थिति को बाइंड करता है.
  • मैनेजमेंट के हिसाब से सही होना: स्टेट होल्डर में बताए गए लॉजिक को दोहराया जा सकता है वह भी बिना यूज़र इंटरफ़ेस (यूआई) में बदलाव किए.
  • टेस्टेबिलिटी: यूज़र इंटरफ़ेस (यूआई) और इसके स्टेट प्रोडक्शन लॉजिक की जांच की जा सकती है स्वतंत्र रूप से काम करता है.
  • पढ़ने का बेहतर अनुभव: कोड पढ़ने वाले लोगों को यूज़र इंटरफ़ेस (यूआई) के बीच का अंतर साफ़ तौर पर दिख सकता है प्रज़ेंटेशन कोड और यूज़र इंटरफ़ेस (यूआई) स्टेट प्रोडक्शन कोड.

अपने साइज़ या दायरे पर ध्यान दिए बिना, हर यूज़र इंटरफ़ेस (यूआई) एलिमेंट का 1:1 संबंध उसके हिसाब से राज्य हो सकता है. इसके अलावा, राज्य धारक के पास उपयोगकर्ता की ऐसी किसी भी कार्रवाई को स्वीकार और प्रोसेस करना जिसकी वजह से यूज़र इंटरफ़ेस (यूआई) की स्थिति में बदलाव हो सकता है और अगले राज्य में होने वाले बदलाव के बारे में बताना चाहिए.

राज्य के मालिकों के टाइप

यूज़र इंटरफ़ेस (यूआई) की स्थिति और लॉजिक की तरह ही, दो तरह के राज्य हो सकते हैं यूज़र इंटरफ़ेस (यूआई) लेयर में:

  • बिज़नेस लॉजिक स्टेट होल्डर.
  • यूज़र इंटरफ़ेस (यूआई) लॉजिक स्टेट होल्डर.

नीचे दिए सेक्शन में, राज्य सरकार से अलग-अलग तरह के लोगों के बारे में जानकारी हासिल की गई है. जिसकी शुरुआत बिज़नेस लॉजिक स्टेट होल्डर से होगी.

बिज़नेस लॉजिक और उसका स्टेट होल्डर

बिज़नेस लॉजिक स्टेट होल्डर, उपयोगकर्ता इवेंट को प्रोसेस करते हैं और डेटा या डोमेन से डेटा बदलते हैं लेयर पर टैप करें. बेहतरीन उपयोगकर्ता अनुभव देने के लिए, जब Android लाइफ़साइकल और ऐप्लिकेशन के कॉन्फ़िगरेशन में हुए बदलावों को ध्यान में रखते हुए, स्टेट होल्डर जो कारोबारी लॉजिक का इस्तेमाल करते हैं उनकी प्रॉपर्टी में ये प्रॉपर्टी होनी चाहिए:

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

उदाहरण के लिए "अभी में Android" ऐप्लिकेशन:

Android में Now ऐप्लिकेशन से पता चलता है कि किसी मुख्य ऐप्लिकेशन फ़ंक्शन को दिखाने वाले नेविगेशन डेस्टिनेशन का
अपना यूनीक बिज़नेस लॉजिक स्टेट होल्डर है.
चौथी इमेज: Android ऐप्लिकेशन में Now

बिज़नेस लॉजिक स्टेट होल्डर के तौर पर काम करने से, इस मामले में, AuthorViewModel यूज़र इंटरफ़ेस (यूआई) की स्थिति दिखाता है:

@HiltViewModel
class AuthorViewModel @Inject constructor(
    savedStateHandle: SavedStateHandle,
    private val authorsRepository: AuthorsRepository,
    newsRepository: NewsRepository
) : ViewModel() {

    val uiState: StateFlow<AuthorScreenUiState> = …

    // Business logic
    fun followAuthor(followed: Boolean) {
      …
    }
}

ध्यान दें कि AuthorViewModel में पहले बताए गए एट्रिब्यूट मौजूद हैं:

प्रॉपर्टी विवरण
AuthorScreenUiState उपलब्ध कराता है AuthorViewModel, AuthorsRepository और NewsRepository का डेटा पढ़ता है और इस डेटा का इस्तेमाल AuthorScreenUiState बनाने के लिए करता है. इसके अलावा, यह कारोबारी लॉजिक तब भी लागू होता है, जब उपयोगकर्ता AuthorsRepository को सौंपकर किसी Author को फ़ॉलो या अनफ़ॉलो करना चाहता है.
इसके पास डेटा लेयर का ऐक्सेस होता है AuthorsRepository और NewsRepository का एक इंस्टेंस, इसे इसके कंस्ट्रक्टर में पास किया जाता है. इससे, यह Author को फ़ॉलो करने वाले बिज़नेस लॉजिक को लागू कर पाता है.
Activity मनोरंजन बचा है इसे ViewModel के साथ लागू किया गया है, इसलिए यह Activity के मनोरंजन वाले इलाके में सेव रहेगा. प्रोसेस बंद होने के मामले में, डेटा लेयर से यूज़र इंटरफ़ेस (यूआई) की स्थिति को पहले जैसा करने के लिए, ज़रूरी कम से कम जानकारी देने के लिए SavedStateHandle ऑब्जेक्ट को पढ़ा जा सकता है.
लंबे समय तक ज़िंदा रहने की स्थिति ViewModel, नेविगेशन ग्राफ़ तक सीमित होता है. इसलिए, जब तक नेविगेशन ग्राफ़ से लेखक के डेस्टिनेशन को नहीं हटाया जाता, तब तक uiState StateFlow में यूज़र इंटरफ़ेस (यूआई) की स्थिति, मेमोरी में बनी रहती है. StateFlow का इस्तेमाल करने से, कारोबारी लॉजिक को लागू करने का फ़ायदा भी मिलता है, जो स्थिति को लेज़ी पैदा करता है. ऐसा इसलिए, क्योंकि यूज़र इंटरफ़ेस (यूआई) स्टेट का कलेक्टर होने पर ही राज्य जनरेट होता है.
अपने यूज़र इंटरफ़ेस (यूआई) के लिए खास है AuthorViewModel, सिर्फ़ लेखक के नेविगेशन डेस्टिनेशन पर लागू होता है. इसे किसी अन्य जगह पर फिर से इस्तेमाल नहीं किया जा सकता. अगर कोई ऐसा बिज़नेस लॉजिक है जिसे नेविगेशन डेस्टिनेशन पर फिर से इस्तेमाल किया जाता है, तो उस बिज़नेस लॉजिक को डेटा या डोमेन लेयर के स्कोप वाले कॉम्पोनेंट में शामिल किया जाना चाहिए.

बिज़नेस लॉजिक स्टेट होल्डर के तौर पर ViewModel

Android डेवलपमेंट में ViewModels के फ़ायदे, उन्हें इन कामों के लिए सही बनाते हैं ऐप्लिकेशन का डेटा तैयार करने और उसे बिज़नेस लॉजिक का ऐक्सेस देना प्रज़ेंटेशन दिखेगा. इन फ़ायदों में ये शामिल हैं:

  • ViewModels से ट्रिगर होने वाली कार्रवाइयां, कॉन्फ़िगरेशन में होने वाले बदलावों से बचाती हैं.
  • नेविगेशन के साथ इंटिग्रेशन:
    • स्क्रीन के बैक स्टैक पर होने पर, नेविगेशन ViewModels को कैश मेमोरी में सेव करता है. यह है जब आप पहले से लोड किया गया डेटा तुरंत उपलब्ध अपनी मंज़िल पर लौटें. किसी साइट के साथ ऐसा करना ज़्यादा मुश्किल है स्टेट होल्डर जो कंपोज़ेबल स्क्रीन के लाइफ़साइकल को फ़ॉलो करता है.
    • डेस्टिनेशन के पीछे से पॉप-अप होने पर, ViewModel भी मिट जाता है स्टैक करें, ताकि यह पक्का किया जा सके कि आपके राज्य को अपने-आप खाली कर दिया जाए. यह है यह कंपोज़ेबल डिस्पोज़ल को सुनने से अलग है, जो कॉन्फ़िगरेशन की वजह से, कई वजहें हो सकती हैं. जैसे, नई स्क्रीन पर जाना बदलाव या अन्य वजहें हो सकती हैं.
  • Hilt जैसी अन्य Jetpack लाइब्रेरी के साथ इंटिग्रेशन.

यूज़र इंटरफ़ेस (यूआई) लॉजिक और इसका स्टेट होल्डर

यूज़र इंटरफ़ेस (यूआई) लॉजिक, ऐसे डेटा पर काम करता है जो यूज़र इंटरफ़ेस (यूआई) से मिलता है. यह इनमें से कोई भी हो सकता है यूज़र इंटरफ़ेस (यूआई) एलिमेंट पर' या यूज़र इंटरफ़ेस (यूआई) डेटा सोर्स, जैसे कि अनुमतियों का एपीआई या Resources. यूज़र इंटरफ़ेस (यूआई) लॉजिक का इस्तेमाल करने वाले राज्य के मालिकों के पास आम तौर पर ये प्रॉपर्टी:

  • यूज़र इंटरफ़ेस (यूआई) स्थिति जनरेट करता है और यूज़र इंटरफ़ेस (यूआई) एलिमेंट की स्थिति को मैनेज करता है.
  • Activity मनोरंजन पर कोई असर नहीं पड़ेगा: राज्य से जुड़े ऐसे लोग जो यूज़र इंटरफ़ेस (यूआई) में होस्ट किए गए हैं लॉजिक अक्सर यूज़र इंटरफ़ेस (यूआई) के डेटा सोर्स पर निर्भर करता है और यह जानकारी कॉन्फ़िगरेशन परिवर्तनों में अक्सर मेमोरी लीक. अगर राज्य के मालिकों को कॉन्फ़िगरेशन में डेटा बनाए रखना है बदलाव, वे Activity में बचे रहने के लिए बेहतर कॉम्पोनेंट को सौंपना होगा मनोरंजन. उदाहरण के लिए, Jetpack Compose में, कंपोज़ेबल यूज़र इंटरफ़ेस (यूआई) एलिमेंट की स्थितियां remembered फ़ंक्शन के साथ बनाया गया फ़ंक्शन अक्सर rememberSaveable को डेलिगेट की जाती है Activity मनोरंजन के लिए राज्य को सुरक्षित रखें. ऐसे फ़ंक्शन के उदाहरण rememberScaffoldState() और rememberLazyListState() शामिल हैं.
  • इसमें डेटा के यूज़र इंटरफ़ेस (यूआई) के स्कोप वाले सोर्स के रेफ़रंस हैं: डेटा के सोर्स, जैसे कि लाइफ़साइकल एपीआई और रिसॉर्स को सुरक्षित तरीके से रेफ़र किया जा सकता है और यूज़र इंटरफ़ेस (यूआई) लॉजिक के तौर पर पढ़ा जा सकता है स्टेट होल्डर का लाइफ़साइकल एक ही है, जो यूज़र इंटरफ़ेस (यूआई) का है.
  • एक से ज़्यादा यूज़र इंटरफ़ेस (यूआई) पर फिर से इस्तेमाल किया जा सकता है: एक ही यूज़र इंटरफ़ेस (यूआई) लॉजिक के अलग-अलग इंस्टेंस स्टेट होल्डर को ऐप्लिकेशन के अलग-अलग हिस्सों में फिर से इस्तेमाल किया जा सकता है. उदाहरण के लिए, कोई राज्य किसी चिप ग्रुप के लिए, उपयोगकर्ता के इनपुट इवेंट को मैनेज करने वाले होल्डर का इस्तेमाल, खोज के लिए किया जा सकता है फ़िल्टर चिप के लिए पेज, और "to" ईमेल पाने वालों के लिए फ़ील्ड.

यूज़र इंटरफ़ेस (यूआई) लॉजिक स्टेट होल्डर को आम तौर पर, सामान्य क्लास के साथ लागू किया जाता है. यह है क्योंकि यूज़र इंटरफ़ेस (यूआई) लॉजिक स्टेट बनाने के लिए खुद ज़िम्मेदार होता है होल्डर और यूज़र इंटरफ़ेस (यूआई) लॉजिक स्टेट होल्डर का लाइफ़साइकल, यूज़र इंटरफ़ेस (यूआई) के जैसा ही है. उदाहरण के लिए, Jetpack Compose में स्टेट होल्डर कंपोज़िशन का हिस्सा है और कंपोज़िशन के लाइफ़साइकल के मुताबिक काम करता है.

यह ऊपर दिए गए उदाहरण में दिखाया गया है. अब Android सैंपल में:

अब Android में, यूज़र इंटरफ़ेस (यूआई) लॉजिक को मैनेज करने के लिए, प्लेन क्लास स्टेट होल्डर का इस्तेमाल किया जाता है
इमेज 5: 'Android में अभी' सुविधा का सैंपल ऐप्लिकेशन

Android में Now नमूने में, सबसे नीचे वाला ऐप्लिकेशन बार या नेविगेशन रेल दिखती है नेविगेशन की सुविधा भी मिलती है. छोटी स्क्रीन पर और बड़ी स्क्रीन, नेविगेशन रेल पर दिखेंगी.

क्योंकि इसमें इस्तेमाल होने वाला सही नेविगेशन यूज़र इंटरफ़ेस (यूआई) एलिमेंट तय करने का लॉजिक NiaApp कंपोज़ेबल फ़ंक्शन, कारोबार के लॉजिक पर निर्भर नहीं करता. इसे मैनेज किया जा सकता है एक सामान्य क्लास स्टेट होल्डर से, जिसे NiaAppState कहा जाता है:

@Stable
class NiaAppState(
    val navController: NavHostController,
    val windowSizeClass: WindowSizeClass
) {

    // UI logic
    val shouldShowBottomBar: Boolean
        get() = windowSizeClass.widthSizeClass == WindowWidthSizeClass.Compact ||
            windowSizeClass.heightSizeClass == WindowHeightSizeClass.Compact

    // UI logic
    val shouldShowNavRail: Boolean
        get() = !shouldShowBottomBar

   // UI State
    val currentDestination: NavDestination?
        @Composable get() = navController
            .currentBackStackEntryAsState().value?.destination

    // UI logic
    fun navigate(destination: NiaNavigationDestination, route: String? = null) { /* ... */ }

     /* ... */
}

ऊपर दिए गए उदाहरण में, NiaAppState के बारे में नीचे दी गई जानकारी इस तरह से दी गई है ध्यान देने योग्य:

  • Activity मनोरंजन में नहीं बचेगा: NiaAppState में remembered है कंपोज़ेबल फ़ंक्शन की मदद से कंपोज़िशन इस्तेमाल करके rememberNiaAppState नाम रखने की प्रोसेस अपनाएं. Activity के फिर से बनने के बाद, पिछला इंस्टेंस खो जाता है और एक नया इंस्टेंस इस डिपेंडेंसी पास की जाती हैं, जो Activity को फिर से बनाया गया. ये डिपेंडेंसी नई हो सकती हैं या पिछला कॉन्फ़िगरेशन. उदाहरण के लिए, rememberNavController() का इस्तेमाल इसमें किया जाता है NiaAppState कंस्ट्रक्टर और यह rememberSaveable को डेलिगेट करता है Activity मनोरंजन के लिए राज्य को सुरक्षित रखें.
  • इसमें डेटा के यूज़र इंटरफ़ेस (यूआई) के दायरे वाले सोर्स के रेफ़रंस हैं: navigationController, Resources, और अन्य मिलते-जुलते लाइफ़साइकल के स्कोप वाले टाइप को NiaAppState में सुरक्षित रखा जा सकता है, क्योंकि उनका लाइफ़साइकल स्कोप एक ही होता है.

स्टेट होल्डर के लिए ViewModel और सामान्य क्लास में से कोई एक चुनना

ऊपर दिए गए सेक्शन से, ViewModel और सामान्य क्लास स्टेट में से कोई एक चुनें होल्डर, यूज़र इंटरफ़ेस (यूआई) की स्थिति और डेटा के सोर्स पर लागू होने वाले लॉजिक पर आता है और लॉजिक उस पर काम करता हो.

खास जानकारी के लिए, नीचे दिया गया डायग्राम यूज़र इंटरफ़ेस (यूआई) में राज्य के मालिकों की पोज़िशन दिखाता है स्टेट प्रोडक्शन पाइपलाइन:

डेटा बनाने वाली लेयर से यूज़र इंटरफ़ेस (यूआई) लेयर में डेटा फ़्लो
इमेज 6: यूज़र इंटरफ़ेस (यूआई) स्टेट प्रोडक्शन पाइपलाइन में, राज्य के मालिक. ऐरो का मतलब है डेटा फ़्लो.

आपको यूज़र इंटरफ़ेस (यूआई) स्थिति बनाने के लिए, सबसे नज़दीकी राज्य होल्डर का इस्तेमाल करना चाहिए जहां इसे देखा जाता है. कम औपचारिक तौर पर, आपको इस राज्य में इतना कम उचित मालिकाना हक को बनाए रखते हुए, ऐसा किया जा सकता है. अगर आपको कारोबार का ऐक्सेस चाहिए लॉजिक के साथ काम करता है और जब तक स्क्रीन पर नेविगेट किया जा सकता है, तब तक यूज़र इंटरफ़ेस (यूआई) स्थिति जारी रखने की ज़रूरत होती है, Activity के मनोरंजन के लिए भी, ViewModel बेहतरीन विकल्प है अपने बिज़नेस लॉजिक स्टेट होल्डर को लागू करने के लिए. कम समय तक चलने वाली यूज़र इंटरफ़ेस (यूआई) स्थिति के लिए और यूज़र इंटरफ़ेस (यूआई) लॉजिक, एक प्लेन क्लास, जिसका लाइफ़साइकल पूरी तरह से यूज़र इंटरफ़ेस (यूआई) पर निर्भर होता है के लिए पर्याप्त है.

राज्य धारकों को मिल सकता है

राज्य के मालिक तब तक किसी अन्य राज्य पर निर्भर रह सकते हैं, जब तक उनकी डिपेंडेंसी एक बराबर या कम समय का लाइफ़टाइम. इसके कुछ उदाहरण यहां दिए गए हैं:

  • यूआई लॉजिक स्टेट होल्डर, किसी दूसरे यूज़र इंटरफ़ेस (यूआई) लॉजिक स्टेट होल्डर पर भी निर्भर कर सकता है.
  • स्क्रीन लेवल स्टेट होल्डर, यूज़र इंटरफ़ेस (यूआई) लॉजिक स्टेट होल्डर पर निर्भर करता है.

यह कोड स्निपेट दिखाता है कि Compose का DrawerState किस तरह से निर्भर करता है कोई अन्य इंटरनल स्टेट होल्डर, SwipeableState और ऐप्लिकेशन का यूज़र इंटरफ़ेस (यूआई) लॉजिक स्टेट होल्डर, DrawerState पर निर्भर हो सकता है:

@Stable
class DrawerState(/* ... */) {
  internal val swipeableState = SwipeableState(/* ... */)
  // ...
}

@Stable
class MyAppState(
  private val drawerState: DrawerState,
  private val navController: NavHostController
) { /* ... */ }

@Composable
fun rememberMyAppState(
  drawerState: DrawerState = rememberDrawerState(DrawerValue.Closed),
  navController: NavHostController = rememberNavController()
): MyAppState = remember(drawerState, navController) {
  MyAppState(drawerState, navController)
}

यूज़र इंटरफ़ेस (यूआई) लॉजिक के ज़रिए ऐसी डिपेंडेंसी का उदाहरण दिया गया है जो स्टेट होल्डर से आउटला करती है स्टेट होल्डर, जो कि स्क्रीन लेवल स्टेट होल्डर के आधार पर अलग-अलग होता है. इससे, कम समय तक बने रहने वाले स्टेट होल्डर की फिर से इस्तेमाल करने की क्षमता और इसे ज़्यादा लॉजिक का ऐक्सेस देता है की ज़रूरत नहीं है.

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

class MyScreenViewModel(/* ... */) {
  val uiState: StateFlow<MyScreenUiState> = /* ... */
  fun doSomething() { /* ... */ }
  fun doAnotherThing() { /* ... */ }
  // ...
}

@Stable
class MyScreenState(
  // DO NOT pass a ViewModel instance to a plain state holder class
  // private val viewModel: MyScreenViewModel,

  // Instead, pass only what it needs as a dependency
  private val someState: StateFlow<SomeState>,
  private val doSomething: () -> Unit,

  // Other UI-scoped types
  private val scaffoldState: ScaffoldState
) {
  /* ... */
}

@Composable
fun rememberMyScreenState(
  someState: StateFlow<SomeState>,
  doSomething: () -> Unit,
  scaffoldState: ScaffoldState = rememberScaffoldState()
): MyScreenState = remember(someState, doSomething, scaffoldState) {
  MyScreenState(someState, doSomething, scaffoldState)
}

@Composable
fun MyScreen(
  modifier: Modifier = Modifier,
  viewModel: MyScreenViewModel = viewModel(),
  state: MyScreenState = rememberMyScreenState(
    someState = viewModel.uiState.map { it.toSomeState() },
    doSomething = viewModel::doSomething
  ),
  // ...
) {
  /* ... */
}

नीचे दिया गया डायग्राम, यूज़र इंटरफ़ेस (यूआई) और अलग-अलग पिछले कोड स्निपेट के स्टेट मालिक:

यूज़र इंटरफ़ेस (यूआई) जो यूआई लॉजिक स्टेट होल्डर और स्क्रीन लेवल स्टेट होल्डर, दोनों पर निर्भर करता है
सातवीं इमेज: अलग-अलग राज्य के मालिकों के हिसाब से यूज़र इंटरफ़ेस (यूआई). ऐरो का मतलब डिपेंडेंसी है.

सैंपल

नीचे दिए गए Google नमूने, यूज़र इंटरफ़ेस (यूआई) लेयर. इस दिशा-निर्देश को देखने के लिए, उन्हें एक्सप्लोर करें: