Skip placeHolderSize logic when no match is found Fixes: 343147836 Test: New test added Change-Id: Ief0b6d1b03f9f35dd91c6b002463db76767f7182
diff --git a/compose/animation/animation/src/androidInstrumentedTest/kotlin/androidx/compose/animation/SharedTransitionTest.kt b/compose/animation/animation/src/androidInstrumentedTest/kotlin/androidx/compose/animation/SharedTransitionTest.kt index 9604026..b80aaf7 100644 --- a/compose/animation/animation/src/androidInstrumentedTest/kotlin/androidx/compose/animation/SharedTransitionTest.kt +++ b/compose/animation/animation/src/androidInstrumentedTest/kotlin/androidx/compose/animation/SharedTransitionTest.kt
@@ -77,8 +77,10 @@ import androidx.compose.ui.graphics.compositeOver import androidx.compose.ui.layout.ContentScale import androidx.compose.ui.layout.ScaleFactor +import androidx.compose.ui.layout.approachLayout import androidx.compose.ui.layout.onGloballyPositioned import androidx.compose.ui.layout.onPlaced +import androidx.compose.ui.layout.onSizeChanged import androidx.compose.ui.layout.positionInWindow import androidx.compose.ui.platform.LocalDensity import androidx.compose.ui.platform.testTag @@ -2643,6 +2645,47 @@ } @Test + fun testPlaceHolderLogicSkippedWhenNoMatch() { + var parentSize: IntSize? = null + val changeInProgress = true + var testSize by mutableStateOf(IntSize.Zero) + rule.setContent { + AnimatedVisibility(visible = true) { + SharedTransitionLayout { + Box( + Modifier.onSizeChanged { parentSize = it } + .sharedBounds( + rememberSharedContentState("test"), + this@AnimatedVisibility + ) + ) { + Box( + Modifier.approachLayout( + isMeasurementApproachInProgress = { changeInProgress } + ) { measurable, constraints -> + measurable.measure(constraints).run { + layout(testSize.width, testSize.height) { place(0, 0) } + } + } + .requiredSize(40.dp, 40.dp) + ) + } + } + } + } + rule.waitForIdle() + assertEquals(testSize, parentSize) + + testSize = IntSize(20, 25) + rule.waitForIdle() + assertEquals(testSize, parentSize) + + testSize = IntSize(35, 10) + rule.waitForIdle() + assertEquals(testSize, parentSize) + } + + @Test fun testUserModifierInSharedTransitionLayout() { var scope: SharedTransitionScope? = null rule.setContent {
diff --git a/compose/animation/animation/src/commonMain/kotlin/androidx/compose/animation/SharedContentNode.kt b/compose/animation/animation/src/commonMain/kotlin/androidx/compose/animation/SharedContentNode.kt index 2a3de05..8d6b5e6 100644 --- a/compose/animation/animation/src/commonMain/kotlin/androidx/compose/animation/SharedContentNode.kt +++ b/compose/animation/animation/src/commonMain/kotlin/androidx/compose/animation/SharedContentNode.kt
@@ -161,18 +161,20 @@ } private fun MeasureScope.place(placeable: Placeable): MeasureResult { - val (w, h) = - state.placeHolderSize.calculateSize( - requireLookaheadLayoutCoordinates().size, - IntSize(placeable.width, placeable.height) - ) - return layout(w, h) { + if (!sharedElement.foundMatch) { // No match - if (!sharedElement.foundMatch) { + return layout(placeable.width, placeable.height) { // Update currentBounds coordinates?.updateCurrentBounds() placeable.place(0, 0) - } else { + } + } else { + val (w, h) = + state.placeHolderSize.calculateSize( + requireLookaheadLayoutCoordinates().size, + IntSize(placeable.width, placeable.height) + ) + return layout(w, h) { // Start animation if needed if (sharedElement.targetBounds != null) { boundsAnimation.animate(