有片段A和B。应用程序以A开头,然后,如果满足某些条件,则使用幻灯片动画自动导航到B:
fragmentTransaction
.setCustomAnimations(R.anim.slide_in_left, R.anim.slide_out_right, R.anim.slide_in_right, R.anim.slide_out_left)
.replace(R.id.container, mCurrentFragment, fragmentId)
.commitAllowingStateLoss();
我知道在mCurrentFragment
中保留对Fragments的引用是不好的,但是在这种情况下,该引用不会用于任何可疑的事情。
在大多数情况下,一切正常。
但是,如果在显示某些系统对话框时启动应用程序(例如,使用OTG将设备连接到USB时批准应用程序的自动启动),则会发生真正奇怪的事情:应用程序导航至Fragment B,但未显示UI并且保持透明。
我重现了该问题,甚至AndroidStudio的布局检查器都声称当前可见的UI属于FragmentB。发生这种情况时,由于Fragment B是透明的,因此我可以看到Fragment A的UI,但无法与之交互。该应用程序只是变得对任何触摸事件都没有响应,需要被杀死。
我添加了一些日志记录,可以看到以下内容:
// app start
[main] INFO MainActivity onStart
[main] INFO MainActivity onResume
[main] INFO FragmentA onResume
// system dialog shown
[main] INFO MainActivity onPause
[main] INFO FragmentA onPause
// replace fragment
[main] INFO navigateTo(); fragmentName: FragmentB
[main] INFO FragmentA onStop
[main] INFO FragmentB onViewCreated
[main] INFO FragmentB onStart
// dismiss system dialog
[main] INFO MainActivity onResume
[main] INFO FragmentB onResume
问题似乎与“暂停”应用程序时导航发生的事实有关。
此外,我发现this question描述了非常相似(可能相同)的问题,这表明该问题可能与Fragment事务上的动画有关。
编辑:
再执行几次测试后,似乎此错误确实与动画FragmentTransaction有关,因为如果删除动画,我将无法重现该错误。
编辑2:
忘记提及此应用程序尚未迁移到AndroidX,因此它使用对Fragments的支持:
implementation 'com.android.support:appcompat-v7:28.0.0'
编辑3:
我试图构建一个最小的独立应用程序来重现此问题。尽管它可以在生产应用程序中轻松复制,但我无法在此独立的存储库中复制它。试图在生命周期方法中添加可变数量的延迟,但这没有帮助。现在,我开始认为它也可能会实现为其他功能...
我对可用于解决此错误的变通办法有一些想法,但我真的很想知道此行为的根本原因,以及它是应用程序还是Android框架中的错误。