Jetpack Compose中用Intent打开链接报ActivityNotFoundException怎么解决?
问题排查及解决方法
报错根因
android.content.ActivityNotFoundException 出现的核心原因是系统没有找到可以匹配你传入的Intent的Activity组件,当前场景下绝大多数情况是传入的uri没有带合法的scheme前缀。
排查步骤
- 第一步:打印传入的
content参数值,确认uri是否带有http://或者https://前缀,你报错信息里的dat=example.com就明显缺少协议前缀,Uri.parse会把example.com识别为scheme为example的uri,自然没有应用能处理。 - 第二步:如果确认uri不带协议前缀,统一给uri补全默认的
https://前缀后再解析;如果是其他协议的uri(比如tel、mailto、sms等),也要确保scheme拼写正确。 - 第三步:添加Intent可用性校验,在启动Activity之前先判断系统是否有能处理该Intent的应用,避免崩溃。
- 第四步:Android 11及以上版本需要注意,如果你的应用targetSdk≥30,需要在AndroidManifest.xml里添加
<queries>标签声明你要访问的外部应用能力,否则即使存在可用Activity也会检测不到。
修复后的代码实现
@Composable fun MeetingDetailRowWithLink( header: String, content: String ) { val context = LocalContext.current // 处理uri补全协议前缀 val validUri = remember(content) { val rawUri = content.trim() if (rawUri.startsWith("http://") || rawUri.startsWith("https://")) { Uri.parse(rawUri) } else { // 默认补全https前缀,如果你确定是http场景可以自行调整 Uri.parse("https://$rawUri") } } val intent = remember(validUri) { Intent(Intent.ACTION_VIEW, validUri) } Column( modifier = Modifier .padding(10.dp), horizontalAlignment = Alignment.Start ) { Text( text = header, color = MaterialTheme.colors.primary ) Text( text = content, modifier = Modifier .clickable { // 先校验Intent是否可被处理 if (intent.resolveActivity(context.packageManager) != null) { context.startActivity(intent) } else { // 可添加无可用应用的提示,比如Toast Toast.makeText(context, "没有找到可打开该链接的应用", Toast.LENGTH_SHORT).show() } } ) } }
AndroidManifest.xml补充配置(targetSdk≥30需要)
如果是打开http/https链接,在manifest的<manifest>标签下添加如下配置:
<queries> <intent> <action android:name="android.intent.action.VIEW" /> <category android:name="android.intent.category.BROWSABLE" /> <data android:scheme="https" /> </intent> <!-- 如果需要支持http再添加下面的配置 --> <intent> <action android:name="android.intent.action.VIEW" /> <category android:name="android.intent.category.BROWSABLE" /> <data android:scheme="http" /> </intent> </queries>
内容的提问来源于stack exchange,提问作者mucahid-erdogan
相关产品推荐
相关产品推荐

