FlowRow
ve FlowColumn
, Row
ve Column
'e benzer ancak kapsayıcıda yer kalmadığında öğelerin bir sonraki satıra akması bakımından farklı olan kompozisyonlardır. Bu işlemle birden fazla satır veya sütun oluşturulur. Bir satırdaki öğe sayısı, maxItemsInEachRow
veya maxItemsInEachColumn
ayarlanarak da kontrol edilebilir. FlowRow
ve FlowColumn
'i kullanarak duyarlı düzenler oluşturabilirsiniz. Öğeler bir boyut için çok büyükse içerik kesilmez. maxItemsInEach*
ile Modifier.weight(weight)
'ı birlikte kullanarak gerektiğinde bir satırın veya sütunun genişliğini dolduran/genişleten düzenler oluşturabilirsiniz.
Tipik bir örnek, çip veya filtreleme kullanıcı arayüzüdür:
Temel kullanım
FlowRow
veya FlowColumn
'ü kullanmak için aşağıdaki bileşenleri oluşturun ve içine standart akışı takip etmesi gereken öğeleri yerleştirin:
@Composable private fun FlowRowSimpleUsageExample() { FlowRow(modifier = Modifier.padding(8.dp)) { ChipItem("Price: High to Low") ChipItem("Avg rating: 4+") ChipItem("Free breakfast") ChipItem("Free cancellation") ChipItem("£50 pn") } }
Bu snippet, ilk satırda yer kalmadığında öğelerin otomatik olarak bir sonraki satıra aktığı, yukarıda gösterilen kullanıcı arayüzünü oluşturur.
Akış düzeninin özellikleri
Akış düzenleri, uygulamanızda farklı düzenler oluşturmak için kullanabileceğiniz aşağıdaki özelliklere ve özelliklere sahiptir.
Ana eksen düzenlemesi: yatay veya dikey düzenleme
Ana eksen, öğelerin yerleştirildiği eksendir (örneğin, FlowRow
öğeleri yatay olarak düzenlenir). FlowRow
içindeki horizontalArrangement
parametresi, boş alanın öğeler arasında dağıtılma şeklini kontrol eder.
Aşağıdaki tabloda, FlowRow
için öğelerde horizontalArrangement
ayarlama örnekleri gösterilmektedir:
Yatay düzenleme |
Sonuç |
|
|
FlowColumn
için verticalArrangement
ile benzer seçenekler kullanılabilir. Varsayılan değer Arrangement.Top
'dir.
Çapraz eksen düzenlemesi
Çapraz eksen, ana eksene ters yönde olan eksendir. Örneğin, FlowRow
için bu dikey eksendir. Kapsayıcıdaki genel içeriğin çapraz eksende nasıl düzenleneceğini değiştirmek için FlowRow
için verticalArrangement
ve FlowColumn
için horizontalArrangement
kullanın.
FlowRow
için aşağıdaki tabloda, öğelerde farklı verticalArrangement
ayarlama örnekleri gösterilmektedir:
Dikey düzenleme |
Sonuç |
|
|
FlowColumn
için horizontalArrangement
ile benzer seçenekler kullanılabilir.
Varsayılan çapraz eksen düzenlemesi Arrangement.Start
'tür.
Öğeleri tek tek hizalama
Satırdaki öğeleri farklı hizalamalarla konumlandırmak isteyebilirsiniz. Bu düğme, öğeleri mevcut satır içinde hizalladığından verticalArrangement
ve horizontalArrangement
'ten farklıdır. Bunu Modifier.align()
ile uygulayabilirsiniz.
Örneğin, bir FlowRow
içindeki öğeler farklı yüksekliklere sahip olduğunda satır, en büyük öğenin yüksekliğini alır ve öğelere Modifier.align(alignmentOption)
uygular:
Dikey hizalama |
Sonuç |
|
|
FlowColumn
için benzer seçenekler mevcuttur. Varsayılan hizalama Alignment.Start
'tür.
Satır veya sütundaki maksimum öğe sayısı
maxItemsInEachRow
veya maxItemsInEachColumn
parametreleri, bir satırda izin verilecek maksimum öğeyi tanımlar ve ardından bir sonraki satıra sarmalanır. Varsayılan değer Int.MAX_INT
'tür. Bu değer, boyutları satıra sığmasına izin verdiği sürece mümkün olduğunca fazla öğeye izin verir.
Örneğin, maxItemsInEachRow
ayarlandığında ilk düzenin yalnızca 3 öğe içermesi zorunlu kılınabilir:
Maksimum değer ayarlanmadı |
|
Akış öğelerini geç yükleme
ContextualFlowRow
ve ContextualFlowColumn
, akış satırınızın veya sütununuzun içeriğini yavaşça yüklemenize olanak tanıyan FlowRow
ve FlowColumn
'in özelleştirilmiş bir sürümüdür. Ayrıca, öğenin ilk satırda olup olmadığı gibi öğelerin konumu (dizin, satır numarası ve kullanılabilir boyut) hakkında bilgi sağlarlar. Bu, büyük veri kümeleri için ve bir öğeyle ilgili bağlamsal bilgilere ihtiyacınız olduğunda faydalıdır.
maxLines
parametresi, görüntülenen satır sayısını sınırlar ve overflow
parametresi, öğelerin taştığı durumlarda neyin gösterileceğini belirtir. Böylece özel bir expandIndicator
veya collapseIndicator
belirtebilirsiniz.
Örneğin, "+ (kalan öğe sayısı)" veya "Daha Az Göster" düğmesi göstermek için:
val totalCount = 40 var maxLines by remember { mutableStateOf(2) } val moreOrCollapseIndicator = @Composable { scope: ContextualFlowRowOverflowScope -> val remainingItems = totalCount - scope.shownItemCount ChipItem(if (remainingItems == 0) "Less" else "+$remainingItems", onClick = { if (remainingItems == 0) { maxLines = 2 } else { maxLines += 5 } }) } ContextualFlowRow( modifier = Modifier .safeDrawingPadding() .fillMaxWidth(1f) .padding(16.dp) .wrapContentHeight(align = Alignment.Top) .verticalScroll(rememberScrollState()), verticalArrangement = Arrangement.spacedBy(4.dp), horizontalArrangement = Arrangement.spacedBy(8.dp), maxLines = maxLines, overflow = ContextualFlowRowOverflow.expandOrCollapseIndicator( minRowsToShowCollapse = 4, expandIndicator = moreOrCollapseIndicator, collapseIndicator = moreOrCollapseIndicator ), itemCount = totalCount ) { index -> ChipItem("Item $index") }
Öğe ağırlıkları
Ağırlık, bir öğenin faktörüne ve yerleştirildiği satırdaki kullanılabilir alana göre öğeyi büyütür. Önemli bir nokta, bir öğenin genişliğini hesaplamak için ağırlıkların nasıl kullanıldığıyla ilgili olarak FlowRow
ve Row
arasında bir fark olmasıdır. Rows
için ağırlık, Row
'daki tüm öğelere dayanır. FlowRow
ile ağırlık, FlowRow
kapsayıcısındaki tüm öğelere değil, bir öğenin yerleştirildiği satırdaki öğelere dayanır.
Örneğin, aynı satıra ait 4 öğeniz varsa ve bunların her biri 1f, 2f, 1f
ve 3f
ağırlıklarına sahipse toplam ağırlık 7f
olur. Bir satır veya sütundaki kalan alan 7f
'e bölünür. Ardından her öğe genişliği şu şekilde hesaplanır: weight * (remainingSpace / totalWeight)
.
Izgara benzeri bir düzen oluşturmak için Modifier.weight
ve maksimum öğelerin FlowRow
veya FlowColumn
ile bir kombinasyonunu kullanabilirsiniz. Bu yaklaşım, cihazınızın boyutuna göre ayarlanan duyarlı düzenler oluşturmak için kullanışlıdır.
Ağırlıkları kullanarak neler başarabileceğinize dair birkaç farklı örnek vardır. Aşağıda gösterildiği gibi öğelerin eşit boyutta olduğu bir ızgara buna örnek gösterilebilir:
Eşit öğe boyutlarına sahip bir ızgara oluşturmak için şunları yapabilirsiniz:
val rows = 3 val columns = 3 FlowRow( modifier = Modifier.padding(4.dp), horizontalArrangement = Arrangement.spacedBy(4.dp), maxItemsInEachRow = rows ) { val itemModifier = Modifier .padding(4.dp) .height(80.dp) .weight(1f) .clip(RoundedCornerShape(8.dp)) .background(MaterialColors.Blue200) repeat(rows * columns) { Spacer(modifier = itemModifier) } }
Önemli bir nokta, başka bir öğe ekleyip bunu 9 yerine 10 kez tekrarlarsanız tüm satırın toplam ağırlığı 1f
olduğu için son öğe son sütunun tamamını kaplar:
Ağırlıkları Modifier.width(exactDpAmount), Modifier.aspectRatio(aspectRatio)
veya Modifier.fillMaxWidth(fraction)
gibi diğer Modifiers
ile birleştirebilirsiniz. Bu değiştiricilerin tümü, FlowRow
(veya FlowColumn
) içindeki öğelerin duyarlı boyutlandırılmasına olanak tanımak için birlikte çalışır.
Ayrıca, iki öğenin her birinin genişliğin yarısını, bir öğenin ise sonraki sütunun tüm genişliğini kapladığı, farklı öğe boyutlarından oluşan bir ızgara da oluşturabilirsiniz:
Bunu aşağıdaki kodla yapabilirsiniz:
FlowRow( modifier = Modifier.padding(4.dp), horizontalArrangement = Arrangement.spacedBy(4.dp), maxItemsInEachRow = 2 ) { val itemModifier = Modifier .padding(4.dp) .height(80.dp) .clip(RoundedCornerShape(8.dp)) .background(Color.Blue) repeat(6) { item -> // if the item is the third item, don't use weight modifier, but rather fillMaxWidth if ((item + 1) % 3 == 0) { Spacer(modifier = itemModifier.fillMaxWidth()) } else { Spacer(modifier = itemModifier.weight(0.5f)) } } }
Kesirli boyutlandırma
Modifier.fillMaxWidth(fraction)
özelliğini kullanarak bir öğenin kaplaması gereken kapsayıcının boyutunu belirtebilirsiniz. Bu, Modifier.fillMaxWidth(fraction)
'ün Row
veya Column
'ye uygulandığındaki işleyişinden farklıdır. Row/Column
öğeleri, kapsayıcının tüm genişliği yerine kalan genişliğin bir yüzdesini kaplar.
Örneğin, aşağıdaki kod FlowRow
yerine Row
kullanıldığında farklı sonuçlar verir:
FlowRow( modifier = Modifier.padding(4.dp), horizontalArrangement = Arrangement.spacedBy(4.dp), maxItemsInEachRow = 3 ) { val itemModifier = Modifier .clip(RoundedCornerShape(8.dp)) Box( modifier = itemModifier .height(200.dp) .width(60.dp) .background(Color.Red) ) Box( modifier = itemModifier .height(200.dp) .fillMaxWidth(0.7f) .background(Color.Blue) ) Box( modifier = itemModifier .height(200.dp) .weight(1f) .background(Color.Magenta) ) }
|
|
|
fillMaxColumnWidth()
ve fillMaxRowHeight()
FlowColumn
veya FlowRow
içindeki bir öğeye Modifier.fillMaxColumnWidth()
ya da Modifier.fillMaxRowHeight()
uygulamak, aynı sütundaki veya satırdaki öğelerin sütundaki/satırdaki en büyük öğeyle aynı genişliği veya yüksekliği kaplamasını sağlar.
Örneğin, bu örnekte Android tatlılarının listesini görüntülemek için FlowColumn
kullanılmaktadır. Öğelere Modifier.fillMaxColumnWidth()
uygulandığında ve uygulanmadığında ve öğeler kaydırıldığında her öğenin genişliğindeki farkı görebilirsiniz.
FlowColumn( Modifier .padding(20.dp) .fillMaxHeight() .fillMaxWidth(), horizontalArrangement = Arrangement.spacedBy(8.dp), verticalArrangement = Arrangement.spacedBy(8.dp), maxItemsInEachColumn = 5, ) { repeat(listDesserts.size) { Box( Modifier .fillMaxColumnWidth() .border(1.dp, Color.DarkGray, RoundedCornerShape(8.dp)) .padding(8.dp) ) { Text( text = listDesserts[it], fontSize = 18.sp, modifier = Modifier.padding(3.dp) ) } } }
Her öğeye uygulanan |
|
Genişlik değişikliği ayarlanmadı (öğeleri sarmalama) |
Sizin için önerilenler
- Not: JavaScript kapalıyken bağlantı metni gösterilir
- Düzen oluşturmayla ilgili temel bilgiler
- Oluşturma'da ConstraintLayout
- Düzenleyici işlemleri {:#editor-actions}