katspaugh / wavesurfer.js

Audio waveform player
https://wavesurfer.xyz
BSD 3-Clause "New" or "Revised" License
8.79k stars 1.63k forks source link

Play function not working ios safari and desktop safari #3379

Closed korayrubicoda closed 11 months ago

korayrubicoda commented 11 months ago

Bug description

Unhandled Promise Rejection: NotSupportedError: The operation is not supported. wavesurfer.current.play(); function does not work in safari

Environment

Minimal code snippet

  const handlePlayPause = () => {
    setTimePlay(true);
    setPlay(!playing);
    if (playing) {
      wavesurfer.current.pause();
    } else {
      wavesurfer.current.play();
    }
  };

Screenshots

Screenshot 2023-12-04 at 16 08 16
korayrubicoda commented 11 months ago

I think the problem is that the blob link does not work. Do I need to do anything extra for the source blob?

const formWaveSurferOptions = (ref: any) => ({
    container: ref,
    waveColor: "rgba(255, 255, 255, 0.3)",
    progressColor: "#D2E951",
    cursorColor: "black",
    barWidth: 3,
    barRadius: 4,
    responsive: true,
    hideScrollbar: true,
    height: 38,
    barGap: 5.5,
    interact: interact,
    url:blobUrl,
    // If true, normalize by the maximum peak instead of 1.0.
    normalize: true,
    // Use the PeakCache to improve rendering speed of large waveforms.
    peaks:peaks[0],

    // backend: "MediaElement",
    mediaType: "audio",
  });

  useEffect(() => {
    if (duration === 0) {
      setDuration(totalTime);
    }
  }, [duration, totalTime]);

  useEffect(() => {
    // setLoading(true);
    setPlay(false);
    setTimePlay(false);

    const options: any = formWaveSurferOptions(waveformRef.current);
    wavesurfer.current = WaveSurfer.create(options);

    /*
    let _peaks = testData.data;
    if (peaks && peaks.length > 0 && peaks !== "" && peaks !== undefined) {
      _peaks = peaks.filter((x: any) => x !== 0 && x !== undefined);
    }
    wavesurfer.current.backend.setPeaks(_peaks);
    wavesurfer.current.drawBuffer();
    */
    wavesurfer.current.on("audioprocess", function () {
      let _currentTime = wavesurfer.current.getCurrentTime();

      setCurrentTime(_currentTime);
    });
    wavesurfer.current.on("ready", function () {
      // setLoading(false);
      let _totalTime = wavesurfer.current.getDuration();
      setTotalTime(_totalTime);
      // https://wavesurfer-js.org/docs/methods.html
      // wavesurfer.current.play();

      // make sure object stillavailable when file loaded
      if (wavesurfer.current) {
        wavesurfer.current.setVolume(volume);
        setVolume(volume);
      }
    });
    wavesurfer.current.on("finish", function () {
      setPlay(false);
      setTimePlay(false);
    });
    return () => wavesurfer.current.destroy();
  }, [url]);

  useEffect(() => {
    if (playing) {
      const _remainingTime = (duration ? duration : totalTime) - currentTime;
      setRemainingTime(_remainingTime);
      getCurrentTime(currentTime);
    }
  }, [currentTime, totalTime]);

  const handlePlayPause = useCallback(
    () => {
      setTimePlay(true);
      setPlay(!playing);
      if (wavesurfer.current.isPlaying()) {
        setTimePlay(false);
        wavesurfer.current.pause();
      } else {
        setTimePlay(true);
        wavesurfer.current.play();
      }
    },
    [wavesurfer]
  );