Notice a row arriving, and stop subcomposing the list at the keyboard
Two faults from making the retained window lazy, both of them mine. A screen of blank between the last message and the box it was typed in. The window was recomputed when the view had moved far enough, and a message arriving does not move the view -- so the new row fell outside the window and stood in as a spacer of its guessed height. The version number the check compares against is only bumped by the recompute it guards, so asking before refreshing meant never noticing. It refreshes first now, and the window also watches how many rows there are, because a row arriving is the case it exists to catch and the one that does not announce itself through the scroll position. And the keyboard, which was the most expensive thing on the screen. The visible height came from a `BoxWithConstraints` wrapped around the transcript -- that is a `SubcomposeLayout`, and the IME animation changes the visible height on every frame of its slide, so the entire transcript was being subcomposed again for each of them. The same number read in the layout phase, from the scroll container's own measurement, makes it a relayout instead, and the rows keep the measurements they already have. Checked on the emulator: the newest message sits against the composer with the keyboard up, and there is no gap. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
1 parent
2b24362cc4
commit
9052e5f55e
2 files changed
+29
-9
No files matched your search
@@ -8,7 +8,6 @@ import androidx.activity.result.PickVisualMediaRequest
|
||||
import androidx.activity.result.contract.ActivityResultContracts
|
||||
import androidx.compose.foundation.Image
|
||||
import androidx.compose.foundation.layout.Box
|
||||
import androidx.compose.foundation.layout.BoxWithConstraints
|
||||
import androidx.compose.foundation.layout.Column
|
||||
import androidx.compose.foundation.layout.Row
|
||||
import androidx.compose.foundation.layout.Spacer
|
||||
@@ -1415,13 +1414,10 @@ fun SessionScreen(settings: ServerSettings, summary: SessionSummary, onBack: ()
|
||||
// is no frame in which the transcript is somewhere other than where it was left.
|
||||
val settled = !restoring && !listState.settling
|
||||
Box(Modifier.weight(1f).fillMaxWidth()) {
|
||||
BoxWithConstraints(Modifier.fillMaxSize()) {
|
||||
Box(Modifier.fillMaxSize()) {
|
||||
TranscriptColumn(
|
||||
rows = rows,
|
||||
state = listState,
|
||||
// A scrollable child is measured with no height bound, so the content cannot
|
||||
// ask how tall the visible area is; this is the only place that knows.
|
||||
viewportHeight = maxHeight,
|
||||
contentPadding = TRANSCRIPT_PADDING,
|
||||
spacing = TRANSCRIPT_SPACING,
|
||||
modifier =
|
||||
|
||||
Reference in new issue
Block a user