uniapp(微信小程序、App)中获取音频文件时长duration

748 阅读2分钟

1.需求介绍

  • 在uniapp中获取上传的音频文件的时长,根据时长来校验提交规则。

2.实现

2.1 在微信小程序中获取音频文件时长。

根据 uni.createInnerAudioContext()来获取音频文化时长,点击可直达该api的官方文档说明。

2.1.1 不兼容的写法
  • 基于 uni.createInnerAudioContext() 封装的方法
  • ios微信小程序中可以获取到音频文件时长,在android微信小程序中就获取不到音频文件时长。
  const getAudioDurationByWx = (filePath) => {
    return new Promise((resolve, reject) => {
        // 创建并返回内部 audio 上下文 `innerAudioContext` 对象。
      const audioContext = uni.createInnerAudioContext();
      audioContext.src = filePath

      let retryCount = 0 // 当前重试获取音频文件时长的次数
      const maxRetries = 3 // 最大次数重试获取音频文件时长的次数

      const checkDuration = () => {
        if (audioContext.duration > 0) {
          const duration = audioContext.duration // 获取音频文件的时长
          audioContext.destroy() // 获取到音频文件的时长后, 直接销毁 `innerAudioContext`对象
          resolve(duration) // 音频文件的时长返回出去,供外面使用。
        } else if (retryCount < maxRetries) { // 重新试着获取时长。
          retryCount++
          setTimeout(checkDuration, 500) // 每500ms检查一次
        } else {
          audioContext.destroy(); // 超过了最大重试获取音频文件时长的次数后,直接销毁 `innerAudioContext`对象
          reject(new Error('无法获取音频时长'))
        }
      }

      // 等待一段时间后开始获取时长。
      setTimeout(() => {
        checkDuration()
      }, 100)

    // 监听`innerAudioContext`对象的错误回调方法
      audioContext.onError((err) => {
        audioContext.destroy()
        reject(err)
      })
    })
  }
2.1.2 微信小程序中的兼容写法
  • 参考博客,点击也可直达文档。
  • 如下列出代码
const getAudioDurationByWx = (filePath) => {
  return new Promise((resolve, reject) => {
    const audioContext = uni.createInnerAudioContext()
    audioContext.volume = 0; // 音量0
    audioContext.autoplay = true; // 自动播放
    audioContext.src = filePath

    audioContext.onTimeUpdate(() => {
      if (audioContext.duration > 0) {
        const duration = audioContext.duration
        audioContext.destroy()
        resolve(duration)
      } else {
        audioContext.destroy()
        reject('无法获取音频时长')
      }
      audioContext.destroy(); // 销毁实例
    })

    audioContext.onError((err) => {
      audioContext.destroy()
      reject(err)
    })
  })
}

2.2 在Android中获取音频文件时长

2.2.1 在Android中如下获取

  • 注意: 因为是音频文件上传,记得要去manifest.json中配置文件上传权限
const getAudioDurationByApp = (filePath) => {
  return new Promise((resolve, reject) => {
    try {
      if(plus.os.name.toLowerCase() === 'android') {
        const MediaMetadataRetriever = plus.android.importClass('android.media.MediaMetadataRetriever')
        const retriever = new MediaMetadataRetriever()

        retriever.setDataSource(filePath)
        const duration = retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_DURATION)
        const durationInSeconds = Math.floor(parseInt(duration) / 1000)

        retriever.release()
        resolve(durationInSeconds)
      }
    } catch (e) {
      console.error('获取音频时长失败:', e)
      reject(e)
    }
  })
}

最后

  • 如有不正之处,请佬不吝赐教,万分感谢。
  • 祝大家向上!