paint-brush
रीसाइक्लरव्यू को अनुकूलित करने के 3 त्वरित तरीकेद्वारा@azamatnurkhojayev
1,147 रीडिंग
1,147 रीडिंग

रीसाइक्लरव्यू को अनुकूलित करने के 3 त्वरित तरीके

द्वारा Azamat Nurkhojayev7m2024/05/14
Read on Terminal Reader

बहुत लंबा; पढ़ने के लिए

इस लेख में, मैं RecyclerView का उपयोग करते समय अनुकूलन के त्वरित तरीकों पर नज़र डालना चाहूँगा। RecyclerView एक उपयोगकर्ता इंटरफ़ेस घटक है, अर्थात, एक तत्व जिसे सूची को सुविधाजनक रूप से प्रदर्शित करने के लिए इंटरफ़ेस में जोड़ा जा सकता है।
featured image - रीसाइक्लरव्यू को अनुकूलित करने के 3 त्वरित तरीके
Azamat Nurkhojayev HackerNoon profile picture


हेलो सब लोग!


इस लेख में, मैं RecyclerView का उपयोग करते समय अनुकूलन के त्वरित तरीकों पर नज़र डालना चाहूंगा।


रीसाइक्लर व्यू एक यूजर इंटरफ़ेस घटक है, यानी एक ऐसा तत्व जिसे इंटरफ़ेस में जोड़कर आसानी से सूची प्रदर्शित की जा सकती है। यह कोड में बनाया गया है और इसमें सूची को प्रदर्शित करने, एनिमेट करने और ऑप्टिमाइज़ करने के लिए पहले से ही उपकरण मौजूद हैं, और यह कस्टमाइज़ेशन सेटिंग्स का भी समर्थन करता है।

रीसाइक्लरव्यू के मुख्य घटक

RecyclerView को सही ढंग से काम करने के लिए, आपको निम्नलिखित घटकों को लागू करना होगा:

  • RecyclerView , जिसे हमारी गतिविधि के लेआउट में जोड़ा जाना चाहिए;
  • Adapter , जो सूची के साथ डेटा को सम्मिलित करता है, संसाधित करता है और संबद्ध करता है;
  • ListAdapter , Adapter को अद्यतन करता है और कन्स्ट्रक्टर में DiffUtil को स्वीकार करता है;
  • ViewHolder , जो संसाधनों को अनुकूलित करने के लिए कार्य करता है और सूची में शामिल सभी तत्वों के लिए एक प्रकार का कंटेनर है;
  • DiffUtil , जिसका उपयोग सूची को अनुकूलित करने के लिए किया जाता है।


मैं यह नहीं बताऊंगा कि इसे शुरू से कैसे लागू किया जाए, आप इसे लिंक पर पा सकते हैं।

व्यूहोल्डर का प्रथम अनुकूलन.

बाइंडिंग करते समय ViewHolder में संसाधनों और कास्टिंग तक पहुंच हटाएँ।


उदाहरण के लिए, नीचे दिया गया कोड लें:

 data class TrackingUiModel( val id: Long, val title: String, @ColorRes val color: Int, val eventId: Long, val state: TrackingState, val startTime: Long, val endTime: Long, val countTime: Long, val formattedTime: String, ) class TrackingViewHolder(itemView: View): ViewHolder(itemView) { private val binding : TrackingItemBinding by viewBinding() @SuppressLint("SetTextI18n") fun bind(data: TrackingUiModel) { val stateText = when (data.state) { TrackingState.START -> itemView.context.getString(R.string.in_progress) TrackingState.PAUSE -> itemView.context.getString(R.string.pause) else -> { "" } } binding.eventId.text = data.eventId.toString() binding.eventTitle.text = "${data.title} $stateText" binding.eventColor.setBackgroundColor(ContextCompat.getColor(itemView.context, data.color)) binding.countTextView.text = data.formattedTime } }


हर बार जब bind विधि को कॉल किया जाता है, तो getString और getColor कॉल को कॉल किया जाएगा, और स्ट्रिंग कास्टिंग के लिए toString भी कॉल किया जाएगा। इस तरह हम अधिक मेमोरी का उपभोग करते हैं। और आपको यह सुनिश्चित करने की आवश्यकता है कि bind विधि जल्दी से निष्पादित हो, और आपको यह सुनिश्चित करने का प्रयास करना चाहिए कि ViewHolder कार्य केवल सूची आइटम प्रदर्शित कर रहा है। अनुकूलन के लिए, TrackingUiModel ऑब्जेक्ट में स्ट्रिंग eventId , stateText और color प्राप्त करना बेहतर है।


अनुकूलित कोड अब इस तरह दिखता है:

 data class TrackingUiModel( val id: Long, val title: String, val color: Int, val eventId: String, val state: TrackingState, val stateText: String, val startTime: Long, val endTime: Long, val countTime: Long, val formattedTime: String, ) class TrackingViewHolder(itemView: View): ViewHolder(itemView) { private val binding : TrackingItemBinding by viewBinding() fun bind(data: TrackingUiModel) { binding.eventId.text = data.eventId binding.eventTitle.text = "${data.title} ${data.stateText}" binding.eventColor.setBackgroundColor(data.color) binding.countTextView.text = data.formattedTime } }


हमने ViewHolder से आगे सब कुछ ले लिया है, हमें जो कुछ भी चाहिए और तैयार है वह TrackingUiModel में प्राप्त होगा।

दूसरा, हम ListAdapter और DiffUtil का उपयोग करेंगे।

यदि आप RecyclerView.Adapter उपयोग कर रहे हैं तो आपको ListAdapter पर स्विच करना चाहिए, और इसके साथ DiffUtil उपयोग करना चाहिए।


उदाहरण के लिए, नीचे दिया गया कोड लें:

 class TrackingAdapter: RecyclerView.Adapter<TrackingViewHolder>(){ private val mItems = mutableListOf<TrackingUiModel>() override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): TrackingViewHolder { return TrackingViewHolder( LayoutInflater.from(parent.context) .inflate(R.layout.tracking_item, parent, false)) } override fun getItemCount(): Int = mItems.size override fun onBindViewHolder(holder: TrackingViewHolder, position: Int) { holder.bind(mItems[position]) } fun setItems(items: List<TrackingUiModel>){ mItems.clear() mItems.addAll(items) notifyDataSetChanged() } }


सूची तत्वों को जोड़ते समय, setItems विधि को कॉल करने से सूची साफ़ हो जाती है, सूची तत्व जुड़ जाते हैं, और अंत में notifyDataSetChanged कॉल किया जाता है।


आइए कल्पना करें कि हम सूची को बदलते या अपडेट करते हैं, और हर बार setItems विधि को कॉल किया जाएगा; यह काफी संसाधन-खपत होगा। इस कारण से, ListAdapter और DiffUtil उपयोग करना बेहतर है।


नीचे एक संशोधित TrackingAdapter है जो ListAdapter क्रियान्वित करता है और DiffUtil उपयोग करता है; मेरे उदाहरण में, यह TrackingDiffCallback वर्ग है।


सूची जोड़ने के लिए, हम trackingAdapter.submitList विधि का उपयोग करते हैं, और अंत में, एडाप्टर हमारे लिए सूची को अद्यतन करने का सारा काम कर देगा।


 class TrackingAdapter: ListAdapter<TrackingUiModel, TrackingViewHolder>(TrackingDiffCallback()){ override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): TrackingViewHolder { return TrackingViewHolder( LayoutInflater.from(parent.context) .inflate(R.layout.tracking_item, parent, false)) } override fun onBindViewHolder(holder: TrackingViewHolder, position: Int) { holder.bind(getItem(position)) } }


 class TrackingDiffCallback: DiffUtil.ItemCallback<TrackingUiModel>() { override fun areItemsTheSame(oldItem: TrackingUiModel, newItem: TrackingUiModel): Boolean { return oldItem.id == newItem.id } override fun areContentsTheSame(oldItem: TrackingUiModel, newItem: TrackingUiModel): Boolean { return oldItem == newItem } }


तीसरा, पेलोड का उपयोग करें.

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


पेलोड का उपयोग करने के लिए, आइए ViewHolder , DiffUtil , और Adapter में परिवर्तन करें।


मेरे मामले में, मैं निम्नलिखित परिवर्तन करूंगा।


TrackingViewHolder में, हम उस डेटा के साथ एक बाइंड विधि जोड़ते हैं जिसे बदलने की आवश्यकता होती है।

 fun bind(data: TrackingUiModel, newTime: String) { binding.eventId.text = data.eventId binding.eventTitle.text = "${data.title} ${data.stateText}" binding.eventColor.setBackgroundColor(data.color) binding.countTextView.text = newTime }


TrackingDiffCallback में, हम getChangePayload विधि को ओवरराइड करते हैं और बदले जा रहे फ़ील्ड की तुलना करते हैं। मेरे मामले में, यह formattedTime है।

 override fun getChangePayload(oldItem: TrackingUiModel, newItem: TrackingUiModel): Any? { if (oldItem.formattedTime != newItem.formattedTime) return newItem.formattedTime return super.getChangePayload(oldItem, newItem) }


TrackingListAdapter, हम onBindViewHolder विधि को पेलोड के साथ ओवरराइड करते हैं। हम जाँचते हैं कि पेलोड खाली है या नहीं, अगर यह खाली नहीं है, तो हम पहला तत्व प्राप्त करते हैं और पेलोड के लिए बाइंड विधि को कॉल करते हैं।

 override fun onBindViewHolder(holder: TrackingViewHolder, position: Int, payloads: MutableList<Any>) { if (payloads.isEmpty()) { super.onBindViewHolder(holder, position, payloads) } else { val newTime = payloads.firstOrNull() as? String ?: "" holder.bind(getItem(position), newTime) } } 



बिना पेलोड के


पेलोड के साथ



संदर्भ लिंक: