如何使用焦点元素实现共享元素过渡
How to implement shared element transition with focal element
我想在我的应用程序中实现共享元素转换,当一个 activity 的回收器视图项转换为另一个 activity 时,如下所示:https://storage.googleapis.com/spec-host-backup/mio-design%2Fassets%2F15N3n1xwTt0briEbfIvFUG01pMv2d_xaT%2F02-focus-focalelement-do.mp4. (source: https://material.io/design/motion/choreography.html#using-a-focal-element)
也就是说,该项目正在淡出并更改边界,然后新的 activity 淡入。据我所知,它是简单的 AutoTransition,但它不起作用。简单的褪色效果也不行。
因此,目前我只实现了项目获得新背景 activity 然后更改其边界。
因此,我最终在生成的 activity 布局中添加了回收站视图项目的布局。点击的项目的数据(例如标题等)被传送到下一个activity和intent.putExtra()
。在这种情况下,共享元素当然是项目的根视图和结果 activity 的根视图。当 activity 启动时,我通过 SharedElementCallback 将项目的数据设置为 activity 中的匹配视图,例如:
setEnterSharedElementCallback(
object : SharedElementCallback() {
override fun onSharedElementStart(...) {
val title = intent.getStringExtra(TITLE)
activity_item_title.text = title
........
}
override fun onSharedElementEnd(...) {
}
})
这允许在转换开始时显示完全相同的项目视图。然后它应该开始改变它的边界,同时淡出这个项目的视图。在某个时刻(例如在过渡的中间)当初始视图完全淡出时,activity 的 laouyt 出现,逐渐淡入。为此,我们需要在过渡过程中隐藏项目的视图 (View.visibility = View.GONE
) 并使 activity 视图可见。可能这不是最好的方法,但我通过向共享元素输入转换添加一个侦听器并使用 Handler().postDelayed
:
来解决这个问题
window.sharedElementEnterTransition.addListener(
object : android.transition.Transition.TransitionListener {
override fun onTransitionEnd(transition: Transition) {}
override fun onTransitionResume(transition: Transition) {}
override fun onTransitionPause(transition: Transition) {}
override fun onTransitionCancel(transition: Transition) {}
override fun onTransitionStart(transition: Transition) {
Handler().postDelayed({
activity_item.visibility = View.GONE
activity_view_1.visibility = View.VISIBLE
activity_view_2.visibility = View.VISIBLE
.............
.............
// Also you could e.g. set the background to your activity here, ets.
activity_view_root.background = backgroundDrawable
}, 150) //suppuse that the whole transition length is 300ms
}
}
})
过渡动画本身可能如下所示:
<transitionSet>
<targets>
<target android:targetId="@id/activity_root_view"/>
</targets>
<transition
class="com.organization.app.utils.FadeOutTransition"
android:duration="150"/>
<transition
class="com.organization.app.utils.FadeInTransition"
android:startDelay="150"/>
<changeBounds android:duration="300"/>
</transitionSet>
这里使用了自定义 FadeOutTransition 和 FadeInTransition,因为简单的 android <fade/>
动画不适用于共享元素。这些 类 与此处答案中给出的相似:Why Fade transition doesn't work on Shared Element.
创建 return 转换的步骤类似。
我想在我的应用程序中实现共享元素转换,当一个 activity 的回收器视图项转换为另一个 activity 时,如下所示:https://storage.googleapis.com/spec-host-backup/mio-design%2Fassets%2F15N3n1xwTt0briEbfIvFUG01pMv2d_xaT%2F02-focus-focalelement-do.mp4. (source: https://material.io/design/motion/choreography.html#using-a-focal-element)
也就是说,该项目正在淡出并更改边界,然后新的 activity 淡入。据我所知,它是简单的 AutoTransition,但它不起作用。简单的褪色效果也不行。
因此,目前我只实现了项目获得新背景 activity 然后更改其边界。
因此,我最终在生成的 activity 布局中添加了回收站视图项目的布局。点击的项目的数据(例如标题等)被传送到下一个activity和intent.putExtra()
。在这种情况下,共享元素当然是项目的根视图和结果 activity 的根视图。当 activity 启动时,我通过 SharedElementCallback 将项目的数据设置为 activity 中的匹配视图,例如:
setEnterSharedElementCallback(
object : SharedElementCallback() {
override fun onSharedElementStart(...) {
val title = intent.getStringExtra(TITLE)
activity_item_title.text = title
........
}
override fun onSharedElementEnd(...) {
}
})
这允许在转换开始时显示完全相同的项目视图。然后它应该开始改变它的边界,同时淡出这个项目的视图。在某个时刻(例如在过渡的中间)当初始视图完全淡出时,activity 的 laouyt 出现,逐渐淡入。为此,我们需要在过渡过程中隐藏项目的视图 (View.visibility = View.GONE
) 并使 activity 视图可见。可能这不是最好的方法,但我通过向共享元素输入转换添加一个侦听器并使用 Handler().postDelayed
:
window.sharedElementEnterTransition.addListener(
object : android.transition.Transition.TransitionListener {
override fun onTransitionEnd(transition: Transition) {}
override fun onTransitionResume(transition: Transition) {}
override fun onTransitionPause(transition: Transition) {}
override fun onTransitionCancel(transition: Transition) {}
override fun onTransitionStart(transition: Transition) {
Handler().postDelayed({
activity_item.visibility = View.GONE
activity_view_1.visibility = View.VISIBLE
activity_view_2.visibility = View.VISIBLE
.............
.............
// Also you could e.g. set the background to your activity here, ets.
activity_view_root.background = backgroundDrawable
}, 150) //suppuse that the whole transition length is 300ms
}
}
})
过渡动画本身可能如下所示:
<transitionSet>
<targets>
<target android:targetId="@id/activity_root_view"/>
</targets>
<transition
class="com.organization.app.utils.FadeOutTransition"
android:duration="150"/>
<transition
class="com.organization.app.utils.FadeInTransition"
android:startDelay="150"/>
<changeBounds android:duration="300"/>
</transitionSet>
这里使用了自定义 FadeOutTransition 和 FadeInTransition,因为简单的 android <fade/>
动画不适用于共享元素。这些 类 与此处答案中给出的相似:Why Fade transition doesn't work on Shared Element.
创建 return 转换的步骤类似。