zmxv / react-native-sound

React Native module for playing sound clips
MIT License
2.79k stars 748 forks source link

Playing sound using require in iOS causes error "onError is not a function" #588

Open rgouzal opened 5 years ago

rgouzal commented 5 years ago

When running on app on iOS I get this error:

image

Code being used for initializing sound file:

import Sound from "react-native-sound"

// Load the sound file 'whoosh.mp3' from the app bundle
// See notes below about preloading sounds within initialization code below.
var message_received = new Sound(require("../../res/audio/Page_Turn.mp3"), Sound.MAIN_BUNDLE, (error) => {
    if (error) {
      console.log('failed to load the sound', error);
      return;
    }
    // loaded successfully
    console.log('duration in seconds: ' + message_received.getDuration() + 'number of channels: ' + message_received.getNumberOfChannels());
});

Code for playing sound file: message_received.play()

paulmelnikow commented 5 years ago

Hmm, try removing Sound.MAIN_BUNDLE?

rgouzal commented 5 years ago

I think require is not supported in iOS not sure why, but I end up adding the sound files in the project and use the following as a workaround:

var android_pageturn = "../../res/audio/Page_Turn.mp3";
var ios_pageturn = "Page_Turn.mp3"

if(Platform.OS == "android") {
        message_received = new Sound(require(android_pageturn), Sound.MAIN_BUNDLE, (error) => {
            if (error) {
              console.log('failed to load the sound', error);
              return;
            }
            // loaded successfully
            console.log('duration in seconds: ' + message_received.getDuration() + 'number of channels: ' + message_received.getNumberOfChannels());
        });
    }
    else {
        Sound.setMode("Default")
        Sound.setCategory("Playback")
        message_received = new Sound(ios_pageturn, Sound.MAIN_BUNDLE, async (e) => {
            if(e) {
                console.log(e)
            }
        })
    }

    message_received.play()
rgouzal commented 5 years ago

@paulmelnikow do you mean when using require I should remove Sound.MAIN_BUNDLE?

paulmelnikow commented 5 years ago

If require(...) does not return a string you should exclude Sound.MAIN_BUNDLE.

It probably depends on your tooling, however that is what’s working for me.

rgouzal commented 5 years ago

@paulmelnikow I tried that and it did not work.

message_received = new Sound(require("../../res/audio/Page_Turn.mp3"),  (e) => {
            if(e) {
                console.log(e)
            }
 })
paulmelnikow commented 5 years ago

What is the error? Also, if you assign require("../../res/audio/Page_Turn.mp3") to a variable, what is it?

YisusMB commented 5 years ago

Any solution? actually this is my code and dosnt works :(

const play = (error, sound) => sound.play()

const Sounds = new Sound(
  require('../../assets/sounds/Beep_Short_05_Sound_Effect_Mp3_261.mp3'),
  (error) => play(error, Sounds),
)
paulmelnikow commented 5 years ago

@YisusMB Could you please open a new issue and fill out the full template?

YisusMB commented 5 years ago

@0x01Brain thanks a lot, i import my .mp3 file in xcode and try your code and it works ty!

acarkaan commented 1 year ago

you should add '' instead of Sound.MAIN_BUNDLE example usage:

const Sound3 = new Sound(require("path_of_file"), '', (error) => {
  if (error) {
    console.log('failed to load the sound', error);
    return;
  }
  // loaded successfully
  console.log('duration in seconds: ' + message_received.getDuration() + 'number of channels: ' + message_received.getNumberOfChannels());
});

Sound3.play();