আপনার রাজ্য কোথায় উত্তোলন করা হয়েছে এবং যে যুক্তির প্রয়োজন তার উপর নির্ভর করে, আপনি আপনার UI অবস্থা সংরক্ষণ এবং পুনরুদ্ধার করতে বিভিন্ন API ব্যবহার করতে পারেন। এটি সর্বোত্তমভাবে অর্জন করতে প্রতিটি অ্যাপ API-এর সংমিশ্রণ ব্যবহার করে।
কার্যকলাপ বা প্রক্রিয়া বিনোদনের কারণে যেকোনো Android অ্যাপ তার UI অবস্থা হারাতে পারে। নিম্নলিখিত ঘটনার কারণে রাষ্ট্রের এই ক্ষতি ঘটতে পারে:
- কনফিগারেশন পরিবর্তন . ক্রিয়াকলাপটি ধ্বংস এবং পুনরায় তৈরি করা হয় যদি না কনফিগারেশন পরিবর্তনটি ম্যানুয়ালি পরিচালনা করা হয়।
- সিস্টেম-সূচিত প্রক্রিয়া মৃত্যু । অ্যাপটি ব্যাকগ্রাউন্ডে রয়েছে এবং ডিভাইসটি অন্যান্য প্রসেস ব্যবহার করার জন্য রিসোর্স (যেমন মেমরি) মুক্ত করে।
ইতিবাচক ব্যবহারকারীর অভিজ্ঞতার জন্য এই ঘটনাগুলির পরে রাষ্ট্র সংরক্ষণ করা অপরিহার্য। কোন স্থিতি বজায় রাখতে হবে তা নির্বাচন করা আপনার অ্যাপের অনন্য ব্যবহারকারী প্রবাহের উপর নির্ভর করে। একটি সর্বোত্তম অনুশীলন হিসাবে, আপনাকে কমপক্ষে ব্যবহারকারীর ইনপুট এবং নেভিগেশন-সম্পর্কিত অবস্থা সংরক্ষণ করা উচিত। এর উদাহরণগুলির মধ্যে একটি তালিকার স্ক্রোল অবস্থান, ব্যবহারকারী যে আইটেম সম্পর্কে আরও বিশদ চান তার আইডি, ব্যবহারকারীর পছন্দগুলির অগ্রগতি নির্বাচন, বা পাঠ্য ক্ষেত্রে ইনপুট অন্তর্ভুক্ত।
এই পৃষ্ঠাটি UI স্টেট সঞ্চয় করার জন্য উপলব্ধ API গুলিকে সংক্ষিপ্ত করে যা আপনার স্টেট কোথায় উত্তোলন করা হয়েছে এবং যে যুক্তির প্রয়োজন তার উপর নির্ভর করে।
UI যুক্তি
যদি আপনার স্টেটটি UI-তে উত্তোলন করা হয়, হয় কম্পোজেবল ফাংশন বা প্লেইন স্টেট হোল্ডার ক্লাসে কম্পোজিশন স্কোপ করা হয়, আপনি ক্রিয়াকলাপ এবং প্রক্রিয়া বিনোদন জুড়ে অবস্থা ধরে রাখতে rememberSaveable
ব্যবহার করতে পারেন।
নিম্নলিখিত স্নিপেটে, rememberSaveable
একটি একক বুলিয়ান UI উপাদান অবস্থা সংরক্ষণ করতে ব্যবহৃত হয়:
@Composable fun ChatBubble( message: Message ) { var showDetails by rememberSaveable { mutableStateOf(false) } ClickableText( text = AnnotatedString(message.content), onClick = { showDetails = !showDetails } ) if (showDetails) { Text(message.timestamp) } }
showDetails
হল একটি বুলিয়ান ভেরিয়েবল যা সঞ্চয় করে যদি চ্যাট বুদবুদটি ভেঙে যায় বা প্রসারিত হয়।
rememberSaveable
সংরক্ষিত ইনস্ট্যান্স স্টেট মেকানিজমের মাধ্যমে একটি Bundle
UI উপাদানের অবস্থা সংরক্ষণ করে।
এটি স্বয়ংক্রিয়ভাবে বান্ডিলে আদিম প্রকারগুলি সংরক্ষণ করতে সক্ষম। যদি আপনার স্টেট এমন একটি টাইপের মধ্যে রাখা হয় যা ডেটা ক্লাসের মতো আদিম নয়, আপনি বিভিন্ন স্টোরিং মেকানিজম ব্যবহার করতে পারেন, যেমন Parcelize
টীকা ব্যবহার করা, listSaver
এবং mapSaver
মতো কম্পোজ API ব্যবহার করা, বা কম্পোজ রানটাইম Saver
প্রসারিত করে একটি কাস্টম সেভার ক্লাস বাস্তবায়ন করা ক্লাস এই পদ্ধতিগুলি সম্পর্কে আরও জানতে রাষ্ট্রীয় ডকুমেন্টেশন সংরক্ষণের উপায়গুলি দেখুন।
নিম্নলিখিত স্নিপেটে, rememberLazyListState
কম্পোজ এপিআই LazyListState
সঞ্চয় করে, যা একটি LazyColumn
বা LazyRow
এর স্ক্রোল অবস্থা নিয়ে গঠিত, rememberSaveable
ব্যবহার করে। এটি একটি LazyListState.Saver
ব্যবহার করে, যা একটি কাস্টম সেভার যা স্ক্রোল অবস্থা সংরক্ষণ এবং পুনরুদ্ধার করতে সক্ষম। একটি কার্যকলাপ বা প্রক্রিয়া বিনোদনের পরে (উদাহরণস্বরূপ, ডিভাইসের অভিযোজন পরিবর্তনের মতো কনফিগারেশন পরিবর্তনের পরে), স্ক্রোল অবস্থা সংরক্ষণ করা হয়।
@Composable fun rememberLazyListState( initialFirstVisibleItemIndex: Int = 0, initialFirstVisibleItemScrollOffset: Int = 0 ): LazyListState { return rememberSaveable(saver = LazyListState.Saver) { LazyListState( initialFirstVisibleItemIndex, initialFirstVisibleItemScrollOffset ) } }
সর্বোত্তম অনুশীলন
rememberSaveable
UI স্টেট সঞ্চয় করার জন্য একটি Bundle
ব্যবহার করে, যা অন্যান্য API গুলি দ্বারা শেয়ার করা হয় যা এটিতে লেখে, যেমন আপনার কার্যকলাপে onSaveInstanceState()
কল। যাইহোক, এই Bundle
আকার সীমিত, এবং বড় বস্তু সংরক্ষণ করলে রানটাইমে TransactionTooLarge
ব্যতিক্রম হতে পারে। এটি বিশেষ করে একক Activity
অ্যাপে সমস্যাযুক্ত হতে পারে যেখানে একই Bundle
অ্যাপ জুড়ে ব্যবহার করা হচ্ছে।
এই ধরনের ক্র্যাশ এড়াতে, আপনার বান্ডিলে বড় জটিল বস্তু বা বস্তুর তালিকা সংরক্ষণ করা উচিত নয় ।
পরিবর্তে, আইডি বা কীগুলির মতো প্রয়োজনীয় ন্যূনতম অবস্থা সঞ্চয় করুন এবং স্থায়ী স্টোরেজের মতো আরও জটিল UI অবস্থা পুনরুদ্ধার করার জন্য অন্যান্য পদ্ধতিতে অর্পণ করতে এগুলি ব্যবহার করুন৷
এই ডিজাইন পছন্দগুলি আপনার অ্যাপের জন্য নির্দিষ্ট ব্যবহারের ক্ষেত্রে এবং আপনার ব্যবহারকারীরা কীভাবে এটি আচরণ করবে তার উপর নির্ভর করে।
রাষ্ট্র পুনরুদ্ধার যাচাই করুন
আপনি যাচাই করতে পারেন যে আপনার রচনা উপাদানগুলিতে rememberSaveable
সহ সংরক্ষিত অবস্থাটি সঠিকভাবে পুনরুদ্ধার করা হয়েছে যখন কার্যকলাপ বা প্রক্রিয়াটি পুনরায় তৈরি করা হয়। এটি অর্জনের জন্য নির্দিষ্ট API আছে, যেমন StateRestorationTester
। আরও জানতে টেস্টিং ডকুমেন্টেশন দেখুন।
ব্যবসায়িক যুক্তি
যদি আপনার UI উপাদানের অবস্থা ViewModel
এ উত্তোলন করা হয় কারণ এটি ব্যবসায়িক যুক্তি দ্বারা প্রয়োজন, আপনি ViewModel
এর API ব্যবহার করতে পারেন।
আপনার অ্যান্ড্রয়েড অ্যাপ্লিকেশনে একটি ViewModel
ব্যবহার করার প্রধান সুবিধাগুলির মধ্যে একটি হল এটি বিনামূল্যে কনফিগারেশন পরিবর্তনগুলি পরিচালনা করে। যখন কনফিগারেশন পরিবর্তন হয়, এবং কার্যকলাপটি ধ্বংস হয়ে পুনরায় তৈরি করা হয়, তখন ViewModel
এ উত্তোলিত UI অবস্থা মেমরিতে রাখা হয়। বিনোদনের পরে, পুরানো ViewModel
দৃষ্টান্তটি নতুন কার্যকলাপের উদাহরণের সাথে সংযুক্ত করা হয়।
যাইহোক, একটি ViewModel
দৃষ্টান্ত সিস্টেম-সূচিত প্রক্রিয়ার মৃত্যু থেকে বাঁচতে পারে না। UI স্টেট যাতে টিকে থাকে তার জন্য, ViewModel-এর জন্য Saved State মডিউল ব্যবহার করুন, যাতে SavedStateHandle
API রয়েছে।
সর্বোত্তম অনুশীলন
SavedStateHandle
এছাড়াও UI স্টেট সঞ্চয় করতে Bundle
প্রক্রিয়া ব্যবহার করে, তাই আপনার শুধুমাত্র সাধারণ UI উপাদান স্থিতি সঞ্চয় করতে এটি ব্যবহার করা উচিত।
স্ক্রীন UI অবস্থা , যা ব্যবসার নিয়ম প্রয়োগ করে এবং UI ব্যতীত আপনার অ্যাপ্লিকেশনের স্তরগুলি অ্যাক্সেস করার মাধ্যমে উত্পাদিত হয়, সম্ভাব্য জটিলতা এবং আকারের কারণে SavedStateHandle
এ সংরক্ষণ করা উচিত নয়৷ আপনি স্থানীয় স্থায়ী স্টোরেজের মতো জটিল বা বড় ডেটা সঞ্চয় করতে বিভিন্ন প্রক্রিয়া ব্যবহার করতে পারেন। একটি প্রসেস রিক্রিয়েশনের পরে, স্ক্রীনটি পুনরুদ্ধার করা ক্ষণস্থায়ী অবস্থার সাথে পুনরায় তৈরি করা হয় যা SavedStateHandle
এ সংরক্ষিত ছিল (যদি থাকে), এবং স্ক্রীন UI অবস্থা আবার ডেটা স্তর থেকে উত্পাদিত হয়।
SavedStateHandle
APIs
SavedStateHandle
এর UI এলিমেন্ট স্টেট সঞ্চয় করার জন্য বিভিন্ন API আছে, বিশেষ করে:
State রচনা করুন | saveable() |
---|---|
StateFlow | getStateFlow() |
State
রচনা করুন
MutableState
হিসাবে UI উপাদানের অবস্থা পড়তে এবং লিখতে SavedStateHandle
এর saveable
API ব্যবহার করুন, যাতে এটি ন্যূনতম কোড সেটআপের সাথে কার্যকলাপ এবং প্রক্রিয়া বিনোদন থেকে বেঁচে থাকে।
saveable
এপিআই বাক্সের বাইরে আদিম প্রকারগুলিকে সমর্থন করে এবং কাস্টম সেভারগুলি ব্যবহার করার জন্য একটি stateSaver
প্যারামিটার পায়, ঠিক rememberSaveable()
এর মতো।
নিম্নলিখিত স্নিপেটে, message
ব্যবহারকারীর ইনপুট প্রকারগুলিকে একটি TextField
এ সঞ্চয় করে:
class ConversationViewModel( savedStateHandle: SavedStateHandle ) : ViewModel() { var message by savedStateHandle.saveable(stateSaver = TextFieldValue.Saver) { mutableStateOf(TextFieldValue("")) } private set fun update(newMessage: TextFieldValue) { message = newMessage } /*...*/ } val viewModel = ConversationViewModel(SavedStateHandle()) @Composable fun UserInput(/*...*/) { TextField( value = viewModel.message, onValueChange = { viewModel.update(it) } ) }
saveable
API ব্যবহার করার বিষয়ে আরও তথ্যের জন্য SavedStateHandle
ডকুমেন্টেশন দেখুন।
StateFlow
UI উপাদান স্থিতি সংরক্ষণ করতে getStateFlow()
ব্যবহার করুন এবং SavedStateHandle
থেকে একটি প্রবাহ হিসাবে এটি ব্যবহার করুন। StateFlow
শুধুমাত্র পঠিত হয়, এবং API এর জন্য আপনাকে একটি কী নির্দিষ্ট করতে হবে যাতে আপনি একটি নতুন মান নির্গত করতে ফ্লো প্রতিস্থাপন করতে পারেন। আপনার কনফিগার করা কী দিয়ে, আপনি StateFlow
পুনরুদ্ধার করতে এবং সর্বশেষ মান সংগ্রহ করতে পারেন।
নিম্নলিখিত স্নিপেটে, savedFilterType
হল একটি StateFlow
ভেরিয়েবল যা একটি চ্যাট অ্যাপে চ্যাট চ্যানেলের তালিকায় প্রয়োগ করা একটি ফিল্টার প্রকার সংরক্ষণ করে:
private const val CHANNEL_FILTER_SAVED_STATE_KEY = "ChannelFilterKey" class ChannelViewModel( channelsRepository: ChannelsRepository, private val savedStateHandle: SavedStateHandle ) : ViewModel() { private val savedFilterType: StateFlow<ChannelsFilterType> = savedStateHandle.getStateFlow( key = CHANNEL_FILTER_SAVED_STATE_KEY, initialValue = ChannelsFilterType.ALL_CHANNELS ) private val filteredChannels: Flow<List<Channel>> = combine(channelsRepository.getAll(), savedFilterType) { channels, type -> filter(channels, type) }.onStart { emit(emptyList()) } fun setFiltering(requestType: ChannelsFilterType) { savedStateHandle[CHANNEL_FILTER_SAVED_STATE_KEY] = requestType } /*...*/ } enum class ChannelsFilterType { ALL_CHANNELS, RECENT_CHANNELS, ARCHIVED_CHANNELS }
প্রতিবার ব্যবহারকারী একটি নতুন ফিল্টার টাইপ নির্বাচন করে, setFiltering
বলা হয়। এটি _CHANNEL_FILTER_SAVED_STATE_KEY_
কী সহ সংরক্ষণ করা SavedStateHandle
এ একটি নতুন মান সংরক্ষণ করে। savedFilterType
হল একটি ফ্লো যা কীতে সংরক্ষিত সর্বশেষ মান নির্গত করে। filteredChannels
চ্যানেল ফিল্টারিং সঞ্চালনের জন্য ফ্লোতে সাবস্ক্রাইব করা হয়েছে।
getStateFlow()
API সম্পর্কে আরও তথ্যের জন্য SavedStateHandle
ডকুমেন্টেশন দেখুন।
সারাংশ
নিম্নলিখিত সারণীটি এই বিভাগে কভার করা APIগুলির সংক্ষিপ্ত বিবরণ দেয় এবং UI অবস্থা সংরক্ষণ করতে কখন প্রতিটি ব্যবহার করতে হবে:
ঘটনা | UI যুক্তি | একটি ViewModel ব্যবসায়িক যুক্তি |
---|---|---|
কনফিগারেশন পরিবর্তন | rememberSaveable | স্বয়ংক্রিয় |
সিস্টেম-সূচিত প্রক্রিয়া মৃত্যু | rememberSaveable | SavedStateHandle |
ব্যবহার করার জন্য API নির্ভর করে রাষ্ট্রটি কোথায় রাখা হয়েছে এবং এর জন্য প্রয়োজনীয় যুক্তির উপর। UI লজিক ব্যবহার করা হয় এমন অবস্থার জন্য, rememberSaveable
ব্যবহার করুন। ব্যবসায়িক যুক্তিতে ব্যবহৃত রাষ্ট্রের জন্য, যদি আপনি এটিকে একটি ViewModel
এ ধরে রাখেন, SavedStateHandle
ব্যবহার করে সংরক্ষণ করুন।
অল্প পরিমাণে UI স্টেট সঞ্চয় করার জন্য আপনার বান্ডেল API ব্যবহার করা SavedStateHandle
rememberSaveable
UI কে পূর্বের অবস্থায় ফিরিয়ে আনার জন্য এই তথ্যটি ন্যূনতম প্রয়োজনীয়, অন্যান্য স্টোরিং মেকানিজমের সাথে। উদাহরণস্বরূপ, যদি আপনি একটি প্রোফাইলের আইডি সংরক্ষণ করেন যা ব্যবহারকারী বান্ডেলে দেখছিলেন, আপনি ডেটা স্তর থেকে প্রোফাইলের বিবরণের মতো ভারী ডেটা আনতে পারেন।
UI অবস্থা সংরক্ষণের বিভিন্ন উপায় সম্পর্কে আরও তথ্যের জন্য, সাধারণ সংরক্ষণ UI স্টেট ডকুমেন্টেশন এবং আর্কিটেকচার গাইডের ডেটা স্তর পৃষ্ঠাটি দেখুন।
{% শব্দার্থে %}আপনার জন্য প্রস্তাবিত
- দ্রষ্টব্য: জাভাস্ক্রিপ্ট বন্ধ থাকলে লিঙ্ক টেক্সট প্রদর্শিত হয়
- যেখানে রাজ্য উত্তোলন করতে হবে
- রাজ্য এবং জেটপ্যাক রচনা
- তালিকা এবং গ্রিড