📄 audioSelector.ts
const input = document.querySelector("#input input") as HTMLInputElement;
input?.addEventListener("input", async () => {
    if (input.files?.length !== 1) {
        return;
    }

    const file = input.files.item(0);
    if (file == null) {
        return;
    }
    const audioContext = new AudioContext();
    const audioBuffer = await audioContext.decodeAudioData(await file?.arrayBuffer());
    const offlineAudioContext = new OfflineAudioContext({
        length: audioBuffer.length,
        sampleRate: audioBuffer.sampleRate,
        numberOfChannels: audioBuffer.numberOfChannels,
    });

    const source = offlineAudioContext.createBufferSource();
    source.buffer = audioBuffer;
    source.start();

    const analyserNode = offlineAudioContext.createAnalyser();
    analyserNode.fftSize = 128;
    source.connect(analyserNode);

    offlineAudioContext.suspend(1).then(() => {
        const frequencyBuffer = new Uint8Array(analyserNode.frequencyBinCount);
        analyserNode.getByteFrequencyData(frequencyBuffer);
        console.log(frequencyBuffer);
        (window as any).updateCurve(frequencyBuffer);
        return offlineAudioContext.resume();
    });

    analyserNode.connect(offlineAudioContext.destination);
    await offlineAudioContext.startRendering();
});