簡體   English   中英

無法在網頁上獲取 m4a 音頻文件的長度

[英]cant get length of m4a audio file on webpage

我正在嘗試制作一個 nodejs 網站,該網站將返回用戶選擇的任何音頻文件的長度(以秒為單位)。 到目前為止,我可以使用 mp3、wav 和 flac 文件。 但它不適用於所有 .m4a 或 .aif 文件

我的帶有 javascript 的 HTML 頁面的代碼如下:

choose audio file to get length:
<input style="cursor: pointer;" type="file" id="file" multiple="multiple" />

<script>

    //when files are selected:
    $("#file").change(async function (e) {
        console.log('file(s) selected')
        //get files 
        var files = e.currentTarget.files;
        //get number of files
        var numberOfFiles = files.length;
        //for each file
        for (i = 0; i < numberOfFiles; i++) {
            console.log(`songs[${i}].type=`, files[i].type)
            //get file length
            let songLength = await getSongLength(files[i]);
            console.log('songLength=', songLength)
        }

    });

    //recieve audio file, return length
    function getSongLength(song) {
        return new Promise(function (resolve, reject) {
            console.log('getSongLength() begin setup')
            //create objectURL and audio object for ssong
            objectURL = URL.createObjectURL(song);
            mySound = new Audio([objectURL])
            console.log('getSongLength() end setup')
            //when song metadata is loaded:
            mySound.addEventListener("canplaythrough", function (e) {
                console.log('getSongLength() canplaythrough')
                var seconds = e.currentTarget.duration;
                resolve(seconds)
            });

        });
    }

</script>

我收集了 6 個不同的文件進行測試,在我上面的代碼上運行它們后,發現了以下結果:

  • aif:不工作
  • flac:工作
  • m4a_file:不工作
  • m4a_file_from_comments_below:不工作
  • mp3:工作
  • wav:工作

我的測試文件下載: https : //easyupload.io/m/la9xro

似乎當我輸入我的 m4a 文件sample_M4A_file ,它掛在getSongLength()函數內並且從不進入.addEventListener("canplaythrough"函數,是否有任何替代方法可以用來始終如一地獲取每個音頻文件的持續時間(以秒為單位)?

在此處輸入圖片說明

這是因為您的瀏覽器不支持Apple Lossless編解碼器。 如果您在 Safari 中嘗試,它將起作用。
如果您將error事件附加到您的媒體元素,您將看到它 fires

除了使用像mediainfo.js (2.4MB+) 這樣應該支持大多數格式的重型機器之外,沒有真正的通用解決方案。

 const input = document.querySelector( "input" ); input.onchange = async (evt) => { const mediainfo = await new Promise( (res) => MediaInfo(null, res) ); const file = input.files[ 0 ]; const getSize = () => file.size; const readChunk = async (chunkSize, offset) => new Uint8Array( await file.slice(offset, offset + chunkSize).arrayBuffer() ); const info = await mediainfo.analyzeData(getSize, readChunk); // assumes we are only interested in audio duration const audio_track = info.media.track.find( (track) => track[ "@type" ] === "Audio" ); console.log( audio_track.Duration ); };
 <script src="https://unpkg.com/mediainfo.js@0.1.4/dist/mediainfo.min.js"></script> <input type="file">


Ps:使用媒體元素方案時,無需等待canplaythrough ,只需等待loadedmetadata ,如果你得到Infinity,試試這個hack

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM