You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android MediaPlayer调用openFd时崩溃问题求助

解决MediaPlayer加载资产文件时的崩溃问题

我正试图通过图片属性为MediaPlayer设置显示边界,但执行requireContext().assets.openFd(imagename)代码行时应用崩溃,相关代码及崩溃日志如下:

相关代码

player = MediaPlayer().apply {
    requireContext().assets.openFd(imagename)
        .use { descriptor ->

            val metadataRetriever = MediaMetadataRetriever()
            metadataRetriever.setDataSource(
                descriptor.fileDescriptor,
                descriptor.startOffset,
                descriptor.length
            )

            val videoWidth = metadataRetriever.extractMetadata(METADATA_KEY_VIDEO_WIDTH)
                ?.toFloatOrNull()
                ?: 0f
            val videoHeight = metadataRetriever.extractMetadata(METADATA_KEY_VIDEO_HEIGHT)
                ?.toFloatOrNull()
                ?: 0f
            val videoRotation = metadataRetriever.extractMetadata(METADATA_KEY_VIDEO_ROTATION)
                ?.toFloatOrNull()
                ?: 0f

            // 处理视频旋转,确保缩放逻辑计算正确
            val imageSize = RectF(0f, 0f, augmentedImage.extentX, augmentedImage.extentZ)
                .transform(rotationMatrix(videoRotation))

            val videoScaleType = VideoScaleType.CenterCrop

            videoAnchorNode.setVideoProperties(
                videoWidth = videoWidth, videoHeight = videoHeight, videoRotation = videoRotation,
                imageWidth = imageSize.width(), imageHeight = imageSize.height(),
                videoScaleType = videoScaleType
            )
        }

崩溃日志

FATAL EXCEPTION: main
Process: io.github.sceneview.sample.araugmentedimage, PID: 2250
java.lang.RuntimeException: java.lang.reflect.InvocationTargetException
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:588)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1103)
Caused by: java.lang.reflect.InvocationTargetException
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:578)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1103) 
Caused by: java.io.FileNotFoundException: qrcode
at android.content.res.AssetManager.nativeOpenAssetFd(Native Method)
at android.content.res.AssetManager.openFd(AssetManager.java:1011)
at io.github.sceneview.sample.araugmentedimage.MainFragment$onViewCreated$1$2.invoke(MainFragment.kt:77)
at io.github.sceneview.sample.araugmentedimage.MainFragment$onViewCreated$1$2.invoke(MainFragment.kt:59)
at io.github.sceneview.ar.ARSceneView.onSessionUpdated(ARSceneView.kt:324)
at io.github.sceneview.ar.ARSceneView.onFrame(ARSceneView.kt:278)
at io.github.sceneview.SceneView$frameCallback$1.doFrame(SceneView.kt:295)
at android.view.Choreographer$CallbackRecord.run(Choreographer.java:1687)
at android.view.Choreographer$CallbackRecord.run(Choreographer.java:1698)
at android.view.Choreographer.doCallbacks(Choreographer.java:1153)
at android.view.Choreographer.doFrame(Choreographer.java:1069)
at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:1646)
at android.os.Handler.handleCallback(Handler.java:958)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loopOnce(Looper.java:230)
at android.os.Looper.loop(Looper.java:319)
at android.app.ActivityThread.main(ActivityThread.java:8919)
at java.lang.reflect.Method.invoke(Native Method) 
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:578) 
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1103)

解决思路

从崩溃日志的核心错误java.io.FileNotFoundException: qrcode可以看出,是找不到名为qrcode的资产文件,按以下步骤排查修复:

  • 检查文件存在性:确认qrcode文件确实放在项目的src/main/assets目录下,注意Android资产文件名区分大小写,如果实际文件名是QRCode或带后缀(比如qrcode.mp4),要完全匹配。
  • 确认文件路径:如果文件在assets的子目录中(比如assets/videos/qrcode),需要传入完整的相对路径"videos/qrcode",而不是仅传"qrcode"。
  • 验证文件有效性:确保qrcode是MediaPlayer支持的媒体格式(如MP4、3GP等),没有损坏。
  • 添加异常处理:在代码中捕获FileNotFoundException,避免应用崩溃同时方便排查问题,示例:
player = MediaPlayer().apply {
    try {
        requireContext().assets.openFd(imagename).use { descriptor ->
            // 原有逻辑代码
        }
    } catch (e: FileNotFoundException) {
        Log.e("MediaPlayer", "资产文件不存在: $imagename", e)
    }
}
  • 检查打包配置:确认项目的build.gradle文件中没有排除该资产文件,默认Android会打包assets目录下的所有文件,若有自定义打包规则需确保qrcode被包含。

内容的提问来源于stack exchange,提问作者CYAD

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.25 12:58:23