Fragment Lifecycle — Android Fragment hayoti davomida chaqiradigan metod-qayta chaqiruvlarning qat’iy belgilangan ketma-ketligi: yaratilishdan (onAttach) to’liq olib tashlashgacha (onDetach). Fragment Activity-ga qaraganda murakkabroq hayot siklga ega — 11 holat va 7 asosiy qayta chaqiruvni o‘z ichiga oladi. Fragment Lifecycle FragmentManager orqali boshqariladi va uni o‘z ichiga olgan Activity hayot sikli bilan chambarchas bog‘liq. Google ma’lumotlariga ko‘ra, Fragment API Level 21+ da ishlaydigan Android ilovalarining 74%ida qo‘llaniladi, bu Fragment Lifecycle-ni tushunishni professional Android dasturlash uchun majburiy qiladi. Android-ning Fragment Lifecycle haqidagi hujjatlari barcha holatlar va chaqiruv kafolatlarini tavsiflaydi.
Asosiy ma’lumotlar
Fragment Lifecycle — har bir Fragment namunasining yaratilishdan yo‘q qilinishgacha o‘tadigan o‘zaro bog‘liq holatlar va metodlar to‘plami. Activity-dan farqli o‘laroq, Fragment hayot sikli ikki kontekst bilan bog‘liq: Fragmentning o‘zi (onAttach dan onDetach gacha yashaydi) va uning View (onCreateView dan onDestroyView gacha yashaydi). Bu bo‘linish Fragmentning asosiy xususiyati bo‘lib, Fragmentning o‘zini yo‘q qilmasdan ekran aylanishida View yo‘q qilinishini yashab qolishga imkon beradi.
Fragment qayta chaqiruvlarining to‘liq ketma-ketligi:
Google ga ko‘ra, zamonaviy ilovada o‘rtacha fragment foydalanuvchi sessiyasida 3–5 marta to‘liq sikl o‘tadi (ekran aylanishlari va navigatsiya sababli). Barcha fazalarni to‘g‘ri qayta ishlash UI barqarorligining asosidir.
FragmentManager Fragment ni besh asosiy holat orqali boshqaradi, Fragment.State sinfida belgilangan. Har bir holat bajarilgan qayta chaqiruvlarning ma’lum to‘plamiga mos keladi.
| Holat | Ma’nosi | Bajarilgan qayta chaqiruvlar |
|---|---|---|
| INITIALIZED | Fragment yaratilgan, lekin View hali yo‘q | onAttach, onCreate |
| CREATED | View yaratilgan, lekin Fragment ko‘rinmaydi | + onCreateView, onViewCreated |
| STARTED | Fragment ko‘rinadi, lekin faol emas | + onStart |
| RESUMED | Fragment faol, foydalanuvchi bilan o‘zaro aloqada | + onResume |
| DESTROYED | Fragment yo‘q qilingan | + onDestroyView, onDestroy, onDetach |
FragmentManager Fragment ni foydalanuvchi harakatlari va tizim hodisalariga qarab holatlar o‘rtasida harakatlantiradi. Fragment konteynerga qo‘shilganda, u ketma-ket INITIALIZED → CREATED → STARTED → RESUMED o‘tadi. Olib tashlanganda — RESUMED → STARTED → CREATED → DESTROYED.
CREATED holati — alohida: View yo‘q qilinishi mumkin (onDestroyView dan keyin), lekin Fragmentning o‘zi CREATED holatida qoladi (onDestroyView dan keyin, onDestroy dan oldin). Bu FragmentManager ga Fragmentni Viewsiz xotirada saqlashga imkon beradi, bu ekran aylanishlarini yashab qolish uchun zarur.
Fragment Lifecycle va Activity Lifecycle chambarchas bog‘liq, lekin tub farqlarga ega. Fragment har doim Activity ichida yashaydi va uning hayot sikli Activity-xo‘jayinga bog‘liq, lekin unga bir xil emas.
| Aspekt | Activity | Fragment |
|---|---|---|
| Qayta chaqiruvlar soni | 7 (onCreate … onDestroy) | 11 (onAttach … onDetach) |
| View uchun alohida Lifecycle | Yo‘q | Ha (viewLifecycleOwner) |
| Aylanishni yashaydi | Yo‘q (yo‘q qilinadi) | Ha (ViewModel + Fragment yashab qoladi) |
| Xostga bog‘liqlik | Yo‘q | Activity Lifecycle ga bog‘liq |
| Holatni saqlash | onSaveInstanceState | onSaveInstanceState (fragment bo‘yicha) |
| Boshqaruv | Tizim | FragmentManager |
Asosiy amaliy farq: ekran aylanishida Activity to‘liq yo‘q qilinadi (onDestroy) va qayta yaratiladi (onCreate). Fragment aylanishda onDestroyView (View yo‘q qilinadi) → onCreateView (View qayta yaratiladi) o‘tadi, lekin Fragmentning o‘zi va uning ViewModeli tirik qoladi. Bu Fragment ni konfiguratsiya o‘zgarishlarini yashab qolishi kerak bo‘lgan UI mantiqi uchun ideal konteyner qiladi.
Ekran aylanishidagi chaqiruvlar tartibi: Activity.onPause → Fragment.onPause → Activity.onStop → Fragment.onStop → Activity.onDestroy → Fragment.onDestroyView → (Activity yo‘q qilindi) → Activity.onCreate → Fragment.onAttach → Fragment.onCreate → Fragment.onCreateView → Fragment.onViewCreated → Activity.onStart → Fragment.onStart → Activity.onResume → Fragment.onResume.
FragmentManager — fragmentlarni qo‘shish, olib tashlash, almashtirish va ularning holatlarini boshqarish uchun mas’ul markaziy sinf. FragmentManager BackStack stekini yuritadi va tranzaksiyalarda qayta chaqiruvlarning to‘g‘ri tartibini kafolatlaydi. Har bir Activity va har bir ichki joylashgan Fragment o‘z FragmentManageriga ega.
FragmentManager ning asosiy operatsiyalari:
BackStack — FragmentManager tranzaksiyalari steki. Tizim “Orqaga” tugmasi bosilganda BackStack dagi oxirgi tranzaksiya bekor qilinadi (popBackStack()). popBackStack orqali olib tashlangan Fragment tiklanadi. Agar BackStack bo‘sh bo‘lsa, “Orqaga” bosilishi Activity ni tugatadi.
Google ma’lumotlariga ko‘ra, Fragment bilan bog‘liq muammolarning 78%i (takrorlanish, bo‘sh ekranlar, IllegalStateException) FragmentManager dan noto‘g‘ri foydalanish bilan bog‘liq. Asosiy qoida: tranzaksiyalarni kontekstga qarab commit() (asinxron) yoki commitNow() (sinxron) orqali bajaring. commit() ko‘p tranzaksiyalarda to‘g‘ri tartibni kafolatlaydi.
Fragment onSaveInstanceState orqali o‘z holatini saqlash mexanizmini qo‘llab-quvvatlaydi, u Activity dan mustaqil ishlaydi. Fragment holatni Bundle da saqlaydi, u tiklashda onCreate va onCreateView ga uzatiladi.
Fragment qachon holatni saqlaydi:
Zamonaviy yondashuv: Fragment holatini saqlash uchun ViewModel da SavedStateHandle dan foydalaning. SavedStateHandle ekran aylanishi va process death da avtomatik ravishda ma’lumotlarni saqlaydi va tiklaydi, qo‘lda onSaveInstanceState talab qilmaydi. Google SavedStateHandle ni Fragment da UI holatini saqlashning afzal usuli sifatida tavsiya qiladi.
setRetainInstance (Fragment 1.3 dan eskirgan): ilgari Fragment ekran aylanishida setRetainInstance(true) orqali saqlanishi mumkin edi. Bu yondashuv ViewModel + SavedStateHandle bilan almashtirilgan bo‘lib, ular ishonchliroq ishlaydi va maxsus sozlashni talab qilmaydi.
viewLifecycleOwner — Fragment View bilan bog‘liq Lifecycle (onCreateView dan onDestroyView gacha). Bu prinsipial jihatdan muhim tushuncha: viewLifecycleOwner orqali qilingan LiveData/Flow obunalari View yo‘q qilinishida (onDestroyView) avtomatik bekor qilinadi, lekin Fragmentning o‘ziga ta’sir qilmaydi.
viewLifecycleOwner va Fragment lifecycle o‘rtasidagi farq:
Bu nima uchun muhim: agar LiveData ga Fragment lifecycle (this) orqali obuna bo‘lsangiz, onDestroyView dan keyin obuna faol qoladi va LiveData null View ni yangilashga urinib, NPE ga sabab bo‘ladi. viewLifecycleOwner orqali obuna onDestroyView dan keyin hech qanday UI yangilanishi bo‘lmasligini kafolatlaydi.
Qoida: Fragment da har doim UI bilan bog‘liq LiveData, Flow va korutin obunalari uchun viewLifecycleOwner dan foydalaning. ViewModel korutinlari uchun viewModelScope dan foydalaning — u ViewModel ga bog‘liq, Fragment ga emas.
UI ni to‘g‘ri ishga tushirish va viewLifecycleOwner orqali LiveData obunasini namoyish etadi.
class UserListFragment : Fragment() {
private val viewModel: UserListViewModel by viewModels()
override fun onCreateView(
inflater: LayoutInflater,
container: ViewGroup?,
savedInstanceState: Bundle?
): View {
return inflater.inflate(R.layout.fragment_user_list, container, false)
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
val button: Button = view.findViewById(R.id.load_button)
button.setOnClickListener { viewModel.loadUsers() }
viewModel.users.observe(viewLifecycleOwner) { users ->
Log.d("UserListFragment", "Ro‘yxatni yangilash: ${users.size} foydalanuvchi")
}
}
override fun onDestroyView() {
super.onDestroyView()
Log.d("UserListFragment", "onDestroyView: View yo‘q qilindi")
}
}
Fragment onCreateView da layout ni shishiradi, UI ni sozlaydi va onViewCreated da LiveData ga obuna bo‘ladi. viewLifecycleOwner orqali obuna — xotira sizib ketishining oldini olish uchun majburiy talab. onDestroyView View yo‘q qilinishini qayd qiladi — Fragment ekran aylanishini yashab qolishini tasdiqlaydi.
Activity da FragmentManager orqali Fragment qo‘shish, BackStack bilan almashtirish va tiklashni namoyish etadi.
class HostActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_host)
if (savedInstanceState == null) {
supportFragmentManager.beginTransaction()
.add(R.id.fragment_container, HomeFragment())
.addToBackStack(null)
.commit()
}
}
fun openDetail(userId: String) {
supportFragmentManager.beginTransaction()
.replace(R.id.fragment_container, DetailFragment.newInstance(userId))
.addToBackStack(null)
.commit()
}
override fun onBackPressed() {
if (supportFragmentManager.backStackEntryCount > 0) {
supportFragmentManager.popBackStack()
} else {
super.onBackPressed()
}
}
}
class DetailFragment : Fragment() {
companion object {
fun newInstance(userId: String): DetailFragment {
return DetailFragment().apply {
arguments = Bundle().apply { putString("user_id", userId) }
}
}
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
val userId = arguments?.getString("user_id")
Log.d("DetailFragment", "Foydalanuvchi tafsilotlarini yuklash: $userId")
}
}
Activity fragmentlarni boshqarish uchun supportFragmentManager dan foydalanadi. BackStack bilan add() tranzaksiyasi “Orqaga” bosilganda HomeFragment tiklanishini kafolatlaydi. openDetail() joriy Fragment ni argumentlar bilan DetailFragment ga almashtiradi. savedInstanceState == null tekshiruvi ekran aylanishida fragmentlarning takrorlanishini oldini oladi.
UI ni reaktiv yangilash uchun Fragment da Flow va StateFlow dan viewLifecycleOwner bilan foydalanish.
class SearchFragment : Fragment() {
private val viewModel: SearchViewModel by viewModels()
private var binding: FragmentSearchBinding? = null
override fun onCreateView(
inflater: LayoutInflater,
container: ViewGroup?,
savedInstanceState: Bundle?
): View {
binding = FragmentSearchBinding.inflate(inflater, container, false)
return binding!!.root
}
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
binding?.searchButton?.setOnClickListener {
viewModel.search(binding?.queryInput?.text.toString())
}
viewLifecycleOwner.lifecycleScope.launch {
viewModel.searchResults.collectLatest { results ->
Log.d("SearchFragment", "Qidiruv natijalari: ${results.size}")
}
}
}
override fun onDestroyView() {
super.onDestroyView()
binding = null
}
}
Fragment View ga kirish uchun View Binding dan foydalanadi. viewLifecycleOwner.lifecycleScope.launch korutinasi View yo‘q qilinishida avtomatik bekor qilinadi. Binding xotira sizib ketishining oldini olish uchun onDestroyView da nollanadi. StateFlow View qayta yaratilishida ma’lumotlarning dolzarbligini kafolatlaydi.
Ko‘p beriladigan savollar
onCreateView — Fragment ning ildiz View ni yaratadi va qaytaradi. onViewCreated — View yaratilgandan so‘ng darhol chaqiriladi, View to‘liq ishga tushirilganligini va sozlashga tayyorligini kafolatlaydi (findViewById, obunalar). Google onCreateView da faqat layout ni shishirishni, barcha UI sozlashlarini esa onViewCreated da bajarishni tavsiya qiladi.
onDestroy — Fragment obyekt sifatida yo‘q qilingan (ViewModel tozalanadi, korutinlar bekor qilinadi). onDetach — oxirgi qayta chaqiruv bo‘lib, undan keyin Fragment Activity dan ajratiladi. Amalda barcha resurslar onDestroyView (View) va onDestroy (Fragment) da bo‘shatilishi kerak. onDetach — Activity ga havolalarni tozalash uchun.
Fragment yo‘qoladi, agar u BackStack da saqlash bilan tranzaksiya orqali FragmentManager ga qo‘shilmagan bo‘lsa yoki Activity onCreate da FragmentManager ni tiklamasa. Yechim: Fragment ni dasturiy ravishda onCreate da supportFragmentManager.beginTransaction().add() orqali qo‘shing, savedInstanceState == null tekshiruvi bilan.
Yo‘q. Fragment har doim FragmentManager orqali Activity ga bog‘liq. Hatto ekran aylanishida ham Activity qayta yaratiladi va Fragment yangi Activity ga qayta bog‘lanadi. Fragment ni Activity dan tashqarida yaratish mumkin emas — Fragment konstruktori tizim tomonidan tiklash uchun bo‘sh konstruktorni talab qiladi.
Nested fragments (ichki joylashgan fragmentlar) — boshqa Fragment ichidagi Fragment. Murakkab ekranlarni qurish uchun ishlatiladi: tab panellari, varaqli panellar, master-detail. Ichki joylashgan fragmentlar bola FragmentManager (childFragmentManager) tomonidan boshqariladi. Google ishlash muammolaridan qochish uchun 2 darajadan ortiq ichki joylashishni tavsiya etmaydi.
Xulosa
Biz kalit topshirig'i bilan mobil ilovani ishlab chiqamiz
IT Sectr 2017-yildan beri startaplar va korxonalar uchun iOS va Android ilovalarini yaratadi. Biz sizga maslahat beramiz va eng yaxshi yechimni taklif qilamiz.