How to stream mp3 files (iOS) - ios

I have found many related questions on SO, but or because I am very new, or because it doesn't exactly fit my problem, I can't find a way to succeed.
So, all I would like to do is playing an audio file stored on an exernal server directly on the iOS device (iPhone in my case)
I have tried differents solution on the net, and this is what I get until now.
NSString* resourcePath = #"http://www.chiptape.com/chiptape/sounds/medium/laugh.mp3"; //your url
NSURL *url = [[NSURL alloc]initWithString:resourcePath];
NSError *error;
audioPlayer = [[AVAudioPlayer alloc] initWithURL:url error:&error];
audioPlayer.delegate = self;
[url release];
[audioPlayer prepareToPlay];
[audioPlayer play];
The compiler show me this error:
No visible #interface for 'AVAudioPlayer' declares the selector
'initWithURL:error:'
I am not sure at all about my code, and would like your guys to know I have started iOS coding yesterday, so it's not impossible I'm missing something so obvious that tutorials/posts don't mention it.
Also, I have imported the library AVFoundation and imported it on my .h file.
I have also declared this on my .h file
AVAudioPlayer *audioPlayer;
I hope there is an easy way to stream audio file on iOS as provide android/java
Thank you and if you need more details comment and I'll update my post.

Try this:
NSString* resourcePath = #"http://www.chiptape.com/chiptape/sounds/medium/laugh.mp3"; //your url
NSURL *audioURL = [NSURL URLWithString:resourcePath];
AVAudioPlayer *audioPlayer = [[[AVAudioPlayer alloc] initWithContentsOfURL: audioURL error:&error]autorelease];
[audioPlayer play];

I'm working with it recently.
AVAudioPlayer can't work with audio stream. In fact, there isn't an easy way to do that.
You need to learn some Core Audio things, get the raw data of media, play them in audioQueue (audioToolBox framework). Real-time audio processing is not a simple work, it's full of c-level api and so many dirty work, don't rush, have fun :)
Check out the book Learning Core Audio and this open-source audio streamer.
Let me know if you need more help.

Related

Playing several tracks saved locally in sequence

I need to play n tracks one after another with ability to switch to next/previous song and pause. Songs are located in Documents folder.
I looked in AVQueuePlayer, but it seems that this approach is not working with local files, playing by url works fine. Now i can play one song with AVAudioPlayer like this:
NSURL *url = [NSURL fileURLWithPath:[node path]];
self.player = [[AVAudioPlayer alloc] initWithContentsOfURL:url error:nil];
[self.player play];
But it seems that playing bunch of tracks one after another this way is not the best practice.
May be there are frameworks that implement this in more convenient way?
Any suggestions?
StreamingKit is probably what your looking for.

How to play an array of songs using streamingkit library

Has anyone out there ever used this https://github.com/tumtumtum/StreamingKit/ package to play remote mp3 files? How can one load an array of music urls and play them one after the other?
Just as document says:
STKAudioPlayer* audioPlayer = [[STKAudioPlayer alloc] init];
[audioPlayer queue:#"http://www.abstractpath.com/files/audiosamples/sample.mp3"];
[audioPlayer queue:#"http://www.abstractpath.com/files/audiosamples/airplane.aac"];
You just need to add url to queue.

AVAudioPlayer will not play audio in one project with all correct parameters, but will work fine in another project

I have a huge Xcode project, which I have been working on an update to. After installing the iOS 7.1 SDK, playing audio on the AVAudioPlayer in this project no longer works. I created a new, blank project to test out the exact same code, and it worked perfectly.
I know for certain that the file is copied under the bundle resources, the file is added to the target, the URL is perfect because I was able to get the NSData from the NSURL of the file, and it matched. The AVAudioPlayer is a property with both the strong and nonatomic attributes, but it will not play in this one project. I also made sure to set the AVAudioSession to playback mode.
I even created some blank view controller classes to test out the AVAudioPlayer in the project, and it would not work in any of them, but in the new, blank iOS project I made, the sounds plays fine.
In the .h
NSURL *soundUrl;
#property (nonatomic, strong) AVAudioPlayer *soundPlayer;
In the .m
#synthesize soundPlayer = _soundPlayer;
- (void)playSomeSound {
NSError *audioError;
soundUrl = [[NSURL alloc] initFileURLWithPath:[[NSBundle mainBundle] pathForResource:soundFile ofType:#"m4a"]];
_soundPlayer = [[AVAudioPlayer alloc] initWithContentsOfURL:soundUrl error:&audioError];
[[AVAudioSession sharedInstance] setCategory:AVAudioSessionCategoryPlayback error:NULL];
_soundPlayer.delegate = self;
[_soundPlayer play];
}
soundFile is just a string of the name of the sound file that I am trying to play.
I try to log for errors in all the delegate methods of the audio player and in the initialization of the audio player. All errors return (null).
Unlike on iOS 7, where the audio simply does not play, on iOS 6.1, initializing the audio player causes a crash with an EXC_BAD_ACCESS code 2.
Also, the AVAudioPlayer in CocosDenshion seems to work. (I have cocos2d used in parts of my project, but it is not a game.)
Another (possibly important) note is that I use AVAudioRecorder in my project as well. That works perfectly without any issues, and I make sure to switch the AVAudioSessionCategory to playback when I am not recording.
Its due to the change that apple made to AVAudioSession properties in iOS 7.
As per Apple's documentation:
The audio category has changed (e.g. AVAudioSessionCategoryPlayback
has been changed to AVAudioSessionCategoryPlayAndRecord).
So change the line [[AVAudioSession sharedInstance] setCategory:AVAudioSessionCategoryPlayback error:NULL]; to
[[AVAudioSession sharedInstance] setCategory:AVAudioSessionCategoryPlayAndRecord error:NULL];
Considering the fact that exactly the same code works in your other project, it's hard to tell what is the problem in this project. But I can give you a couple of suggestions on further debugging it:
Call your -playSomeSound as the first thing you do in application:didFinishLaunchingWithOptions:. This way you will see whether it's not working because of something else you do before calling it.
Add another sound to your project, and try playing that one. Perhaps still the problem is with the original sound.
Also a couple questions:
Where is audioError declared?
What's the result of [_soundPlayer play] (should return YES on
success)?
hava a try:
[_soundPlayer prepareToPlay];
[_soundPlayer play];
Thanks everyone, but somehow it ended up being a conflict between some Frameworks. There was a bug in Kamcord SDK for iOS, but I am in contact with their development team, and they are working to fix it.
This issue is still apparent in the latest Kamcord SDK, so instead of everyone running in to this issue having to contact them, here's the smallest amount of code/changes you need to fix AVAudioPlayer, and to have Kamcord also include audio from AVAudioPlayer in it's recordings.
First, add OpenAL to your frameworks.
Import OpenAL headers in AppDelegate.m
#import <OpenAl/al.h>
#import <OpenAl/alc.h>
Set up static variables for OpenAL device and context:
static ALCdevice *openALDevice;
static ALCcontext *openALContext;
Create two functions to start and to stop OpenAL
- (void)startOpenAL
{
NSLog(#"OpenAL: Starting");
openALDevice = alcOpenDevice(NULL);
openALContext = alcCreateContext(openALDevice, NULL);
alcMakeContextCurrent(openALContext);
}
- (void)stopOpenAL
{
NSLog(#"OpenAL: Stopping");
alcMakeContextCurrent(NULL);
alcDestroyContext(openALContext);
alcCloseDevice(openALDevice);
}
In AppDelegate.m's didFinishLaunchingWithOptions, start OpenAL (I do it before initializing Kamcord)
[self startOpenAL];
Finally, in applicationWillTerminate, call the stop OpenAL
[self stopOpenAL];
You're done. AVAudioPlayer should now start working again and all of your audio is correctly being recorded by Kamcord.

AVAudioPlayer not working with .pls shoutcast file?

Good Day,
I am working on one Radio APP that gets shoutcast streaming .pls file and plays it with help of AVFoundation framework.
This job is easily done with AVPlayer, but the problem with it is that I can not code or find any good solution to get it working with volume slider, the AVPlayer class does not have volume property.
So now I am trying to get it working with AVAudioPlayer which has volume property, and here is my code:
NSString *resourcePatch = #"http://vibesradio.org:8002/listen.pls";
NSData *_objectData = [NSData dataWithContentsOfURL:[NSURL URLWithString:resourcePatch]];
NSError *error;
vPlayer = [[AVAudioPlayer alloc] initWithData:_objectData error:&error];
vPlayer.numberOfLoops = 0;
vPlayer.volume = 1.0f;
if (vPlayer == nil)
NSLog(#"%#", [error description]);
else
[vPlayer play];
This code is working with uploaded .mp3 files on my server but it is not working with .pls files generated by shoutcast,
Is there any way to fix AVAudioPlayer to work with .pls files, or implement volume slider to AVPlayer ?
Using AVAudioPlayer for stream from network is not a good idea. See what Apple's documentation say on AVAudioPlayer:
An instance of the AVAudioPlayer class, called an audio player,
provides playback of audio data from a file or memory.
Apple recommends that you use this class for audio playback unless you
are playing audio captured from a network stream or require very low
I/O latency.
For change AVPlayer's volume check this question:Adjusting the volume of a playing AVPlayer

iPhone SDK: Play a single WAV from a button

I am currently trying out this code:
NSString *path = [[NSBundle mainBundle] pathForResource:#"dream" ofType:#"m4a"];
AVAudioPlayer* theAudio=[[AVAudioPlayer alloc] initWithContentsOfURL:[NSURL fileURLWithPath:path] error:NULL];
theAudio.delegate = self;
[theAudio play];
However, the SDK says that the ViewController does not implement the AVAudioPlayer Delegate.
Any body any ideas on how to play a WAV (or M4a) using the 2.2 SDK?
You need to add <AVAudioPlayerDelegate> to the end of your controller's class declaration, along these lines:
#interface MyViewController : UIViewController <AVAudioPlayerDelegate>
This'll probably generate some more warnings about delegate methods you need to implement - follow those and you'll be good to go.
Interesting. Try NSURL -URLWithString: - that's what I use in combination with the bundle method you're using. I don't see anything that could be causing a problem other than that. You're testing it on the device, right?
The answer I posted here should definitely help you. Just use audioservices for small wave sounds, unless you need concurrency, it's faster.
iPhoneToot.com has its own itootSound class and a VIDEO to show you how to play a wav file in 2 lines of code. Check them out at iPhoneToot.com. it will save you hours if not days of time!!

Resources