এই কোডল্যাবটি অ্যান্ড্রয়েড কোটলিন ফান্ডামেন্টাল কোর্সের অংশ। আপনি যদি ক্রমানুসারে কোডল্যাবগুলির মাধ্যমে কাজ করেন তবে আপনি এই কোর্সের সর্বাধিক মূল্য পাবেন৷ সমস্ত কোর্স কোডল্যাব অ্যান্ড্রয়েড কোটলিন ফান্ডামেন্টাল কোডল্যাব ল্যান্ডিং পৃষ্ঠায় তালিকাভুক্ত করা হয়েছে।
ভূমিকা
পূর্ববর্তী কোডল্যাবে, আপনি ডিভাইস-কনফিগারেশন পরিবর্তনগুলি থেকে বাঁচতে অ্যাপের ডেটাকে অনুমতি দিতে GuessTheWord অ্যাপে একটি ViewModel ব্যবহার করেছেন। এই কোডল্যাবে, আপনি ViewModel ক্লাসের ডেটার সাথে LiveData কীভাবে সংহত করতে হয় তা শিখবেন। LiveData , যা অ্যান্ড্রয়েড আর্কিটেকচার উপাদানগুলির মধ্যে একটি, আপনাকে এমন ডেটা অবজেক্ট তৈরি করতে দেয় যা অন্তর্নিহিত ডাটাবেস পরিবর্তনের সময় ভিউকে অবহিত করে।
LiveData ক্লাস ব্যবহার করার জন্য, আপনি "পর্যবেক্ষক" (উদাহরণস্বরূপ, কার্যকলাপ বা টুকরা) সেট আপ করেন যা অ্যাপের ডেটাতে পরিবর্তনগুলি পর্যবেক্ষণ করে। LiveData হল লাইফসাইকেল-সচেতন, তাই এটি শুধুমাত্র অ্যাপ-কম্পোনেন্ট পর্যবেক্ষকদের আপডেট করে যারা সক্রিয় জীবনচক্র অবস্থায় আছে।
আপনি ইতিমধ্যে কি জানা উচিত
- কোটলিনে কীভাবে বেসিক অ্যান্ড্রয়েড অ্যাপ তৈরি করবেন।
- আপনার অ্যাপের গন্তব্যের মধ্যে কীভাবে নেভিগেট করবেন।
- কার্যকলাপ এবং খণ্ড জীবনচক্র।
- আপনার অ্যাপে
ViewModelঅবজেক্টগুলি কীভাবে ব্যবহার করবেন। - কিভাবে
ViewModelProvider.Factoryইন্টারফেস ব্যবহার করেViewModelঅবজেক্ট তৈরি করবেন।
আপনি কি শিখবেন
- কি
LiveDataবস্তু দরকারী করে তোলে. -
ViewModelসংরক্ষিত ডেটাতে কীভাবেLiveDataযুক্ত করবেন। - কখন এবং কিভাবে
MutableLiveDataব্যবহার করবেন। -
LiveData. - একটি ব্যাকিং সম্পত্তি ব্যবহার করে কিভাবে
LiveDataএনক্যাপসুলেট করবেন। - কিভাবে একটি UI কন্ট্রোলার এবং এর সংশ্লিষ্ট
ViewModelমধ্যে যোগাযোগ করতে হয়।
আপনি কি করবেন
- GuessTheWord অ্যাপে শব্দ এবং স্কোরের জন্য
LiveDataব্যবহার করুন। - শব্দ বা স্কোর পরিবর্তিত হলে লক্ষ্য করে এমন পর্যবেক্ষকদের যোগ করুন।
- পরিবর্তিত মানগুলি প্রদর্শন করে এমন পাঠ্য দৃশ্যগুলি আপডেট করুন।
- একটি গেম-সমাপ্ত ইভেন্ট যোগ করতে
LiveDataপর্যবেক্ষক প্যাটার্ন ব্যবহার করুন। - আবার প্লে বোতামটি প্রয়োগ করুন।
পাঠ 5 কোডল্যাবগুলিতে, আপনি স্টার্টার কোড দিয়ে শুরু করে GuessTheWord অ্যাপ তৈরি করেন। GuessTheWord হল একটি দুই-প্লেয়ার চ্যারেড -স্টাইলের খেলা, যেখানে খেলোয়াড়রা সম্ভাব্য সর্বোচ্চ স্কোর অর্জন করতে সহযোগিতা করে।
প্রথম প্লেয়ার অ্যাপে থাকা শব্দগুলি দেখে এবং পালাক্রমে প্রতিটি কাজ করে, নিশ্চিত করে যে শব্দটি দ্বিতীয় প্লেয়ারকে না দেখায়৷ দ্বিতীয় খেলোয়াড় শব্দটি অনুমান করার চেষ্টা করে।
গেমটি খেলতে, প্রথম প্লেয়ার ডিভাইসে অ্যাপটি খোলে এবং একটি শব্দ দেখতে পায়, উদাহরণস্বরূপ "গিটার", যেমনটি নীচের স্ক্রিনশটে দেখানো হয়েছে৷
প্রথম খেলোয়াড় শব্দটি কার্যকর করে, সতর্কতা অবলম্বন করে যে শব্দটি নিজেই না বলে।
- যখন দ্বিতীয় প্লেয়ার সঠিকভাবে শব্দটি অনুমান করে, প্রথম প্লেয়ার Got It বোতাম টিপে, যা এক দ্বারা গণনা বৃদ্ধি করে এবং পরবর্তী শব্দটি দেখায়।
- যদি দ্বিতীয় প্লেয়ার শব্দটি অনুমান করতে না পারে, প্রথম খেলোয়াড় স্কিপ বোতাম টিপে, যা গণনা এক দ্বারা হ্রাস করে এবং পরবর্তী শব্দে চলে যায়।
- গেমটি শেষ করতে, এন্ড গেম বোতাম টিপুন। (এই কার্যকারিতা সিরিজের প্রথম কোডল্যাবের জন্য স্টার্টার কোডে নেই।)
এই কোডল্যাবে, আপনি গেমটি শেষ করার জন্য একটি ইভেন্ট যোগ করে GuessTheWord অ্যাপটিকে উন্নত করেন যখন ব্যবহারকারী অ্যাপের সমস্ত শব্দের মাধ্যমে চক্রাকারে যান। এছাড়াও আপনি স্কোর ফ্র্যাগমেন্টে একটি প্লে এগেইন বোতাম যোগ করুন, যাতে ব্যবহারকারী আবার গেমটি খেলতে পারেন।
শিরোনাম পর্দা |
খেলা পর্দা |
স্কোর স্ক্রীন |
এই কাজটিতে, আপনি এই কোডল্যাবের জন্য আপনার স্টার্টার কোডটি সনাক্ত করুন এবং চালান। আপনি আপনার স্টার্টার কোড হিসাবে পূর্ববর্তী কোডল্যাবে তৈরি করা GuessTheWord অ্যাপটি ব্যবহার করতে পারেন, অথবা আপনি একটি স্টার্টার অ্যাপ ডাউনলোড করতে পারেন।
- (ঐচ্ছিক) আপনি যদি আগের কোডল্যাব থেকে আপনার কোড ব্যবহার না করে থাকেন, তাহলে এই কোডল্যাবের জন্য স্টার্টার কোডটি ডাউনলোড করুন । কোডটি আনজিপ করুন এবং অ্যান্ড্রয়েড স্টুডিওতে প্রকল্পটি খুলুন।
- অ্যাপটি চালান এবং গেমটি খেলুন।
- লক্ষ্য করুন যে Skip বোতামটি পরবর্তী শব্দটি প্রদর্শন করে এবং একটি দ্বারা স্কোর হ্রাস করে এবং Got It বোতামটি পরবর্তী শব্দটি দেখায় এবং একটি দ্বারা স্কোর বৃদ্ধি করে। এন্ড গেম বোতামটি গেমটি শেষ করে।
LiveData হল একটি পর্যবেক্ষণযোগ্য ডেটা ধারক শ্রেণী যা জীবনচক্র-সচেতন। উদাহরণস্বরূপ, আপনি GuessTheWord অ্যাপে বর্তমান স্কোরের চারপাশে একটি LiveData মোড়ানো করতে পারেন। এই কোডল্যাবে, আপনি LiveData এর বিভিন্ন বৈশিষ্ট্য সম্পর্কে জানতে পারবেন:
-
LiveDataহল পর্যবেক্ষণযোগ্য, যার মানে হল যখনLiveDataঅবজেক্ট দ্বারা ধারণকৃত ডেটা পরিবর্তিত হয় তখন একজন পর্যবেক্ষককে অবহিত করা হয়। -
LiveDataডেটা ধারণ করে;LiveDataহল একটি মোড়ক যা যেকোনো ডেটার সাথে ব্যবহার করা যেতে পারে -
LiveDataহল লাইফসাইকেল-সচেতন, মানে এটি শুধুমাত্র এমন পর্যবেক্ষকদের আপডেট করে যারা একটি সক্রিয় জীবনচক্র অবস্থায় আছে যেমনSTARTEDবাRESUMED।
এই টাস্কে, আপনি কিভাবে GameViewModel এর বর্তমান স্কোর এবং বর্তমান শব্দ ডেটাকে LiveData এ রূপান্তর করে LiveData অবজেক্টে যেকোনও ডেটা টাইপ মোড়ানো শিখবেন। পরবর্তী একটি টাস্কে, আপনি এই LiveData অবজেক্টগুলিতে একজন পর্যবেক্ষক যোগ করুন এবং কিভাবে LiveData পর্যবেক্ষণ করতে হয় তা শিখুন।
ধাপ 1: LiveData ব্যবহার করতে স্কোর এবং শব্দ পরিবর্তন করুন
-
screens/gameপ্যাকেজের অধীনে,GameViewModelফাইলটি খুলুন। - পরিবর্তনশীল
scoreএবংwordধরন পরিবর্তন করেMutableLiveDataকরুন।
MutableLiveDataহল একটিLiveDataযার মান পরিবর্তন করা যায়।MutableLiveDataহল একটি জেনেরিক ক্লাস, তাই আপনাকে এটিতে থাকা ডেটার ধরন নির্দিষ্ট করতে হবে।
// The current word
val word = MutableLiveData<String>()
// The current score
val score = MutableLiveData<Int>()-
GameViewModelএ,initব্লকের ভিতরে,scoreএবংwordশুরু করুন। একটিLiveDataভেরিয়েবলের মান পরিবর্তন করতে, আপনি ভেরিয়েবলেsetValue()পদ্ধতি ব্যবহার করেন। কোটলিনে, আপনিvalueসম্পত্তি ব্যবহার করেsetValue()কল করতে পারেন।
init {
word.value = ""
score.value = 0
...
}ধাপ 2: LiveData অবজেক্ট রেফারেন্স আপডেট করুন
score এবং word ভেরিয়েবল এখন LiveData ধরনের। এই ধাপে, আপনি value সম্পত্তি ব্যবহার করে এই ভেরিয়েবলের রেফারেন্স পরিবর্তন করুন।
-
GameViewModelএ,onSkip()পদ্ধতিতে,scoreপরিবর্তন করেscore.valueকরুন।scoreসম্ভবতnullহওয়ার বিষয়ে ত্রুটিটি লক্ষ্য করুন। আপনি পরবর্তী এই ত্রুটি ঠিক করুন. - ত্রুটিটি সমাধান করতে,
onSkip()এscore.valueএ একটিnullচেক যোগ করুন। তারপরscoreminus()ফাংশন কল করুন, যাnull-safety সহ বিয়োগ সম্পাদন করে।
fun onSkip() {
if (!wordList.isEmpty()) {
score.value = (score.value)?.minus(1)
}
nextWord()
}- একইভাবে
onCorrect()পদ্ধতিটি আপডেট করুন:scoreভেরিয়েবলে একটিnullচেক যোগ করুন এবংplus()ফাংশনটি ব্যবহার করুন।
fun onCorrect() {
if (!wordList.isEmpty()) {
score.value = (score.value)?.plus(1)
}
nextWord()
}-
GameViewModelএ,nextWord()পদ্ধতির ভিতরে,wordরেফারেন্সwordপরিবর্তন করুন.value
private fun nextWord() {
if (!wordList.isEmpty()) {
//Select and remove a word from the list
word.value = wordList.removeAt(0)
}
}-
GameFragmentএ,updateWordText()পদ্ধতির ভিতরে,viewModel.wordথেকেviewModelএ রেফারেন্স পরিবর্তন করুন.word.value.
/** Methods for updating the UI **/
private fun updateWordText() {
binding.wordText.text = viewModel.word.value
}-
GameFragmentএ,updateScoreText()পদ্ধতির ভিতরে,viewModel.scoreএর রেফারেন্স পরিবর্তন করেviewModelকরুন.score.value.
private fun updateScoreText() {
binding.scoreText.text = viewModel.score.value.toString()
}-
GameFragmentএ,gameFinished()পদ্ধতির ভিতরে,viewModel.scoreএ রেফারেন্স পরিবর্তন করেviewModelকরুন.score.valueপ্রয়োজনীয়null-সেফটি চেক যোগ করুন।
private fun gameFinished() {
Toast.makeText(activity, "Game has just finished", Toast.LENGTH_SHORT).show()
val action = GameFragmentDirections.actionGameToScore()
action.score = viewModel.score.value?:0
NavHostFragment.findNavController(this).navigate(action)
}- আপনার কোডে কোন ত্রুটি আছে তা নিশ্চিত করুন। কম্পাইল করুন এবং আপনার অ্যাপ চালান। অ্যাপটির কার্যকারিতা আগের মতোই হওয়া উচিত।
এই টাস্কটি আগের টাস্কের সাথে ঘনিষ্ঠভাবে সম্পর্কিত, যেখানে আপনি স্কোর এবং শব্দ ডেটাকে LiveData অবজেক্টে রূপান্তর করেছেন। এই টাস্কে, আপনি সেই LiveData অবজেক্টের সাথে Observer অবজেক্ট সংযুক্ত করুন।
-
GameFragment,onCreateView()পদ্ধতির ভিতরে, বর্তমান স্কোর,viewModel.scoreএর জন্যLiveDataঅবজেক্টের সাথে একটিObserverঅবজেক্ট সংযুক্ত করুন।observe()পদ্ধতিটি ব্যবহার করুন এবংviewModelএর আরম্ভ করার পরে কোডটি রাখুন। কোডটি সরল করতে একটি ল্যাম্বডা এক্সপ্রেশন ব্যবহার করুন। (একটি ল্যাম্বডা এক্সপ্রেশন একটি বেনামী ফাংশন যা ঘোষণা করা হয় না, তবে একটি অভিব্যক্তি হিসাবে অবিলম্বে পাস করা হয়।)
viewModel.score.observe(this, Observer { newScore ->
}) Observer রেফারেন্সটি সমাধান করুন। এটি করার জন্য, Observer এ ক্লিক করুন, Alt+Enter টিপুন ( Mac-এ Option+Enter ), এবং androidx.lifecycle.Observer আমদানি করুন।
- আপনি যে পর্যবেক্ষকটি এইমাত্র তৈরি করেছেন সেটি একটি ইভেন্ট গ্রহণ করে যখন পর্যবেক্ষণ করা
LiveDataঅবজেক্ট দ্বারা ধারণকৃত ডেটা পরিবর্তিত হয়। পর্যবেক্ষকের ভিতরে, নতুন স্কোর সহTextViewস্কোর আপডেট করুন।
/** Setting up LiveData observation relationship **/
viewModel.score.observe(this, Observer { newScore ->
binding.scoreText.text = newScore.toString()
})- বর্তমান শব্দ
LiveDataঅবজেক্টের সাথে একটিObserverবস্তু সংযুক্ত করুন। আপনি বর্তমান স্কোরের সাথে একটিObserverবস্তু সংযুক্ত করেছেন একইভাবে এটি করুন।
/** Setting up LiveData observation relationship **/
viewModel.word.observe(this, Observer { newWord ->
binding.wordText.text = newWord
})যখন score বা word মান পরিবর্তিত হয়, তখন স্ক্রিনে প্রদর্শিত score বা word এখন স্বয়ংক্রিয়ভাবে আপডেট হয়।
-
GameFragmentএ,updateWordText()এবংupdateScoreText()পদ্ধতি এবং সেগুলির সমস্ত রেফারেন্স মুছে দিন। আপনার আর এগুলোর প্রয়োজন নেই, কারণ টেক্সট ভিউLiveDataপর্যবেক্ষক পদ্ধতি দ্বারা আপডেট করা হয়। - আপনার অ্যাপ চালান। আপনার গেম অ্যাপটি ঠিক আগের মতোই কাজ করা উচিত, কিন্তু এখন এটি
LiveDataএবংLiveDataপর্যবেক্ষক ব্যবহার করে।
এনক্যাপসুলেশন হল একটি বস্তুর কিছু ক্ষেত্রে সরাসরি অ্যাক্সেস সীমাবদ্ধ করার একটি উপায়। আপনি যখন একটি বস্তুকে এনক্যাপসুলেট করেন, তখন আপনি সর্বজনীন পদ্ধতির একটি সেট প্রকাশ করেন যা ব্যক্তিগত অভ্যন্তরীণ ক্ষেত্রগুলিকে সংশোধন করে। এনক্যাপসুলেশন ব্যবহার করে, আপনি নিয়ন্ত্রণ করেন কিভাবে অন্যান্য ক্লাস এই অভ্যন্তরীণ ক্ষেত্রগুলিকে ম্যানিপুলেট করে।
আপনার বর্তমান কোডে, যেকোনো বাহ্যিক শ্রেণী value বৈশিষ্ট্য ব্যবহার করে score এবং word ভেরিয়েবল পরিবর্তন করতে পারে, উদাহরণস্বরূপ viewModel.score.value ব্যবহার করে। আপনি এই কোডল্যাবে যে অ্যাপটি ডেভেলপ করছেন তাতে কিছু যায় আসে না, কিন্তু একটি প্রোডাকশন অ্যাপে, আপনি ViewModel অবজেক্টের ডেটার উপর নিয়ন্ত্রণ চান।
শুধুমাত্র ViewModel আপনার অ্যাপের ডেটা সম্পাদনা করবে। কিন্তু UI কন্ট্রোলারদের ডেটা পড়তে হবে, তাই ডেটা ক্ষেত্রগুলি সম্পূর্ণ ব্যক্তিগত হতে পারে না। আপনার অ্যাপের ডেটা এনক্যাপসুলেট করতে, আপনি MutableLiveData এবং LiveData অবজেক্ট উভয়ই ব্যবহার করেন।
MutableLiveData বনাম LiveData :
- একটি
MutableLiveDataঅবজেক্টের ডেটা পরিবর্তন করা যেতে পারে, যেমন নামটি বোঝায়।ViewModelভিতরে, ডেটা সম্পাদনাযোগ্য হওয়া উচিত, তাই এটিMutableLiveDataব্যবহার করে। - একটি
LiveDataঅবজেক্টের ডেটা পড়া যায়, কিন্তু পরিবর্তন করা যায় না।ViewModelএর বাইরে থেকে, ডেটা পাঠযোগ্য হওয়া উচিত, কিন্তু সম্পাদনাযোগ্য নয়, তাই ডেটাLiveDataহিসাবে প্রকাশ করা উচিত।
এই কৌশলটি চালানোর জন্য, আপনি একটি Kotlin ব্যাকিং সম্পত্তি ব্যবহার করুন। একটি ব্যাকিং প্রপার্টি আপনাকে সঠিক বস্তু ব্যতীত অন্য গেটার থেকে কিছু ফেরত দিতে দেয়। এই কাজটিতে, আপনি GuessTheWord অ্যাপে score এবং word বস্তুর জন্য একটি ব্যাকিং প্রপার্টি প্রয়োগ করেন।
স্কোর এবং শব্দে একটি ব্যাকিং সম্পত্তি যোগ করুন
-
GameViewModelএ, বর্তমানscoreঅবজেক্টটিকেprivateকরুন। - ব্যাকিং বৈশিষ্ট্যে ব্যবহৃত নামকরণের নিয়ম অনুসরণ করতে,
score_scoreএ পরিবর্তন করুন।_scoreসম্পত্তিটি এখন গেম স্কোরের পরিবর্তনযোগ্য সংস্করণ, যা অভ্যন্তরীণভাবে ব্যবহার করা হবে। -
LiveDataপ্রকারের একটি সর্বজনীন সংস্করণ তৈরি করুন, যাকে বলা হয়score।
// The current score
private val _score = MutableLiveData<Int>()
val score: LiveData<Int>- আপনি একটি আরম্ভ ত্রুটি দেখতে. এই ত্রুটিটি ঘটে কারণ
GameFragmentভিতরে,scoreএকটিLiveDataরেফারেন্স, এবংscoreআর এটির সেটার অ্যাক্সেস করতে পারে না। কোটলিনে গেটার এবং সেটার্স সম্পর্কে আরও জানতে, গেটার এবং সেটার্স দেখুন।
ত্রুটিটি সমাধান করতে,GameViewModelএscoreঅবজেক্টের জন্যget()পদ্ধতিটি ওভাররাইড করুন এবং ব্যাকিং প্রপার্টি,_scoreফেরত দিন।
val score: LiveData<Int>
get() = _score-
GameViewModelএ,scoreরেফারেন্সগুলি এর অভ্যন্তরীণ পরিবর্তনযোগ্য সংস্করণে পরিবর্তন করুন,_score।
init {
...
_score.value = 0
...
}
...
fun onSkip() {
if (!wordList.isEmpty()) {
_score.value = (score.value)?.minus(1)
}
...
}
fun onCorrect() {
if (!wordList.isEmpty()) {
_score.value = (score.value)?.plus(1)
}
...
}-
wordঅবজেক্টের নাম পরিবর্তন করে_wordএবং এর জন্য একটি ব্যাকিং প্রপার্টি যোগ করুন, যেমন আপনিscoreঅবজেক্টের জন্য করেছিলেন।
// The current word
private val _word = MutableLiveData<String>()
val word: LiveData<String>
get() = _word
...
init {
_word.value = ""
...
}
...
private fun nextWord() {
if (!wordList.isEmpty()) {
//Select and remove a word from the list
_word.value = wordList.removeAt(0)
}
}দুর্দান্ত কাজ, আপনি LiveData অবজেক্টের word এবং score এনক্যাপসুলেট করেছেন।
ব্যবহারকারী যখন এন্ড গেম বোতামে ট্যাপ করে তখন আপনার বর্তমান অ্যাপটি স্কোর স্ক্রিনে নেভিগেট করে। খেলোয়াড়রা সমস্ত শব্দের মাধ্যমে সাইকেল চালালে আপনি অ্যাপটিকে স্কোর স্ক্রিনে নেভিগেট করতে চান। খেলোয়াড়রা শেষ শব্দটি দিয়ে শেষ করার পরে, আপনি গেমটি স্বয়ংক্রিয়ভাবে শেষ করতে চান যাতে ব্যবহারকারীকে বোতামটি আলতো চাপতে না হয়।
এই কার্যকারিতা বাস্তবায়নের জন্য, আপনার একটি ইভেন্ট ট্রিগার করা এবং ViewModel থেকে খণ্ডের সাথে যোগাযোগ করা দরকার যখন সমস্ত শব্দ দেখানো হয়েছে৷ এটি করার জন্য, আপনি একটি গেম-সমাপ্ত ইভেন্ট মডেল করতে LiveData পর্যবেক্ষক প্যাটার্ন ব্যবহার করেন।
পর্যবেক্ষক প্যাটার্ন
পর্যবেক্ষক প্যাটার্ন হল একটি সফটওয়্যার ডিজাইন প্যাটার্ন। এটি বস্তুর মধ্যে যোগাযোগ নির্দিষ্ট করে: একটি পর্যবেক্ষণযোগ্য (পর্যবেক্ষণের "বিষয়") এবং পর্যবেক্ষক । একটি পর্যবেক্ষণযোগ্য একটি বস্তু যা তার অবস্থার পরিবর্তন সম্পর্কে পর্যবেক্ষকদের অবহিত করে।

এই অ্যাপে LiveData এর ক্ষেত্রে, পর্যবেক্ষণযোগ্য (বিষয়) হল LiveData অবজেক্ট, এবং পর্যবেক্ষক হল UI কন্ট্রোলারের পদ্ধতি, যেমন টুকরা। যখনই LiveData ভিতরে মোড়ানো ডেটা পরিবর্তিত হয় তখনই একটি রাজ্যের পরিবর্তন ঘটে। ViewModel থেকে টুকরোতে যোগাযোগ করার জন্য LiveData ক্লাসগুলি অত্যন্ত গুরুত্বপূর্ণ৷
ধাপ 1: একটি গেম-সমাপ্ত ইভেন্ট সনাক্ত করতে LiveData ব্যবহার করুন
এই টাস্কে, আপনি একটি গেম-সমাপ্ত ইভেন্ট মডেল করতে LiveData পর্যবেক্ষক প্যাটার্ন ব্যবহার করেন।
-
GameViewModelএ,_eventGameFinishনামে একটিBooleanMutableLiveDataঅবজেক্ট তৈরি করুন। এই বস্তুটি গেম-সমাপ্ত ইভেন্টটি ধরে রাখবে। -
_eventGameFinishঅবজেক্ট আরম্ভ করার পরে,eventGameFinishনামে একটি ব্যাকিং প্রপার্টি তৈরি করুন এবং আরম্ভ করুন।
// Event which triggers the end of the game
private val _eventGameFinish = MutableLiveData<Boolean>()
val eventGameFinish: LiveData<Boolean>
get() = _eventGameFinish-
GameViewModelএ, একটিonGameFinish()পদ্ধতি যোগ করুন। পদ্ধতিতে, গেম-সমাপ্ত ইভেন্ট,eventGameFinish,trueসেট করুন।
/** Method for the game completed event **/
fun onGameFinish() {
_eventGameFinish.value = true
}-
GameViewModelএ,nextWord()পদ্ধতির ভিতরে, শব্দ তালিকা খালি থাকলে গেমটি শেষ করুন।
private fun nextWord() {
if (wordList.isEmpty()) {
onGameFinish()
} else {
//Select and remove a _word from the list
_word.value = wordList.removeAt(0)
}
}-
GameFragmentএ,onCreateView()এর ভিতরে,viewModelশুরু করার পর,eventGameFinishএ একজন পর্যবেক্ষক সংযুক্ত করুন।observe()পদ্ধতি ব্যবহার করুন। ল্যাম্বডা ফাংশনের ভিতরে,gameFinished()পদ্ধতিতে কল করুন।
// Observer for the Game finished event
viewModel.eventGameFinish.observe(this, Observer<Boolean> { hasFinished ->
if (hasFinished) gameFinished()
})- আপনার অ্যাপ চালান, গেম খেলুন এবং সমস্ত শব্দের মধ্য দিয়ে যান। আপনি End Game এ ট্যাপ না করা পর্যন্ত গেমের অংশে থাকার পরিবর্তে অ্যাপটি স্বয়ংক্রিয়ভাবে স্কোর স্ক্রিনে নেভিগেট করে।
শব্দ তালিকা খালি হওয়ার পরে,eventGameFinishসেট করা হয়, গেমের খণ্ডে সংশ্লিষ্ট পর্যবেক্ষক পদ্ধতিকে কল করা হয় এবং অ্যাপটি স্ক্রিন ফ্র্যাগমেন্টে নেভিগেট করে। - আপনার যোগ করা কোড একটি জীবনচক্র সমস্যা চালু করেছে। সমস্যাটি বুঝতে,
GameFragmentক্লাসে,gameFinished()পদ্ধতিতে নেভিগেশন কোডটি মন্তব্য করুন। পদ্ধতিতেToastবার্তা রাখতে ভুলবেন না।
private fun gameFinished() {
Toast.makeText(activity, "Game has just finished", Toast.LENGTH_SHORT).show()
// val action = GameFragmentDirections.actionGameToScore()
// action.score = viewModel.score.value?:0
// NavHostFragment.findNavController(this).navigate(action)
}
- আপনার অ্যাপ চালান, গেম খেলুন এবং সমস্ত শব্দের মধ্য দিয়ে যান। একটি টোস্ট বার্তা যা বলে "গেম সবে শেষ হয়েছে" গেম স্ক্রিনের নীচে সংক্ষেপে প্রদর্শিত হবে, যা প্রত্যাশিত আচরণ।
এখন ডিভাইস বা এমুলেটর ঘোরান। টোস্ট আবার প্রদর্শন! ডিভাইসটি আরও কয়েকবার ঘোরান, এবং আপনি সম্ভবত প্রতিবার টোস্ট দেখতে পাবেন। এটি একটি বাগ, কারণ টোস্ট শুধুমাত্র একবার প্রদর্শন করা উচিত, যখন খেলা শেষ হয়। প্রতিবার খণ্ডটি পুনরায় তৈরি করার সময় টোস্টটি প্রদর্শন করা উচিত নয়। আপনি পরবর্তী টাস্কে এই সমস্যাটি সমাধান করুন।
|
|
ধাপ 2: গেম-সমাপ্ত ইভেন্ট রিসেট করুন
সাধারণত, LiveData শুধুমাত্র ডেটা পরিবর্তিত হলেই পর্যবেক্ষকদের কাছে আপডেট প্রদান করে। এই আচরণের একটি ব্যতিক্রম হল যখন পর্যবেক্ষক একটি নিষ্ক্রিয় থেকে একটি সক্রিয় অবস্থায় পরিবর্তিত হয় তখন পর্যবেক্ষকরাও আপডেট পান।
এই কারণেই আপনার অ্যাপে গেম-সমাপ্ত টোস্ট বারবার ট্রিগার হয়। যখন স্ক্রীন ঘূর্ণনের পরে গেমের খণ্ডটি পুনরায় তৈরি করা হয়, তখন এটি একটি নিষ্ক্রিয় থেকে একটি সক্রিয় অবস্থায় চলে যায়। খণ্ডের পর্যবেক্ষক বিদ্যমান ViewModel সাথে পুনরায় সংযুক্ত হয় এবং বর্তমান ডেটা গ্রহণ করে। gameFinished() পদ্ধতিটি পুনরায় ট্রিগার করা হয় এবং টোস্ট প্রদর্শন করা হয়।
এই টাস্কে, আপনি এই সমস্যাটি ঠিক করুন এবং GameViewModel এ eventGameFinish পতাকা রিসেট করে শুধুমাত্র একবার টোস্ট প্রদর্শন করুন।
-
GameViewModelএ, গেম সমাপ্ত ইভেন্ট,_eventGameFinishরিসেট করতে একটিonGameFinishComplete()পদ্ধতি যোগ করুন।
/** Method for the game completed event **/
fun onGameFinishComplete() {
_eventGameFinish.value = false
}-
GameFragmentএ,gameFinished()এর শেষে,viewModelঅবজেক্টেonGameFinishComplete()কল করুন। (gameFinished()এ নেভিগেশন কোড ছেড়ে দিন এখনের জন্য মন্তব্য করা হয়েছে।)
private fun gameFinished() {
...
viewModel.onGameFinishComplete()
}- অ্যাপটি চালান এবং গেমটি খেলুন। সমস্ত শব্দের মধ্য দিয়ে যান, তারপর ডিভাইসের পর্দার অভিযোজন পরিবর্তন করুন। টোস্ট শুধুমাত্র একবার প্রদর্শিত হয়.
-
GameFragmentএ,gameFinished()পদ্ধতির ভিতরে, নেভিগেশন কোডটি আনকমেন্ট করুন।
অ্যান্ড্রয়েড স্টুডিওতে মন্তব্য করার জন্য, মন্তব্য করা লাইনগুলি নির্বাচন করুন এবংControl+/( একটি ম্যাকেCommand+/) টিপুন।
private fun gameFinished() {
Toast.makeText(activity, "Game has just finished", Toast.LENGTH_SHORT).show()
val action = GameFragmentDirections.actionGameToScore()
action.score = viewModel.score.value?:0
findNavController(this).navigate(action)
viewModel.onGameFinishComplete()
}Android Studio দ্বারা অনুরোধ করা হলে, androidx.navigation.fragment.NavHostFragment.findNavController আমদানি করুন।
- অ্যাপটি চালান এবং গেমটি খেলুন। আপনি সমস্ত শব্দের মধ্য দিয়ে যাওয়ার পরে অ্যাপটি চূড়ান্ত স্কোর স্ক্রিনে স্বয়ংক্রিয়ভাবে নেভিগেট করে তা নিশ্চিত করুন।
|
|
দারুণ কাজ! আপনার অ্যাপটি গেম-সমাপ্ত ইভেন্টকে ট্রিগার করতে GameViewModel থেকে গেমের খণ্ডটিতে যোগাযোগ করতে LiveData ব্যবহার করে যে শব্দ তালিকাটি খালি রয়েছে। গেমের খণ্ডটি তারপর স্কোর খণ্ডে নেভিগেট করে।
এই টাস্কে, আপনি ScoreViewModel এ একটি LiveData অবজেক্টে স্কোর পরিবর্তন করুন এবং এতে একজন পর্যবেক্ষক সংযুক্ত করুন। আপনি যখন GameViewModel এ LiveData যোগ করেছিলেন তখন আপনি যা করেছিলেন এই কাজটি একই রকম।
আপনি সম্পূর্ণতার জন্য ScoreViewModel এ এই পরিবর্তনগুলি করেন, যাতে আপনার অ্যাপের সমস্ত ডেটা LiveData ব্যবহার করে।
-
ScoreViewModelএ,scoreভেরিয়েবলের ধরনটিকেMutableLiveDataএ পরিবর্তন করুন। নিয়মানুযায়ী_scoreএ এটির নাম পরিবর্তন করুন এবং একটি ব্যাকিং প্রপার্টি যোগ করুন।
private val _score = MutableLiveData<Int>()
val score: LiveData<Int>
get() = _score-
ScoreViewModelএ,initব্লকের ভিতরে,_scoreশুরু করুন। আপনি আপনার পছন্দ মতোinitব্লকে লগটি সরাতে বা ছেড়ে দিতে পারেন।
init {
_score.value = finalScore
}-
ScoreFragmentএ,onCreateView()ভিতরে,viewModelশুরু করার পর, স্কোরLiveDataঅবজেক্টের জন্য একজন পর্যবেক্ষক সংযুক্ত করুন। ল্যাম্বডা এক্সপ্রেশনের ভিতরে, স্কোর টেক্সট ভিউতে স্কোর মান সেট করুন।ViewModelথেকে স্কোর মান সহ পাঠ্য দৃশ্যকে সরাসরি বরাদ্দ করে এমন কোডটি সরান।
যোগ করার জন্য কোড:
// Add observer for score
viewModel.score.observe(this, Observer { newScore ->
binding.scoreText.text = newScore.toString()
})সরানোর জন্য কোড:
binding.scoreText.text = viewModel.score.toString()Android Studio দ্বারা অনুরোধ করা হলে, androidx.lifecycle.Observer আমদানি করুন।
- আপনার অ্যাপটি চালান এবং গেমটি খেলুন। অ্যাপটি আগের মতো কাজ করা উচিত, কিন্তু এখন এটি স্কোর আপডেট করতে
LiveDataএবং একজন পর্যবেক্ষক ব্যবহার করে।
এই টাস্কে, আপনি স্কোর স্ক্রিনে একটি প্লে এগেইন বোতাম যোগ করুন এবং একটি LiveData ইভেন্ট ব্যবহার করে এটির ক্লিক শ্রোতাকে প্রয়োগ করুন। বোতামটি স্কোর স্ক্রীন থেকে গেম স্ক্রিনে নেভিগেট করার জন্য একটি ইভেন্টকে ট্রিগার করে।
অ্যাপের জন্য স্টার্টার কোডে প্লে এগেইন বোতাম রয়েছে, কিন্তু বোতামটি লুকানো আছে।
-
res/layout/score_fragment.xmlএ,play_again_buttonবোতামের জন্য,visibilityবৈশিষ্ট্যের মানvisibleপরিবর্তন করুন।
<Button
android:id="@+id/play_again_button"
...
android:visibility="visible"
/>-
ScoreViewModelএ,_eventPlayAgainনামকBooleanধরে রাখতে একটিLiveDataঅবজেক্ট যোগ করুন। স্কোর স্ক্রীন থেকে গেম স্ক্রিনে নেভিগেট করতেLiveDataইভেন্ট সংরক্ষণ করতে এই বস্তুটি ব্যবহার করা হয়।
private val _eventPlayAgain = MutableLiveData<Boolean>()
val eventPlayAgain: LiveData<Boolean>
get() = _eventPlayAgain-
ScoreViewModelএ, ইভেন্ট সেট এবং রিসেট করার পদ্ধতি সংজ্ঞায়িত করুন,_eventPlayAgain।
fun onPlayAgain() {
_eventPlayAgain.value = true
}
fun onPlayAgainComplete() {
_eventPlayAgain.value = false
}-
ScoreFragment,eventPlayAgainজন্য একজন পর্যবেক্ষক যোগ করুন।returnস্টেটমেন্টের আগেonCreateView()এর শেষে কোডটি রাখুন। ল্যাম্বডা এক্সপ্রেশনের ভিতরে, গেম স্ক্রিনে ফিরে যান এবংeventPlayAgainরিসেট করুন।
// Navigates back to game when button is pressed
viewModel.eventPlayAgain.observe(this, Observer { playAgain ->
if (playAgain) {
findNavController().navigate(ScoreFragmentDirections.actionRestart())
viewModel.onPlayAgainComplete()
}
})androidx.navigation.fragment.findNavController আমদানি করুন, যখন Android Studio দ্বারা প্রম্পট করা হবে।
-
ScoreFragmentএ,onCreateView()এর ভিতরে, PlayAgain বোতামে একটি ক্লিক শ্রোতা যোগ করুন এবংviewModel.onPlayAgain()কল করুন।
binding.playAgainButton.setOnClickListener { viewModel.onPlayAgain() }- আপনার অ্যাপটি চালান এবং গেমটি খেলুন। গেমটি শেষ হয়ে গেলে, স্কোর স্ক্রীন চূড়ান্ত স্কোর এবং আবার প্লে বোতামটি দেখায়। PlayAgain বোতামটি আলতো চাপুন, এবং অ্যাপটি গেম স্ক্রিনে নেভিগেট করে যাতে আপনি আবার গেমটি খেলতে পারেন।

ভালো কাজ! আপনি ViewModel এ LiveData অবজেক্ট ব্যবহার করতে আপনার অ্যাপের আর্কিটেকচার পরিবর্তন করেছেন এবং আপনি LiveData অবজেক্টের সাথে পর্যবেক্ষকদের সংযুক্ত করেছেন। LiveData দ্বারা ধারণকৃত মান পরিবর্তিত হলে LiveData পর্যবেক্ষক বস্তুকে অবহিত করে।
অ্যান্ড্রয়েড স্টুডিও প্রকল্প: GuessTheWord
লাইভডেটা
-
LiveDataহল একটি পর্যবেক্ষণযোগ্য ডেটা ধারক শ্রেণী যা জীবনচক্র-সচেতন, Android আর্কিটেকচার উপাদানগুলির মধ্যে একটি৷ - ডেটা আপডেট হলে স্বয়ংক্রিয়ভাবে আপডেট হতে আপনার UI সক্ষম করতে আপনি
LiveDataব্যবহার করতে পারেন। -
LiveDataপর্যবেক্ষণযোগ্য, যার মানে হল যে কোনও ক্রিয়াকলাপ বা একটি খণ্ডের মতো একজন পর্যবেক্ষককে অবহিত করা যেতে পারে যখনLiveDataঅবজেক্টের কাছে থাকা ডেটা পরিবর্তিত হয়। -
LiveDataডেটা ধারণ করে; এটি একটি মোড়ক যা যেকোনো তথ্যের সাথে ব্যবহার করা যেতে পারে। -
LiveDataহল লাইফসাইকেল-সচেতন, মানে এটি শুধুমাত্র এমন পর্যবেক্ষকদের আপডেট করে যারা একটি সক্রিয় জীবনচক্র অবস্থায় আছে যেমনSTARTEDবাRESUMED।
LiveData যোগ করতে
-
ViewModelএ ডেটা ভেরিয়েবলের ধরনLiveDataবাMutableLiveDataএ পরিবর্তন করুন।
MutableLiveData হল একটি LiveData অবজেক্ট যার মান পরিবর্তন করা যায়। MutableLiveData হল একটি জেনেরিক ক্লাস, তাই আপনাকে এটিতে থাকা ডেটার ধরন নির্দিষ্ট করতে হবে।
-
LiveDataদ্বারা ধারণকৃত ডেটার মান পরিবর্তন করতে,LiveDataভেরিয়েবলেsetValue()পদ্ধতি ব্যবহার করুন।
LiveData encapsulate করতে
-
ViewModelভিতরে থাকাLiveDataসম্পাদনাযোগ্য হওয়া উচিত।ViewModelএর বাইরে,LiveDataপাঠযোগ্য হওয়া উচিত। এটি একটি Kotlin ব্যাকিং সম্পত্তি ব্যবহার করে প্রয়োগ করা যেতে পারে। - একটি কোটলিন ব্যাকিং প্রপার্টি আপনাকে সঠিক বস্তু ব্যতীত অন্য কোনো গেটার থেকে কিছু ফেরত দিতে দেয়।
-
LiveDataএনক্যাপসুলেট করতে,ViewModelভিতরেprivateMutableLiveDataব্যবহার করুন এবংViewModelবাইরে একটিLiveDataব্যাকিং প্রপার্টি ফেরত দিন।
পর্যবেক্ষণযোগ্য লাইভডেটা
-
LiveDataএকটি পর্যবেক্ষক প্যাটার্ন অনুসরণ করে। "পর্যবেক্ষণযোগ্য" হলLiveDataঅবজেক্ট, এবং পর্যবেক্ষক হল UI কন্ট্রোলারের পদ্ধতি, যেমন টুকরো টুকরো। যখনইLiveDataভিতরে মোড়ানো ডেটা পরিবর্তিত হয়, UI কন্ট্রোলারগুলিতে পর্যবেক্ষক পদ্ধতিগুলিকে অবহিত করা হয়। -
LiveDataপর্যবেক্ষণযোগ্য করতে,observe()পদ্ধতি ব্যবহার করে পর্যবেক্ষকদের (যেমন কার্যকলাপ এবং টুকরা)LiveDataরেফারেন্সের সাথে একটি পর্যবেক্ষক বস্তু সংযুক্ত করুন। - এই
LiveDataপর্যবেক্ষক প্যাটার্নটিViewModelথেকে UI কন্ট্রোলারের সাথে যোগাযোগ করতে ব্যবহার করা যেতে পারে।
উদাসীনতা কোর্স:
অ্যান্ড্রয়েড বিকাশকারী ডকুমেন্টেশন:
অন্যান্য:
- কোটলিনে ব্যাকিং সম্পত্তি
এই বিভাগে একজন প্রশিক্ষকের নেতৃত্বে একটি কোর্সের অংশ হিসাবে এই কোডল্যাবের মাধ্যমে কাজ করা শিক্ষার্থীদের জন্য সম্ভাব্য হোমওয়ার্ক অ্যাসাইনমেন্ট তালিকাভুক্ত করা হয়েছে। নিম্নলিখিতগুলি করা প্রশিক্ষকের উপর নির্ভর করে:
- প্রয়োজনে হোমওয়ার্ক বরাদ্দ করুন।
- শিক্ষার্থীদের সাথে যোগাযোগ করুন কিভাবে হোমওয়ার্ক অ্যাসাইনমেন্ট জমা দিতে হয়।
- হোমওয়ার্ক অ্যাসাইনমেন্ট গ্রেড.
প্রশিক্ষকরা এই পরামর্শগুলি যতটা কম বা যতটা চান ততটা ব্যবহার করতে পারেন, এবং তাদের উপযুক্ত মনে করে অন্য কোনও হোমওয়ার্ক বরাদ্দ করতে নির্দ্বিধায় করা উচিত।
আপনি যদি নিজে থেকে এই কোডল্যাবের মাধ্যমে কাজ করে থাকেন, তাহলে আপনার জ্ঞান পরীক্ষা করার জন্য এই হোমওয়ার্ক অ্যাসাইনমেন্টগুলিকে নির্দ্বিধায় ব্যবহার করুন৷
এই প্রশ্নগুলোর উত্তর দাও
প্রশ্ন 1
আপনি কীভাবে একটি ViewModel সংরক্ষিত LiveData এনক্যাপসুলেট করবেন যাতে বাহ্যিক বস্তুগুলি আপডেট না করেই ডেটা পড়তে পারে?
-
ViewModelঅবজেক্টের ভিতরে, ডেটার ডেটা টাইপকেprivateLiveDataপরিবর্তন করুন।MutableLiveDataপ্রকারের শুধুমাত্র পঠনযোগ্য ডেটা প্রকাশ করতে একটি ব্যাকিং সম্পত্তি ব্যবহার করুন। -
ViewModelঅবজেক্টের ভিতরে, ডেটার ডেটা টাইপকেprivateMutableLiveDataএ পরিবর্তন করুন।LiveDataপ্রকারের শুধুমাত্র পঠনযোগ্য ডেটা প্রকাশ করতে একটি ব্যাকিং সম্পত্তি ব্যবহার করুন। - UI কন্ট্রোলারের ভিতরে, ডেটার ডেটা প্রকারকে
privateMutableLiveDataএ পরিবর্তন করুন।LiveDataপ্রকারের শুধুমাত্র পঠনযোগ্য ডেটা প্রকাশ করতে একটি ব্যাকিং সম্পত্তি ব্যবহার করুন। -
ViewModelঅবজেক্টের ভিতরে, ডাটার ডাটা টাইপকেLiveDataএ পরিবর্তন করুন।LiveDataপ্রকারের শুধুমাত্র পঠনযোগ্য ডেটা প্রকাশ করতে একটি ব্যাকিং সম্পত্তি ব্যবহার করুন।
প্রশ্ন 2
UI কন্ট্রোলার নিচের কোন অবস্থায় থাকলে LiveData একটি UI কন্ট্রোলার (যেমন একটি খণ্ড) আপডেট করে?
- আবার শুরু হয়েছে
- ব্যাকগ্রাউন্ডে
- বিরতি দেওয়া হয়েছে
- থেমে গেল
প্রশ্ন 3
LiveData পর্যবেক্ষক প্যাটার্নে, পর্যবেক্ষণযোগ্য আইটেমটি কী (কী পর্যবেক্ষণ করা হয়)?
- পর্যবেক্ষক পদ্ধতি
- একটি
LiveDataঅবজেক্টের ডেটা - UI কন্ট্রোলার
-
ViewModelঅবজেক্ট
পরবর্তী পাঠ শুরু করুন:
এই কোর্সে অন্যান্য কোডল্যাবগুলির লিঙ্কগুলির জন্য, Android Kotlin Fundamentals codelabs ল্যান্ডিং পৃষ্ঠাটি দেখুন।




