You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

Android应用使用jAudioTagger设置新音频封面图时抛出异常求助

Android应用使用jAudioTagger设置新音频封面图时抛出异常求助

嘿,我注意到你这段用来处理音频封面的代码还没写完呢,应该是在用jAudioTagger设置封面的时候碰到异常了吧?先给你梳理下可能的问题点和修正方向!

你提供的封面处理代码片段:

val inputStream = resolver.openInputStream(artwork)             
val bitmap = BitmapFactory.decodeStream(inputStream)             
val stream = ByteArrayOutputStream()             
bitmap.compress(android.graphics.Bitmap.CompressFormat.PNG, 80, stream)             
val byteArray = stream.toByteArray()             
val newArtwork = ArtworkFactory.getNew()             
newArtwork.binaryData = byteArray             
newArtwork.mime

首先说几个你代码里的明显问题,也是大概率导致异常的原因:

  • MIME类型未设置完整:jAudioTagger的Artwork对象必须指定正确的MIME类型,比如你用PNG格式压缩的封面,要把代码补全为newArtwork.mimeType = "image/png",如果是JPEG就设为image/jpeg,这步缺失会直接导致设置封面失败。
  • Bitmap空值未处理BitmapFactory.decodeStream(inputStream)有可能返回null(比如输入流无效、图片格式不支持),这时候直接调用bitmap.compress会触发空指针异常,一定要加非空判断。
  • 资源流未关闭:打开的inputStreamstream如果不手动关闭,会造成资源泄漏,甚至可能干扰后续jAudioTagger对音频文件的写入操作。
  • 未结合音频格式适配标签类型:不同的音频格式对应不同的标签标准(比如MP3用ID3v2,FLAC用VorbisComment),如果标签类型不匹配,设置封面时也会抛出异常。

给你一个修正后的完整示例代码:

fun updateAudioCover(resolver: ContentResolver, artworkUri: Uri, audioFilePath: String) {
    var inputStream: InputStream? = null
    var outputStream: ByteArrayOutputStream? = null

    try {
        // 打开封面图片的输入流
        inputStream = resolver.openInputStream(artworkUri) ?: run {
            // 处理输入流打开失败的情况
            println("无法打开封面图片输入流")
            return
        }

        // 解码Bitmap,加非空判断
        val bitmap = BitmapFactory.decodeStream(inputStream) ?: run {
            println("Bitmap解码失败")
            return
        }

        // 将Bitmap转为字节数组
        outputStream = ByteArrayOutputStream()
        val compressFormat = Bitmap.CompressFormat.PNG
        bitmap.compress(compressFormat, 80, outputStream)
        val coverBytes = outputStream.toByteArray()

        // 初始化jAudioTagger的Artwork对象
        val newArtwork = ArtworkFactory.getNew().apply {
            binaryData = coverBytes
            // 对应压缩格式设置MIME类型
            mimeType = if (compressFormat == Bitmap.CompressFormat.PNG) "image/png" else "image/jpeg"
            description = "专辑封面"
            width = bitmap.width
            height = bitmap.height
        }

        // 打开目标音频文件,根据格式选择对应的标签类型
        val audioFile = File(audioFilePath)
        val audioTagFile = AudioFileIO.read(audioFile)
        val tag = audioTagFile.tag ?: audioTagFile.createDefaultTag()

        // 覆盖原有的封面(如果有的话)
        tag.deleteField(FieldKey.COVER_ART)
        tag.setField(FieldKey.COVER_ART, newArtwork)

        // 写入修改后的标签到音频文件
        AudioFileIO.write(audioTagFile)
        println("封面设置成功!")

    } catch (e: Exception) {
        // 打印详细异常信息,方便定位问题
        println("设置封面时出错:${e.message}")
        e.printStackTrace()
    } finally {
        // 关闭所有打开的流,释放资源
        try {
            inputStream?.close()
            outputStream?.close()
        } catch (e: IOException) {
            e.printStackTrace()
        }
    }
}

额外的排查建议:

  • 优先查看异常堆栈信息:这是定位问题最直接的方式,比如如果是权限问题,堆栈会提示SecurityException;如果是文件不可写,会提示IOException
  • 检查文件权限:如果音频文件在外部存储,要确保你的应用申请了READ_EXTERNAL_STORAGEWRITE_EXTERNAL_STORAGE权限,Android 10及以上还要注意分区存储的适配,或者使用MANAGE_EXTERNAL_STORAGE权限(如果是针对旧版本兼容)。
  • 确认音频文件状态:确保目标音频文件没有被其他进程占用,并且当前应用有读写该文件的权限。
  • 检查jAudioTagger版本:建议使用最新的稳定版,旧版本对某些音频格式(比如FLAC、AAC)的支持可能存在bug。

备注:内容来源于stack exchange,提问作者Antonio Caravaggio

火山引擎 最新活动