I have a column which consists of multiple composables of one Text (For row title) and one lazyrow (For row items), for TV screens
For reference :
Column {
AlignedRow(data)
}
fun AlignedRow(data) {
if (data != null)
Column {
Text()
LazyRow {
items(data.rowList) {
//add items
}
}
}
While scrolling the parent column downwards, everything is as expected; but while scrolling back up, the top most AlignedRow only focusses on one of the child items at the top of the screen and thus the title text is left out of the screen?
How can I make this scroll work in a way so that when we scroll up both the lazyrow and the title text is rendered onto the screen? Any help would be appreciated!
You can create a extension method on Modifier which will bring the entire item in view if any of its children is focused.
internal fun Modifier.bringIntoViewIfChildrenAreFocused(): Modifier = composed(
inspectorInfo = debugInspectorInfo { name = "bringIntoViewIfChildrenAreFocused" },
factory = {
var myRect: Rect = Rect.Zero
this
.onSizeChanged {
myRect = Rect(Offset.Zero, Offset(it.width.toFloat(), it.height.toFloat()))
}
.bringIntoViewResponder(
remember {
object : BringIntoViewResponder {
// return the current rectangle and ignoring the child rectangle received.
@ExperimentalFoundationApi
override fun calculateRectForParent(localRect: Rect): Rect = myRect
// The container is not expected to be scrollable. Hence the child is
// already in view with respect to the container.
@ExperimentalFoundationApi
override suspend fun bringChildIntoView(localRect: () -> Rect?) {}
}
}
)
}
)
Here is how you can use it:
Column {
AlignedRow(data)
}
fun AlignedRow(data) {
if (data != null)
Column(Modifier.bringIntoViewIfChildrenAreFocused()) {
Text()
LazyRow {
items(data.rowList) {
//add items
}
}
}
}
Reference from the official Compose for TV library