屏幕旋转后rememberLauncherForActivityResult的onResult不触发求助
问题:屏幕旋转后拍照的ActivityResult回调延迟触发
我有一个用于拍照的Composable组件:
@Composable fun MyView() { val cameraLauncher = rememberLauncherForActivityResult( contract = ActivityResultContracts.TakePicture(), onResult = { success -> Log.d("PersonView","TakePicture success=$success") //do stuff... } ) //some where in the view val tempFile = createTempFile(context,person) cameraLauncher.launch(context.provideFileAsUri(tempFile)) }
触发流程与问题:
初始为竖屏状态:
- 调用
cameraLauncher.launch(context.provideFileAsUri(tempFile))启动相机 - 将屏幕旋转为横屏
- 拍摄照片并确认
- 返回应用后,
onResult回调未被触发 - 把屏幕转回竖屏后,
onResult才会执行
如何修改才能让onResult在屏幕方向改变后也能立即触发?
解决方案
这个问题的核心是屏幕旋转导致Composable所在的Activity/Fragment重建,原来的rememberLauncherForActivityResult实例被销毁,新实例无法关联之前启动的相机任务,只有切回原方向时,旧实例恢复才会触发回调。
可以通过以下两种方式解决:
方式1:用rememberSaveable保存Launcher(推荐)
把cameraLauncher的remember替换为rememberSaveable,确保屏幕旋转时Launcher实例能被正确保存和恢复:
@Composable fun MyView() { val cameraLauncher = rememberSaveable { rememberLauncherForActivityResult( contract = ActivityResultContracts.TakePicture(), onResult = { success -> Log.d("PersonView","TakePicture success=$success") //do stuff... } ) } // 注意:将启动逻辑放在用户交互事件中,避免重组时重复启动相机 Button(onClick = { val tempFile = createTempFile(context,person) cameraLauncher.launch(context.provideFileAsUri(tempFile)) }) { Text("拍照") } }
方式2:锁定Activity屏幕方向(简单直接)
如果应用不需要支持屏幕旋转,可以在AndroidManifest.xml中给对应Activity添加固定方向的配置:
<activity android:name=".YourActivity" android:screenOrientation="portrait" android:configChanges="orientation|screenSize"> </activity>
也可以在Composable中动态锁定方向:
@Composable fun MyView(context: Context) { val activity = context.findActivity() DisposableEffect(Unit) { val originalOrientation = activity.requestedOrientation activity.requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_PORTRAIT onDispose { activity.requestedOrientation = originalOrientation } } // 原相机Launcher代码... }
额外注意事项
- 不要在Composable根节点直接调用
cameraLauncher.launch,否则每次重组都会重复启动相机,务必将启动逻辑绑定到点击事件等用户交互上。 - 确保
createTempFile生成的文件拥有正确的读写权限,避免相机无法写入文件导致回调异常。
内容的提问来源于stack exchange,提问作者Ricky Mo
相关产品推荐
相关产品推荐

