Kullanıcı arayüzü katmanı kılavuzunda, kullanıcı arayüzü katmanı için Kullanıcı Arayüzü Durumunu oluşturma ve yönetme yöntemi olarak tek yönlü veri akışı (UDF) ele alınmaktadır.
Ayrıca, UDF yönetiminde devlet sahibi adı verilen özel bir sınıfa yetki vermenin avantajları da vurgulanmaktadır. Eyalet sahibini ViewModel
veya düz sınıf aracılığıyla uygulayabilirsiniz. Bu belgede, durum sahiplerine ve kullanıcı arayüzü katmanında oynadıkları role daha yakından bakılmıştır.
Bu belgenin sonunda, uygulama durumunun kullanıcı arayüzü katmanında, yani kullanıcı arayüzü durumu üretim ardışık düzeninde nasıl yönetileceğini öğrenmiş olmanız gerekir. Aşağıdakileri anlayabilmeniz ve bilmeniz gerekir:
- Kullanıcı arayüzü katmanındaki kullanıcı arayüzü durumu türlerini anlayın.
- Kullanıcı arayüzü katmanındaki bu kullanıcı arayüzü durumlarında çalışan mantık türlerini anlayın.
ViewModel
veya basit sınıf gibi bir eyalet sahibinin uygun uygulamasını nasıl seçeceğinizi öğrenin.
Kullanıcı arayüzü durumu üretim ardışık düzeninin öğeleri
Kullanıcı arayüzü durumu ve bunu oluşturan mantık, kullanıcı arayüzü katmanını tanımlar.
Kullanıcı arayüzü durumu
Kullanıcı arayüzü durumu, kullanıcı arayüzünü açıklayan özelliktir. İki tür kullanıcı arayüzü durumu vardır:
- Ekran kullanıcı arayüzü durumu, ekranda görüntülemeniz gereken şeydir. Örneğin, bir
NewsUiState
sınıfı, kullanıcı arayüzünü oluşturmak için gereken haber makalelerini ve diğer bilgileri içerebilir. Bu durum, uygulama verilerini içerdiği için genellikle hiyerarşinin diğer katmanlarıyla bağlantılıdır. - Kullanıcı arayüzü öğesi durumu, oluşturulma şeklini etkileyen kullanıcı arayüzü öğelerinde bulunan özellikleri ifade eder. Bir kullanıcı arayüzü öğesi gösterilebilir veya gizlenebilir ve belirli bir yazı tipi, yazı tipi boyutu veya yazı tipi rengine sahip olabilir. Android Görünümlerinde Görünüm, doğası gereği durum bilgili olduğundan durumu değiştirme veya sorgulama yöntemleri sunduğu için bu durumu yönetir. Bunun örneği, metni için
TextView
sınıfınınget
veset
yöntemleridir. Jetpack Compose'da durum, oluşturulabilecek olanın dışındadır ve hatta bile oluşturma işlemini, oluşturulabilir öğenin yakın yakınından, çağıran birleştirilebilir işleve veya bir durum sahibine gönderebilirsiniz.Scaffold
composable içinScaffoldState
buna örnek olarak verilebilir.
Mantık
Uygulama verileri ve kullanıcı etkinlikleri, kullanıcı arayüzü durumunun zaman içinde değişmesine neden olduğundan kullanıcı arayüzü durumu statik bir mülk değildir. Kullanıcı arayüzü durumunun hangi bölümlerinin değiştiği, neden değiştiği ve ne zaman değişmesi gerektiği de dahil olmak üzere değişikliğin ayrıntılarını mantık belirler.
Bir uygulamanın mantığı, iş mantığı veya kullanıcı arayüzü mantığı olabilir:
- İş mantığı, uygulama verileri için ürün gereksinimlerinin uygulanmasıdır. Örneğin, kullanıcı düğmeye dokunduğunda haber okuyucu uygulamasında bir makaleye yer işareti koyma. Bir dosyaya veya veritabanına yer işareti kaydetme mantığı, genellikle alana veya veri katmanlarına yerleştirilir. Durum sorumlusu, genellikle ortaya koydukları yöntemleri çağırarak bu mantığı bu katmanlara devreder.
- Kullanıcı arayüzü mantığı, ekranda kullanıcı arayüzü durumunun nasıl gösterileceğiyle ilgilidir. Örneğin, kullanıcı bir kategori seçtiğinde doğru arama çubuğu ipucunun elde edilmesi, bir listedeki belirli bir öğeye kaydırılması veya kullanıcı bir düğmeyi tıkladığında gezinme mantığının belirli bir ekrana gelmesi.
Android yaşam döngüsü, kullanıcı arayüzü durumu ve mantığının türleri
Kullanıcı arayüzü katmanının iki bölümü vardır: Biri kullanıcı arayüzü yaşam döngüsünden bağımsız, diğeri bağımlı. Bu ayırma, her bir parça için kullanılabilen veri kaynaklarını belirlediğinden farklı türde kullanıcı arayüzü durumu ve mantık gerektirir.
- Kullanıcı arayüzü yaşam döngüsünden bağımsız: Kullanıcı arayüzü katmanının bu bölümü, uygulamanın veri oluşturma katmanlarıyla (veri veya alan katmanları) ilgilidir ve iş mantığıyla tanımlanır. Kullanıcı arayüzündeki yaşam döngüsü, yapılandırma değişiklikleri ve
Activity
yeniden oluşturma işlemleri, kullanıcı arayüzü durumu üretim hattının etkin olup olmadığını etkileyebilir ancak üretilen verilerin geçerliliğini etkilemez. - Kullanıcı arayüzü yaşam döngüsüne bağlı: Kullanıcı arayüzü katmanının bu bölümü, kullanıcı arayüzü mantığıyla ilgilidir ve yaşam döngüsünden veya yapılandırma değişikliklerinden doğrudan etkilenir. Bu değişiklikler, içerisinde okunan veri kaynaklarının geçerliliğini doğrudan etkiler ve dolayısıyla durumu yalnızca yaşam döngüsü aktif olduğunda değişebilir. Çalışma zamanı izinleri ve yerelleştirilmiş dizeler gibi yapılandırmaya bağlı kaynakları alma, buna örnek olarak gösterilebilir.
Yukarıda belirtilenler, aşağıdaki tabloyla özetlenebilir:
Kullanıcı Arayüzü Yaşam Döngüsü Bağımsız | Kullanıcı Arayüzü Yaşam Döngüsüne bağımlı |
---|---|
İş mantığı | Kullanıcı Arayüzü Mantığı |
Ekran kullanıcı arayüzü durumu |
Kullanıcı arayüzü durumu üretim ardışık düzeni
Kullanıcı arayüzü durumu üretim ardışık düzeni, kullanıcı arayüzü durumu üretmek için gerçekleştirilen adımları ifade eder. Bu adımlar, daha önce tanımlanan mantık türlerinin uygulanmasından oluşur ve tamamen kullanıcı arayüzünüzün ihtiyaçlarına bağlıdır. Bazı kullanıcı arayüzleri, ardışık düzenin hem Kullanıcı Arayüzü Yaşam Döngüsünden hem de Kullanıcı Arayüzü Yaşam Döngüsü'ne bağlı bölümlerinden yararlanabilir veya hiçbirinden fayda sağlamayabilir.
Yani kullanıcı arayüzü katmanı ardışık düzeninin aşağıdaki permütasyonları geçerlidir:
Kullanıcı arayüzünün kendisi tarafından üretilen ve yönetilen kullanıcı arayüzü durumu. Örneğin, basit ve yeniden kullanılabilir bir temel sayaç:
@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") } } }
Kullanıcı arayüzü mantığı → Kullanıcı arayüzü. Örneğin, kullanıcının listenin en üstüne atlamasına olanak tanıyan bir düğmeyi gösterme veya gizleme.
@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() } }
İş mantığı → kullanıcı arayüzü. Ekranda geçerli kullanıcının fotoğrafını gösteren bir kullanıcı arayüzü öğesi.
@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) }
İş mantığı → kullanıcı arayüzü mantığı → kullanıcı arayüzü. Belirli bir kullanıcı arayüzü durumu için ekranda doğru bilgileri görüntülemek üzere kayan bir kullanıcı arayüzü öğesidir.
@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) } } } }
Kullanıcı arayüzü durumu üretim ardışık düzenine her iki tür mantığın da uygulandığı durumlarda, iş mantığı her zaman kullanıcı arayüzü mantığından önce uygulanmalıdır. Kullanıcı arayüzü mantığından sonra iş mantığını uygulamaya çalışmak, iş mantığının kullanıcı arayüzü mantığına bağlı olduğu anlamına gelir. Bunun neden bir sorun olduğu, farklı mantık türlerine ve durum sahiplerine ayrıntılı bir şekilde değinilerek aşağıdaki bölümlerde ele alınmaktadır.
Devlet sahipleri ve sorumlulukları
Eyalet sahibinin sorumluluğu, uygulamanın okuyabilmesi için durumu depolamaktır. Mantığın gerekli olduğu durumlarda aracı görevi görür ve gerekli mantığı barındıran veri kaynaklarına erişim sağlar. Bu şekilde durum sahibi, mantığı uygun veri kaynağına yetkilendirir.
Bunun sonucunda şu avantajlar elde edilir:
- Basit kullanıcı arayüzleri: Kullanıcı arayüzü yalnızca durumunu bağlar.
- Sürdürülebilirlik: Durum sahibinde tanımlanan mantık, kullanıcı arayüzünün kendisi değiştirilmeden yinelenebilir.
- Test edilebilirlik: Kullanıcı arayüzü ve durum üretim mantığı bağımsız olarak test edilebilir.
- Okunabilirlik: Kodu okuyanlar, kullanıcı arayüzü sunu kodu ile kullanıcı arayüzü durumu üretim kodu arasındaki farklılıkları net bir şekilde görebilir.
Boyutu veya kapsamı ne olursa olsun her kullanıcı arayüzü öğesinin, karşılık gelen durum sahibiyle 1:1 bir ilişkisi vardır. Ayrıca durum sahibi, kullanıcı arayüzü durum değişikliğine neden olabilecek tüm kullanıcı işlemlerini kabul edip işleyebilmeli ve sonraki durum değişikliğini üretmelidir.
Devlet sahibi türleri
Kullanıcı arayüzü durum ve mantık türlerine benzer şekilde, kullanıcı arayüzü katmanında, kullanıcı arayüzü yaşam döngüsüyle olan ilişkilerine göre tanımlanan iki tür durum sahibi vardır:
- İş mantığı durum sahibi.
- Kullanıcı arayüzü mantık durumu tutucusu.
Aşağıdaki bölümlerde, iş mantığı durum sahibinden başlayarak devlet sahiplerinin türlerine daha yakından bakılmaktadır.
İş mantığı ve durum bilgisi
İş mantığı durum sahipleri, kullanıcı etkinliklerini işler ve verileri veri veya alan katmanlarından ekran kullanıcı arayüzü durumuna dönüştürür. Android yaşam döngüsü ve uygulama yapılandırması değişikliklerini göz önünde bulundururken optimum kullanıcı deneyimi sunmak için iş mantığından yararlanan devlet sahiplerinin aşağıdaki özelliklere sahip olması gerekir:
Özellik | Ayrıntı |
---|---|
Kullanıcı Arayüzü Durumunu oluşturur | İş mantığı durum sahipleri, kullanıcı arayüzleri için kullanıcı arayüzü durumlarını oluşturmaktan sorumludur. Bu kullanıcı arayüzü durumu, genellikle kullanıcı etkinliklerinin işlenmesinin ve alandan ve veri katmanlarından gelen verilerin okunmasından kaynaklanır. |
Etkinlik rekreasyon aracılığıyla elde tutulur | İş mantığı durum sahipleri, Activity yeniden oluşturma genelinde durum ve durum işleme ardışık düzenlerini koruyarak sorunsuz bir kullanıcı deneyimi sunmaya yardımcı olur. Devlet sahibinin saklanması mümkün olmadığı ve yeniden oluşturulduğu durumlarda (genellikle işlem ölümünden sonra) tutarlı bir kullanıcı deneyimi sağlamak için son durumunu kolayca yeniden oluşturabilmelidir. |
Uzun ömürlü duruma sahip olma | İş mantığı durum sahipleri, genellikle navigasyon hedefleri için durumu yönetmek amacıyla kullanılır. Bunun sonucunda, gezinme grafiğinden kaldırılana kadar gezinme değişikliklerindeki durumlarını genellikle korurlar. |
Kullanıcı arayüzüne özgü olmalıdır ve yeniden kullanılamaz | İş mantığı durum sahipleri, genellikle TaskEditViewModel veya TaskListViewModel gibi belirli bir uygulama işlevi için durum oluşturur ve bu nedenle, yalnızca bu uygulama işlevi için geçerli olur. Aynı durum sahibi, bu uygulama işlevlerini farklı form faktörlerinde destekleyebilir. Örneğin, uygulamanın mobil, TV ve tablet sürümleri aynı iş mantığı durum sahibini yeniden kullanabilir. |
Örneğin, "Now in Android" uygulamasındaki yazar gezinme hedefini ele alalım:
İş mantığı durum sahibi olarak hareket eden AuthorViewModel
, bu durumda kullanıcı arayüzü durumunu oluşturur:
@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
öğesinin daha önce açıklanan özelliklere sahip olduğuna dikkat edin:
Özellik | Ayrıntı |
---|---|
AuthorScreenUiState üretir |
AuthorViewModel , AuthorsRepository ve NewsRepository verilerindeki verileri okur ve bu verileri AuthorScreenUiState üretmek için kullanır. Kullanıcı, AuthorsRepository için yetki vererek bir Author öğesini takip etmek veya takibi bırakmak istediğinde iş mantığını da uygular. |
Veri katmanına erişimi var | AuthorsRepository ve NewsRepository örnekleri, oluşturucuda kendisine iletilir ve bu sayede Author izleme iş mantığını uygulayabilir. |
Activity etkinlik sırasında hayatta kalır |
ViewModel ile uygulandığından hızlı Activity yeniden oluşturma işleminde tutulur. İşlemin ölmesi durumunda, kullanıcı arayüzü durumunu veri katmanından geri yüklemek için gereken minimum bilgi miktarını sağlamak üzere SavedStateHandle nesnesi şuradan okunabilir: |
Uzun ömürlü duruma sahip | ViewModel , gezinme grafiğinin kapsamındadır. Bu nedenle, yazar hedefi gezinme grafiğinden kaldırılmadığı sürece uiState StateFlow içindeki kullanıcı arayüzü durumu bellekte kalır. StateFlow kullanımı, durumu tembel oluşturan iş mantığının uygulanmasının avantajını da ekler. Bunun nedeni, yalnızca kullanıcı arayüzü durumu bir toplayıcısı durumunda durum üretilmesidir. |
Kullanıcı arayüzüne özgü olmalıdır | AuthorViewModel yalnızca yazarın gezinme hedefi için geçerlidir ve başka hiçbir yerde yeniden kullanılamaz. Gezinme hedeflerinde yeniden kullanılan bir iş mantığı varsa bu iş mantığının veri veya alan katmanı kapsamlı bir bileşene dahil edilmesi gerekir. |
İş mantığı durum sahibi olarak ViewModel
Android geliştirmedeki ViewModels, bunları iş mantığına erişim ve uygulama verilerini ekranda sunum için hazırlamaya uygun hale getirir. Bu avantajlardan bazıları şunlardır:
- ViewModels tarafından tetiklenen işlemler yapılandırma değişikliklerini atlatmaya devam eder.
- Gezinme ile entegrasyon:
- Gezinme, ekran arka yığındayken ViewModel'leri önbelleğe alır. Daha önce yüklediğiniz verilerin hedefinize geri döndüğünüzde anında kullanılabilir olması önemlidir. Oluşturulabilir ekranın yaşam döngüsünü takip eden bir eyalet sahibi için bunu yapmanın daha zor bir yolu olduğunu söyleyebiliriz.
- ViewModel, hedef arka yığından çıkarıldığında da temizlenir. Böylece durum otomatik olarak temizlenir. Bu, yapılandırma değişikliği veya başka nedenlerle yeni bir ekrana gitme gibi birden çok nedenden dolayı oluşturulabilecek bir araya getirilmesini dinlemeden farklıdır.
- Hilt gibi diğer Jetpack kitaplıklarıyla entegrasyon.
Kullanıcı arayüzü mantığı ve durum koruyucu
Kullanıcı arayüzü mantığı, kullanıcı arayüzünün sağladığı veriler üzerinde çalışan bir mantıktır. Bu, kullanıcı arayüzü öğelerinin durumunda veya izinler API'si ya da Resources
gibi kullanıcı arayüzü veri kaynaklarında olabilir. Kullanıcı arayüzü mantığını kullanan durum sahipleri genellikle aşağıdaki özelliklere sahiptir:
- Kullanıcı arayüzü durumunu oluşturur ve kullanıcı arayüzü öğelerinin durumunu yönetir.
Activity
yeniden oluşturmasından sonra dayanmaz: Kullanıcı arayüzü mantığında barındırılan eyalet sahipleri, genellikle kullanıcı arayüzünün kendisinden gelen veri kaynaklarına bağımlıdır ve bu bilgileri yapılandırma değişiklikleri genelinde saklamaya çalışmak, bellek sızıntısına neden olmamasından daha sıktır. Devlet sahiplerinin yapılandırma değişiklikleri boyunca değişmeleri için verilerin korunmasını istemeleri durumunda,Activity
rekreasyonunda hayatta kalmak için başka bir bileşene yetki vermeleri gerekir. Örneğin Jetpack Compose'daremembered
işlevleriyle oluşturulan yazılabilir kullanıcı arayüzü öğe durumları genellikleActivity
yeniden oluşturma genelinde durumu korumak içinrememberSaveable
'ye yetki verir. Bu tür işlevlere örnek olarakrememberScaffoldState()
verememberLazyListState()
verilebilir.- Kullanıcı arayüzü kapsamlı veri kaynaklarına referans içeriyor: Kullanıcı arayüzü mantık durumu sahibi, kullanıcı arayüzü ile aynı yaşam döngüsüne sahip olduğundan yaşam döngüsü API'leri ve Kaynaklar gibi veri kaynaklarına güvenli bir şekilde referans verilebilir ve bu kaynaklar okunabilir.
- Birden çok kullanıcı arayüzünde yeniden kullanılabilir: Aynı kullanıcı arayüzü mantığı durum sahibinin farklı örnekleri, uygulamanın farklı bölümlerinde yeniden kullanılabilir. Örneğin, bir çip grubuna ilişkin kullanıcı girişi etkinliklerini yönetmek için bir durum sahibi, filtre çiplerinin arama sayfasında ve ayrıca e-posta alıcıları için "alıcı" alanı için kullanılabilir.
Kullanıcı arayüzü mantık durumu tutucusu genellikle düz bir sınıfla uygulanır. Bunun nedeni, kullanıcı arayüzü mantıksal durum sahibinin oluşturulmasından kullanıcı arayüzünün sorumlu olması ve kullanıcı arayüzü mantık durumu sahibinin, kullanıcı arayüzüyle aynı yaşam döngüsüne sahip olmasıdır. Örneğin Jetpack Compose'da eyalet sahibi Bestenin bir parçasıdır ve Beste'nin yaşam döngüsünü izler.
Yukarıdaki bu, Now in Android örneğinde aşağıdaki örnekte belirtilebilir:
Android'de Now örneğinde, cihazın ekran boyutuna bağlı olarak gezinme için alt uygulama çubuğu veya gezinme çubuğu gösterilmektedir. Küçük ekranlarda alt uygulama çubuğu, daha büyük ekranlarda ise gezinme çubuğu kullanılır.
NiaApp
oluşturulabilir işlevinde kullanılan uygun gezinme kullanıcı arayüzü öğesine karar verme mantığı iş mantığına bağlı olmadığından, bu öğe NiaAppState
adlı bir düz sınıf durum sahibi tarafından yönetilebilir:
@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) { /* ... */ }
/* ... */
}
Yukarıdaki örnekte, NiaAppState
ile ilgili aşağıdaki ayrıntılar dikkat çekicidir:
Activity
yeniden oluşturma işleminden sonra da kalamaz:NiaAppState
, Oluşturma adlandırma kurallarına uygun bir Oluşturulabilir işlevrememberNiaAppState
ile oluşturduğu için Beste'deremembered
değerine sahiptir.Activity
yeniden oluşturulduktan sonra önceki örnek kaybedilir ve tüm bağımlılıklarının aktarıldığı yeni bir örnek oluşturulur. Bu örnek, yeniden oluşturulanActivity
öğesinin yeni yapılandırmasına uygun olur. Bu bağımlılıklar yeni olabilir veya önceki yapılandırmadan geri yüklenmiş olabilir. ÖrneğinrememberNavController()
,NiaAppState
oluşturucuda kullanılır veActivity
yeniden oluşturmasında durumu korumak içinrememberSaveable
öğesine yetki verir.- Kullanıcı arayüzü kapsamlı veri kaynaklarına referanslar içeriyor:
navigationController
,Resources
ve diğer benzer yaşam döngüsü kapsamlı türlere yapılan referanslar, aynı yaşam döngüsü kapsamını paylaştıkları içinNiaAppState
içinde güvenli bir şekilde barındırılabilir.
Eyalet sahibi için ViewModel ve düz sınıf arasından seçim yapın
Yukarıdaki bölümlerde, ViewModel
ile düz sınıf durum sahibi arasında seçim yapmak, kullanıcı arayüzü durumuna uygulanan mantığa ve mantığın üzerinde çalıştığı veri kaynaklarına bağlıdır.
Özet olarak, aşağıdaki şemada devlet sahiplerinin kullanıcı arayüzü durum üretim hattındaki konumu gösterilmektedir:
Sonuç olarak, kullanıcı arayüzü durumlarını, tüketildiği yere en yakın eyalet sahiplerini kullanarak üretmelisiniz. Daha az resmi bir şekilde, uygun sahipliği sürdürürken eyaleti mümkün olduğunca düşük tutmalısınız. İş mantığına erişmeniz ve kullanıcı arayüzü durumunun, Activity
yeniden pazarlamasında bile bir ekrana gidilebildiği sürece kalıcı olması gerekiyorsa ViewModel
, iş mantığı durum sahibi uygulamanız için mükemmel bir seçenektir. Daha kısa ömürlü kullanıcı arayüzü durumu ve kullanıcı arayüzü mantığı için yaşam döngüsü yalnızca kullanıcı arayüzüne bağlı olan düz bir sınıf yeterli olacaktır.
Eyalet sahipleri birleştirilmiştir
Bağımlılıkların süresi eşit veya daha kısa olduğu sürece devlet sahipleri başka devlet sahiplerine bağımlı olabilirler. Buna örnek olarak aşağıdakiler gösterilebilir:
- bir kullanıcı arayüzü mantık durumu tutucusu, başka bir kullanıcı arayüzü mantık durumu sahibine bağlı olabilir.
- ekran düzeyinde durum tutucu, kullanıcı arayüzü mantık durumu tutucusuna bağlı olabilir.
Aşağıdaki kod snippet'inde, Compose DrawerState
işlevinin başka bir dahili durum sahibine (SwipeableState
) nasıl bağlı olduğu ve bir uygulamanın kullanıcı arayüzü mantık durumu sahibinin DrawerState
öğesine nasıl bağlı olabileceği gösterilmektedir:
@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)
}
Durum sahibini aşan bağımlılığa örnek olarak, ekran seviyesi durum sahibine bağlı bir kullanıcı arayüzü mantık durumu sahibi verilebilir. Bu, daha kısa ömürlü durum sahibinin yeniden kullanılabilirliğini azaltır ve gerçekten ihtiyaç duyduğundan daha fazla mantığa ve duruma erişim sağlar.
Daha kısa süreli durum sahibinin daha yüksek kapsamlı bir durum sahibinden belirli bilgilere ihtiyacı varsa durum sahibi örneğini iletmek yerine parametre olarak yalnızca ihtiyacı olan bilgileri iletin. Örneğin, aşağıdaki kod snippet'inde kullanıcı arayüzü mantık durumu tutucu sınıfı, tüm ViewModel örneğini bağımlılık olarak iletmek yerine, tam olarak ihtiyaç duyduğu şeyi ViewModel'den parametre olarak alır.
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
),
// ...
) {
/* ... */
}
Aşağıdaki şemada, kullanıcı arayüzü ile önceki kod snippet'inin farklı durum sahipleri arasındaki bağımlılıklar gösterilmektedir:
Sana Özel
Aşağıdaki Google örnekleri, kullanıcı arayüzü katmanında eyalet sahiplerinin kullanımını göstermektedir. Bu kılavuzu inceleyerek örnekleri inceleyin:
Sizin için önerilenler
- Not: Bağlantı metni JavaScript kapalıyken gösterilir
- Kullanıcı arayüzü katmanı
- Kullanıcı arayüzü durumu üretimi
- Uygulama mimarisi rehberi