Status Update
Comments
mi...@perplexity.ai <mi...@perplexity.ai> #2
Branch: androidx-master-dev
commit b4a3fe1d53c8c8082cf16795da164c446f7fd912
Author: Ian Lake <ilake@google.com>
Date: Wed Jul 15 14:34:08 2020
Add a hook that fires before the Activity's super.onCreate()
Provide a standard, composable API for libraries and
developers to run code as soon as possible after a
Context is available to an Activity (i.e., before the
logic in the base Activity.onCreate() runs and before any
layout is inflated).
This updates the code in FragmentActivity and
AppCompatActivity to use that new API.
Test: new activity tests pass
Test: existing fragment and appcompat tests still pass
BUG: 161390636
Relnote: "`ComponentActivity` now implements
`ContextAware`, allowing you to add one or more
`OnContextAvailableListener` instances which will
receive a callback before the base `Activity.onCreate()`."
Change-Id: I513da73bc0862b62af4166be35ba353fc7869a09
M activity/activity/api/1.2.0-alpha07.txt
M activity/activity/api/current.txt
M activity/activity/api/public_plus_experimental_1.2.0-alpha07.txt
M activity/activity/api/public_plus_experimental_current.txt
M activity/activity/api/restricted_1.2.0-alpha07.txt
M activity/activity/api/restricted_current.txt
M activity/activity/src/androidTest/java/androidx/activity/ComponentActivityLifecycleTest.kt
A activity/activity/src/androidTest/java/androidx/activity/contextaware/ContextAwareHelperTest.kt
M activity/activity/src/main/java/androidx/activity/ComponentActivity.java
A activity/activity/src/main/java/androidx/activity/contextaware/ContextAware.java
A activity/activity/src/main/java/androidx/activity/contextaware/ContextAwareHelper.java
A activity/activity/src/main/java/androidx/activity/contextaware/OnContextAvailableListener.java
M appcompat/appcompat/build.gradle
M appcompat/appcompat/src/main/java/androidx/appcompat/app/AppCompatActivity.java
M fragment/fragment/src/main/java/androidx/fragment/app/FragmentActivity.java
ti...@google.com <ti...@google.com> #3
Branch: androidx-master-dev
commit 494d98d48e3c95c4338bda7ed1bf46797de257f6
Author: Ian Lake <ilake@google.com>
Date: Mon Aug 03 13:07:36 2020
Deliver the Context when added after it is available
Previously, an OnContextAvailableListener would only
receive a callback if added prior to the Context
being made available.
Rather than allow developers fall into a pitfall
where they add a listener and never receive a
callback, synchronously deliver the currently
available Context to listeners.
Test: updated activity tests pass
BUG: 161390636
Relnote: N/A
Change-Id: I24eff02712c90e84e1998407082e0b07cf04b44a
M activity/activity/api/current.txt
M activity/activity/api/public_plus_experimental_current.txt
M activity/activity/api/restricted_current.txt
M activity/activity/src/androidTest/java/androidx/activity/contextaware/ContextAwareHelperTest.kt
M activity/activity/src/main/java/androidx/activity/ComponentActivity.java
M activity/activity/src/main/java/androidx/activity/contextaware/ContextAware.java
M activity/activity/src/main/java/androidx/activity/contextaware/ContextAwareHelper.java
mi...@perplexity.ai <mi...@perplexity.ai> #4
Branch: androidx-master-dev
commit 5d11382f47626211d512b9135f6b5f40b88f6647
Author: Ian Lake <ilake@google.com>
Date: Mon Aug 03 12:45:55 2020
Simplify OnContextAvailableListener interface
Rather than pass the ContextAware object,
the Context, and a Bundle for saved instance
state, pass only the Context to the
onContextAvailable() callback.
The ContextAware parameter is not needed in
general (unregistering is a corner case that
can be handled by capturing a reference to the
ContextAware).
The saved instance state Bundle is not needed
when we can ensure that the
SavedStateRegistry has had its state restored
before the listeners are called. This ensures
that all Saved State logic is centralized in
the API specifically built for saving state
rather than leaking into other APIs.
To accomplish this API change, the storage of
FragmentManager's and AppCompatDelegate's saved
state was moved to SavedStateRegistry as part of
FragmentActivity and AppCompatActivity,
respectively. Longer term, FragmentManager and
AppCompatDelegate should provide public APIs for
connecting directly to SavedStateRegistry, but
that is out of scope for this change.
Test: activity, fragment, and appcompat tests pass
BUG: 161390636
Relnote: N/A
Change-Id: I32fdd4b2c4c391c3fa97158dbd7508fa96b08d7a
M activity/activity/api/current.txt
M activity/activity/api/public_plus_experimental_current.txt
M activity/activity/api/restricted_current.txt
M activity/activity/src/androidTest/java/androidx/activity/ComponentActivityLifecycleTest.kt
M activity/activity/src/androidTest/java/androidx/activity/ComponentActivitySavedStateTest.kt
M activity/activity/src/androidTest/java/androidx/activity/contextaware/ContextAwareHelperTest.kt
M activity/activity/src/main/java/androidx/activity/ComponentActivity.java
M activity/activity/src/main/java/androidx/activity/contextaware/ContextAwareHelper.java
M activity/activity/src/main/java/androidx/activity/contextaware/OnContextAvailableListener.java
M appcompat/appcompat/src/main/java/androidx/appcompat/app/AppCompatActivity.java
M fragment/fragment/src/androidTest/java/androidx/fragment/app/FragmentArchLifecycleTest.kt
M fragment/fragment/src/main/java/androidx/fragment/app/FragmentActivity.java
ti...@google.com <ti...@google.com> #5
Branch: androidx-master-dev
commit d830158f1671930bab215716e329349a42eec1dd
Author: Ian Lake <ilake@google.com>
Date: Fri Jul 31 14:14:29 2020
Add suspending withContextAvailable to ContextAware
Expand the ContextAware interface to allow developers
to synchronously peek to see if the context is
availble.
This allows us to write a Kotlin extension
withContextAvailable() that runs a non-suspending
block once the context becomes available (either
synchronously if it is already available or by
using a OnContextAvailableListener under the hood
if not).
Test: new tests pass
BUG: 161390636
Relnote: "Added a `peekAvailableContext()` API to
`ContextAware` to allow you to synchronously determine
if a Context is available. A suspending Kotlin extension
`withContextAvailable()` allows you to run a
non-suspending block when the Context becomes available
and return a result."
Change-Id: I8290cd9de8231913036d23a233c177ed45d2d370
M activity/activity-ktx/api/current.txt
M activity/activity-ktx/api/public_plus_experimental_current.txt
M activity/activity-ktx/api/restricted_current.txt
A activity/activity-ktx/src/androidTest/java/androidx/activity/contextaware/ContextAwareTest.kt
A activity/activity-ktx/src/main/java/androidx/activity/contextaware/ContextAware.kt
M activity/activity/api/current.txt
M activity/activity/api/public_plus_experimental_current.txt
M activity/activity/api/restricted_current.txt
M activity/activity/src/androidTest/java/androidx/activity/contextaware/ContextAwareHelperTest.kt
M activity/activity/src/main/java/androidx/activity/ComponentActivity.java
M activity/activity/src/main/java/androidx/activity/contextaware/ContextAware.java
M activity/activity/src/main/java/androidx/activity/contextaware/ContextAwareHelper.java
mi...@perplexity.ai <mi...@perplexity.ai> #6
The new ContextAware
API will be available in Activity 1.2.0-alpha08 and is used by Fragment 1.3.0-alpha08 and AppCompat 1.3.0-alpha02 to implement FragmentManager's and AppCompatDelegate's pre-onCreate() logic.
ti...@google.com <ti...@google.com> #7
Wait, this can't work as advertised.
FragmentActivity extends ComponentActivity
public FragmentActivity(@LayoutRes int contentLayoutId) {
super(contentLayoutId);
init();
}
private void init() {
addOnContextAvailableListener(new OnContextAvailableListener() {
// ...
}
}
ComponentActivity
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
// ...
mContextAwareHelper.dispatchOnContextAvailable(this);
super.onCreate(savedInstanceState);
//...
}
- Call
FragmentActivity
constructor, - which calls
ComponentActivity
super constructor, - which dispatches context available... to noone,
- and calls platform Activity.onCreate.
- Bubble up to
FragmentActivity
constructor and register context listener, - which is invoked synchronously but only after platform
Activity.onCreate
has already been called.
Did I miss something? I'm confused.
mi...@perplexity.ai <mi...@perplexity.ai> #8
Never mind, constructor vs onCreate. :facepalm: Sorry.
ti...@google.com <ti...@google.com>
mi...@perplexity.ai <mi...@perplexity.ai> #9
Re #8 - the fact that these are different things is indeed exactly why this API exists :)
ti...@google.com <ti...@google.com> #11
I'm investigating what would cause items to be composed but not placed.
We'll submit a fix in shared element in 1.8 to account for that scenario if that's an intended behavior.
Have you tried a recent 1.8 release and see if it's reproducible?
mi...@perplexity.ai <mi...@perplexity.ai> #12
Thank you!
Unfortunately we cannot release publicly with 1.8 alpha, and we never reproed this issue locally even with 1.7.x.
ti...@google.com <ti...@google.com> #13
I'll prepare a fix to account for the use case where content may be composed but never participate in either measurement or placement. Keep in mind, the fix likely will only land in 1.8.
mi...@perplexity.ai <mi...@perplexity.ai> #14
Awesome, thank you! If there's any chance to have it in 1.7.6, would be absolutely amazing, but no worries if not. Thanks a lot again for the help!
ap...@google.com <ap...@google.com> #15
Project: platform/frameworks/support
Branch: androidx-main
Author: Doris Liu <
Link:
Require shared element to draw in place before drawing in overlay
Expand for full commit details
Require shared element to draw in place before drawing in overlay
This change fixes a rare issue where a shared element is composed
in both incoming and outgoing content, but measured and placed in
neither. The fix involves checking the shared element has been
drawn for at least frame before drawing it in the overlay. This
accounts for not only the requirement to measure and place shared
elements, but also ensured that when the draw is skipped by
a parent, shared element will not draw.
Fixes: 371802474
Test: New test added
Change-Id: I35108ce255cf4728a9ca3ef7834d6962abcc94c0
Files:
- M
compose/animation/animation/src/androidInstrumentedTest/kotlin/androidx/compose/animation/SharedTransitionTest.kt
- M
compose/animation/animation/src/commonMain/kotlin/androidx/compose/animation/SharedContentNode.kt
- M
compose/animation/animation/src/commonMain/kotlin/androidx/compose/animation/SharedElement.kt
Hash: baae6769d3323d141b17e0d916323cf6487034ea
Date: Wed Nov 13 15:27:39 2024
pr...@google.com <pr...@google.com> #16
The following release(s) address this bug.It is possible this bug has only been partially addressed:
androidx.compose.animation:animation:1.8.0-alpha07
androidx.compose.animation:animation-android:1.8.0-alpha07
androidx.compose.animation:animation-jvmstubs:1.8.0-alpha07
androidx.compose.animation:animation-linuxx64stubs:1.8.0-alpha07
Description
Jetpack Compose component used: Modifier.sharedElement
Hey! We added a shared element transition to the app, using Compose 1.7.3. We are seeing this crash in firebase, however I could not reproduce the issue locally.
Our layout hierarchy looks like this:
NavHost -> ... -> AnimatedVisibility -> ... -> BoxWithConstraints -> First layout with sharedElement
\> ... -> AnimatedVisibility -> ... -> BoxWithConstraints -> Second layout with sharedElement
With "..." I replaced series of "normal" layouts.
The crash is due to this precondition failing:
It seems somehow one of the elements gets drawn without having had layout before.
Any idea if I am doing something wrong, or any workarounds? Thank you!!
Stack trace:
SharedElementInternalState.drawInOverlay
java.lang.IllegalArgumentException - Error: current bounds not set yet.
androidx.compose.animation.SharedElementInternalState.drawInOverlay (SharedElementInternalState.java:196)
androidx.compose.animation.SharedTransitionScopeImpl.drawInOverlay$animation_release (SharedTransitionScopeImpl.java:1086)
androidx.compose.animation.SharedTransitionScopeKt$SharedTransitionScope$1$2$1.invoke (SharedTransitionScope.kt:161)
androidx.compose.animation.SharedTransitionScopeKt$SharedTransitionScope$1$2$1.invoke (SharedTransitionScope.kt:159)
androidx.compose.ui.draw.DrawWithContentModifier.draw (DrawModifier.kt:422)
androidx.compose.ui.node.LayoutNodeDrawScope.drawDirect-eZhPAX0$ui_release (LayoutNodeDrawScope.kt:110)
androidx.compose.ui.node.LayoutNodeDrawScope.draw-eZhPAX0$ui_release (LayoutNodeDrawScope.kt:89)
androidx.compose.ui.node.NodeCoordinator.drawContainedDrawModifiers (NodeCoordinator.kt:450)
androidx.compose.ui.node.NodeCoordinator.draw (NodeCoordinator.kt:439)
androidx.compose.ui.node.LayoutModifierNodeCoordinator.performDraw (LayoutModifierNodeCoordinator.kt:280)
androidx.compose.ui.node.NodeCoordinator.drawContainedDrawModifiers (NodeCoordinator.kt:447)
androidx.compose.ui.node.NodeCoordinator.draw (NodeCoordinator.kt:439)
androidx.compose.ui.node.LayoutNode.draw$ui_release (LayoutNode.kt:1000)
androidx.compose.ui.node.InnerNodeCoordinator.performDraw (InnerNodeCoordinator.kt:196)
androidx.compose.ui.node.LayoutNodeDrawScope.drawContent (LayoutNodeDrawScope.kt:68)
androidx.compose.foundation.BackgroundNode.draw (Background.kt:163)
androidx.compose.ui.node.LayoutNodeDrawScope.drawDirect-eZhPAX0$ui_release (LayoutNodeDrawScope.kt:110)
androidx.compose.ui.node.LayoutNodeDrawScope.draw-eZhPAX0$ui_release (LayoutNodeDrawScope.kt:89)
androidx.compose.ui.node.NodeCoordinator.drawContainedDrawModifiers (NodeCoordinator.kt:450)
androidx.compose.ui.node.NodeCoordinator.access$drawContainedDrawModifiers (NodeCoordinator.kt:58)
androidx.compose.ui.node.NodeCoordinator$drawBlock$1$1.invoke (NodeCoordinator.java:469)
androidx.compose.ui.node.NodeCoordinator$drawBlock$1$1.invoke (NodeCoordinator.java:468)
androidx.compose.runtime.snapshots.Snapshot$Companion.observe (Snapshot.java:2441)
androidx.compose.runtime.snapshots.SnapshotStateObserver$ObservedScopeMap.observe (SnapshotStateObserver.kt:502)
androidx.compose.runtime.snapshots.SnapshotStateObserver.observeReads (SnapshotStateObserver.kt:258)
androidx.compose.ui.node.OwnerSnapshotObserver.observeReads$ui_release (OwnerSnapshotObserver.kt:133)
androidx.compose.ui.node.NodeCoordinator$drawBlock$1.invoke (NodeCoordinator.java:468)
androidx.compose.ui.node.NodeCoordinator$drawBlock$1.invoke (NodeCoordinator.java:466)
androidx.compose.ui.platform.GraphicsLayerOwnerLayer$recordLambda$1.invoke (GraphicsLayerOwnerLayer.java:291)
androidx.compose.ui.platform.GraphicsLayerOwnerLayer$recordLambda$1.invoke (GraphicsLayerOwnerLayer.java:289)
androidx.compose.ui.graphics.layer.GraphicsLayerV29.record (GraphicsLayerV29.android.kt:245)
androidx.compose.ui.graphics.layer.GraphicsLayer.recordInternal (AndroidGraphicsLayer.android.kt:430)
androidx.compose.ui.graphics.layer.GraphicsLayer.record-mL-hObY (AndroidGraphicsLayer.android.kt:423)
androidx.compose.ui.platform.GraphicsLayerOwnerLayer.updateDisplayList (GraphicsLayerOwnerLayer.android.kt:284)
androidx.compose.ui.platform.GraphicsLayerOwnerLayer.drawLayer (GraphicsLayerOwnerLayer.android.kt:229)
androidx.compose.ui.node.NodeCoordinator.draw (NodeCoordinator.kt:434)
androidx.compose.ui.node.LayoutNode.draw$ui_release (LayoutNode.kt:1000)
androidx.compose.ui.node.InnerNodeCoordinator.performDraw (InnerNodeCoordinator.kt:196)
androidx.compose.ui.node.NodeCoordinator.drawContainedDrawModifiers (NodeCoordinator.kt:447)
androidx.compose.ui.node.NodeCoordinator.draw (NodeCoordinator.kt:439)
androidx.compose.ui.node.LayoutNode.draw$ui_release (LayoutNode.kt:1000)
androidx.compose.ui.platform.AndroidComposeView.dispatchDraw (AndroidComposeView.android.kt:1564)
android.view.View.draw (View.java:25180)
android.view.View.updateDisplayListIfDirty (View.java:24036)
android.view.ViewGroup.recreateChildDisplayList (ViewGroup.java:4764)
...