Android7.0系统bug(Service打开Activit无需加FLAG_ACTIVITY_NEW_TASK)

先扔代码,在讨论问题

MainActivity

MyService

ThreeActivity

相信大家已经发现问题了,就是在MyService中的 startActivity(new Intent(this, ThreeActivity.class)); 会报错。但是真的会报错吗?请看下面的效果

三星盖乐世C5效果

vivo Y67A效果

发现了吗?Android7.0上这段代码是没有问题的,也就是说,Android7.0版本上是可以在不是设置 FLAG_ACTIVITY_NEW_TASK的。而Android6.0版本上是不行的。那么这到底是不是个bug呢?接下来咱们从源码入手看下到底是什么原因。

我们知道像Service,BroadcastReceiver,Application等都是ContextWrapper的子类,调用startActivity()时会调用ContextWrapper的startActivity()

这个mBase就是ContextImpl.这个ContextImpl是在ActivityThread里赋值的:

Activity-->ActivityThread::performLaunchActivity()

Service-->ActivityThread::handleCreateService()

Application-->LoadedApk::makeApplication()

有兴趣的同学自行查看,这里就不讨论了 接下来我们先看下ContextImpl的startActivity()

低版本 Android4.4 api-19(截止到Android6.0)

很简单,就是非Activity的Context启动Activity时如果不给intent设置FLAG_ACTIVITY_NEW_TASK就会报错

高版本Android8.0 api-27(Android7.0加入)

跟旧版本的代码相比,这里多了个options的非空判断(options != null),关键就在这里. 由于这里options传的就是null,于是就跳过了这个异常.那么,这里的逻辑是"&&",有一个不成立就算失败,那么我们不设置FLA 这里的注释翻译下是:从Activity外部(Service,BroadcastReceiver,Application等)不设置FLAG_ACTIVITY_NEW_TASK是不能启,可是上面的代码明显没有指定task的id就能成功启动了啊,这应该算Android系统的一个bug吧.(看来谷歌的开发和我们一样,都有迷糊的时候)

所以Android7.0和8.0版本应该都有这个bug(由于我这里没有8.0的手机,希望各位有条件的小伙伴测试下这个问题)

后续Android9.0代码已修复(&&options != null 已改为 &&options == null)

参考:作者 十蛋斯坦 《刨根问底Service为什么能启动Activity》

转载于:https://juejin.im/post/5be3d7cae51d452acd576b39

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值