jetpack
We previously looked at how to handle states inside a Composable with the quantity selection component. In this article, we’ll see how to make a scrollable list. When it comes to display a list of elements, we need to use a RecyclerView
with an adapter to define each item. This basic feature can become hard for so many cases but Jetpack Compose gives a new way to display a scrollable list!
我们之前曾研究过如何使用数量选择组件处理Composable内部的状态。 在本文中,我们将看到如何制作可滚动列表。 在显示元素列表时,我们需要使用带有适配器的RecyclerView
来定义每个项目。 在许多情况下,此基本功能都会变得很难,但是Jetpack Compose提供了一种显示可滚动列表的新方法!
Disclaimer: All source code is developed with Compose 1.0.0-alpha02. Because Jetpack Compose is still in alpha, some source code may change with new versions.
免责声明:所有源代码都是使用Compose 1.0.0-alpha02开发的。 由于Jetpack Compose仍处于Alpha状态,因此某些源代码可能会随新版本而更改。
可滚动的撰写组件 (Scrollable Compose components)
Jetpack Compose offers two ways each to display a scrollable list in vertical or horizontal:
Jetpack Compose提供了两种方法以垂直或水平显示可滚动列表:
ScrollableColumn (resp. ScrollableRow) is a variant of
Column
(orRow
) that scrolls when content is bigger than its height (or width). That can be the equivalent of theScrollView
in the previous framework UI.ScrollableColumn(resp。ScrollableRow)是
Column
(或Row
)的变体,当内容大于其高度(或宽度)时滚动。 这可以等同于以前的框架UI中的ScrollView
。LazyColumnFor (resp. LazyRowFor) is a vertically (or horizontally) scrolling list that only composes and lays out the currently visible items. That can be the equivalent of the
RecyclerView
and its adapter in the previous framework UI.LazyColumnFor ( resp。LazyRowFor )是一个垂直(或水平)滚动列表,仅构成和布局当前可见的项目。 这可以与之前的框架UI中的
RecyclerView
及其适配器等效。
Note: Because we are an Android developer, we want to use
LazyColumnFor
as much as possible but in the current version of Compose, we don’t have as much flexibility withLazyColumnFor
as withScrollableColumn
. e.g. you can’t scroll at a specific position withLazyColumnFor
for now.注意:因为我们是Android开发人员,所以我们希望尽可能多地使用
LazyColumnFor
,但是在当前版本的Compose中,我们对LazyColumnFor
灵活性不如ScrollableColumn
。 例如,您暂时无法使用LazyColumnFor
滚动到特定位置。
产品项目组成 (Product item component)
![Image for post](https://i-blog.csdnimg.cn/blog_migrate/2b61097d795e0757a8031391d7d5a42a.png)
At Decathlon, each product item has a picture, a name and a price. In our example we are going to add the brand following theses specifications:
在迪卡侬,每个产品都有图片,名称和价格。 在我们的示例中,我们将按照以下规范添加品牌:
- The size of the picture is 70 dp in width and height. 图片的宽度和高度为70 dp。
- The text for the brand and the name use Roboto Condensed font, according to the official Decathlon typography. 根据官方的十项全能印刷法,该品牌的文字和名称均使用Roboto Condensed字体。
- The font weight for the brand is bold W700 and for the name bold W400. 该品牌的字体粗细为W700,名称为粗体W400。
The price component developed in this previous article.
在上一篇文章中开发了价格要素。
This component can be reused when we need to display a product in a list. Our model is pretty simple.
当我们需要在列表中显示产品时,可以重复使用此组件。 我们的模型非常简单。
data class Product(
val price: Price,
val name: String,
val brand: String,
val image: String
)
Info: Our picture loads its content from a URL. To do that, you can use accompanist from Chris Banes to load a picture with Coil, an image loader developed and adapted for Kotlin.
信息:我们的图片从URL加载其内容。 为此,您可以使用Chris Banes的伴奏者使用Coil (一种为Kotlin开发并改编的图像加载器)加载图片。
ScrollableColumn和ScrollableRow组件 (ScrollableColumn and ScrollableRow components)
As mentioned earlier we will be using a ScrollableColumn
to make a list which you can scroll vertically or a ScrollableRow
to scroll horizontally. Let’s have a look at the source code, both of these scrollers have a similar method signature.
如前所述,我们将使用ScrollableColumn
创建一个列表,您可以垂直滚动或使用ScrollableRow
水平滚动。 让我们看一下源代码,这两个滚动条都有相似的方法签名。
@Composable
fun ScrollableColumn(
modifier: Modifier = Modifier,
scrollState: ScrollState = rememberScrollState(0f),
verticalArrangement: Arrangement.Vertical = Arrangement.Top,
horizontalGravity: Alignment.Horizontal = Alignment.Start,
reverseScrollDirection: Boolean = false,
isScrollEnabled: Boolean = true,
contentPadding: InnerPadding = InnerPadding(0.dp),
children: @Composable ColumnScope.() -> Unit
)
@Composable
fun ScrollableRow(
modifier: Modifier = Modifier,
scrollState: ScrollState = rememberScrollState(0f),
horizontalArrangement: Arrangement.Horizontal = Arrangement.Start,
verticalGravity: Alignment.Vertical = Alignment.Top,
reverseScrollDirection: Boolean = false,
isScrollEnabled: Boolean = true,
contentPadding: InnerPadding = InnerPadding(0.dp),
children: @Composable RowScope.() -> Unit
)
This is similar to any other component in Jetpack Compose. We can update the modifier
to modify the UI according to our needs, the last parameter is the content of the scrollable area and there are some settings available for the scroll. If we want a simple scrollable list with a divider between each product, we can create our composable like this:
这类似于Jetpack Compose中的任何其他组件。 我们可以根据需要更新modifier
以修改UI,最后一个参数是可滚动区域的内容,并且有一些可用于滚动的设置。 如果我们想要一个简单的可滚动列表,并在每个产品之间使用分隔符,则可以这样创建composable:
@Composable
fun ProductList(products: List<Product>, onClick: (Product) -> Unit) {
ScrollableColumn(modifier = Modifier.fillMaxSize()) {
products.forEachIndexed { index, product ->
ProductItem(product = product, onClick = onClick)
if (index < products.size - 1) {
ProductDivider()
}
}
}
}
We declare our ScrollableColumn
and we iterate inside this component to display our product item. Nothing more. Thanks to declarative UI, we describe what we want to display and Jetpack Compose does the rest!
我们声明ScrollableColumn
并在该组件内部进行迭代以显示我们的产品。 而已。 感谢声明性的UI,我们描述了我们想要显示的内容,其余的由Jetpack Compose完成!
LazyColumnFor和LazyRowFor组件 (LazyColumnFor and LazyRowFor components)
Lazy versions of scrollable components are simpler. You don’t have settings for the scroll but they can take your list of models and you just need to declare your product item depending on the current model given in the itemContent lambda.
可滚动组件的惰性版本更简单。 您没有滚动设置,但是它们可以获取模型列表,您只需要根据itemContent lambda中提供的当前模型声明产品。
@Composable
fun <T> LazyColumnFor(
items: List<T>,
modifier: Modifier = Modifier,
contentPadding: InnerPadding = InnerPadding(0.dp),
horizontalGravity: Alignment.Horizontal = Alignment.Start,
itemContent: @Composable LazyItemScope.(T) -> Unit
)
@Composable
fun <T> LazyRowFor(
items: List<T>,
modifier: Modifier = Modifier,
contentPadding: InnerPadding = InnerPadding(0.dp),
verticalGravity: Alignment.Vertical = Alignment.Top,
itemContent: @Composable LazyItemScope.(T) -> Unit
)
Similar to our previous example, the implementation looks like:
与前面的示例类似,实现如下所示:
@Composable
fun LazyProductList(products: List<Product>, onClick: (Product) -> Unit) {
LazyColumnForIndexed(items = products) { index, product ->
ProductItem(product = product, onClick = onClick)
if (index < products.size - 1) {
ProductDivider()
}
}
}
You don’t need to declare a RecyclerView
with an adapter. Jetpack Compose doesn’t recycle any views. It will just draw what the user should see and you don’t need to care about internal stuff.
您无需使用适配器声明RecyclerView
。 Jetpack Compose不会回收任何视图。 它只会画出用户应该看到的内容,而您无需关心内部内容。
Lists with Jetpack Compose are magic! ✨
Jetpack Compose的列表很神奇! ✨
在特定位置平滑滚动 (Smooth scroll at a specific position)
In many cases, you want to scroll at a specific position in your list. Because your list is sorted alphabetically and you want to go at the first item of a letter or you want to come back at the beginning of the list. If you want to do this, you need to manipulate a ScrollState from the function rememberScrollState.
在许多情况下,您想滚动到列表中的特定位置。 因为您的列表是按字母顺序排序的,所以您想转到字母的第一项,或者想返回列表的开头。 如果要做到这一点,你需要操纵ScrollState从功能rememberScrollState 。
In our example, we display a floating action button at the bottom of our screen. Clicking it will bring us back to the first list item.
在我们的示例中,我们在屏幕底部显示一个浮动操作按钮。 单击它会将我们带回到第一个列表项。
Warning: This feature isn’t available with lazy components. In the current version of Compose, you need to use a scrollable component.
警告:惰性组件不提供此功能。 在当前版本的Compose中,您需要使用可滚动组件。
@Composable
fun ProductList(products: List<Product>) {
val scrollState = rememberScrollState()
Stack {
ScrollableColumn(
scrollState = scrollState,
modifier = Modifier.fillMaxSize(),
) {
// Product item
}
FloatingActionButton(
modifier = Modifier.gravity(align = Alignment.BottomEnd).padding(15.dp),
onClick = {
scrollState.smoothScrollTo(0f)
}
) {
Icon(asset = vectorResource(id = R.drawable.ic_top))
}
}
}
In our composable, we declare a scrollState variable from rememberScrollState
function, we give this state to our scrollable component and we just need to call the needed function to scroll to a specific position, here smoothScrollTo with 0f
that corresponds to the beginning of our list.
在我们的组合的,我们声明从scrollState变量rememberScrollState
功能,我们把这个状态我们的滚动组件,我们只需要调用所需的功能,以滚动到特定位置,在这里smoothScrollTo与0f
对应于我们的名单的开始。
![Image for post](https://i-blog.csdnimg.cn/blog_migrate/f4c5b9050152b2650564161c896f6929.png)
In this post, we’ve taken a quick dive into displaying a product list using LazyColumnFor
and ScrollableColumn
and see how to scroll at a specific position.
在本文中,我们快速浏览了如何使用LazyColumnFor
和ScrollableColumn
显示产品列表,并了解如何在特定位置滚动。
Stay tuned for the next post about Jetpack Compose at Decathlon!
请继续关注有关迪卡侬Jetpack Compose的下一篇文章!
Follow our latest posts on Twitter and LinkedIn and discover our sport tech initiatives like open APIs on our developers website 🚀
关注我们在Twitter和LinkedIn上的最新帖子,并在我们的开发人员网站上发现我们的体育技术计划,例如开放API
If you are interested in joining Decathlon Tech Team, check out our carriers portal to see the different exciting opportunities ! 👩💻👨💻
如果您有兴趣加入迪卡侬技术团队,请访问我们的运营商门户网站,查看各种激动人心的机会! 👩💻👨💻
翻译自: https://medium.com/decathlondevelopers/jetpack-compose-how-to-make-a-scrollable-list-6c8b0a98c98e
jetpack