I am developing a ebook reader. There are some audio files which needs to be played upon clicking on a icon. The audio just plays fine for the first time. But when I press the home button of the app and return into the audio player, the audio is being played twice. The number keeps increasing by 1 every time I press the home button and come back to the audio player. Using debugger I found that this loop is running multiple times. Can anyone explain why is it behaving like that?
-(void)StartPlayingFileWithNotification:(NSNotification *)notifcation{
// Load the array with the sample file
NSString *f = [[notifcation userInfo] valueForKey:#"audiopath"];
NSURL *fileURL = [[NSURL alloc] initFileURLWithPath: f];
if(fileURL == nil){
GLogError(#"%#",#"File Not Found");
return;
}else {
GLogInfo(#"%#",#"Got audio file");
}
if (self.player != nil) {
if (self.player.playing) {
[self.player stop];
}
[player release];
player = nil;
}
self.player = [[AVAudioPlayer alloc] initWithContentsOfURL:fileURL error:nil];
if (self.player)
{
fileName.text = [NSString stringWithFormat: #"%# (%d ch.)", [[player.url relativePath] lastPathComponent], player.numberOfChannels, nil];
NSLog(#"The audio file is %#",fileName.text);
NSLog(#"The file URL is %#",[fileURL description]);
[self updateViewForPlayerInfo:player];
player.numberOfLoops = 0;
player.delegate = self;
[player play];
[self updateViewForPlayerState:player];
}
[fileURL release];
}
Check your #synthesize, member var and #property declarations. Don't you have a typing mistake ? Use self.player everywhere, or just player, but try avoiding mixing both.
Related
I'm trying to download a mp4 file from a server, then save it in a file. After it is saved in the file, I try to play it. When the program runs, it pauses when the file is being download, then the screen turns black when I create the MPMoviePlayerController object.
I did the following.
1. Traced through the code and view the NSDAta object to make sure the right anount of data was being load.
2. added a if ( [mFile fileExistsAtPath:filename]==true ) to make sure the file exist.
3. checked all the return values for a nil.
I'm left out of idears now!
// set up file name to save it under and play it
NSFileManager *mFile= [NSFileManager defaultManager];
NSString *filename=[ NSHomeDirectory() stringByAppendingPathComponent:#"ted10.dat"];
// load video
NSURL *movieUrl=[[NSURL alloc] initWithString:#"http://www.besttechsolutions.biz/projects/golfflix/ted.mp4"];
NSData *data = [NSData dataWithContentsOfURL:movieUrl];
[data writeToURL:movieUrl atomically:YES];
[mFile createFileAtPath:filename contents: data attributes:nil];
// makse sure file exist
if ( [mFile fileExistsAtPath:filename]==true )
{
// play it
NSURL *fileUrl=[ NSURL fileURLWithPath:filename];
mp=[[MPMoviePlayerController alloc] initWithContentURL: fileUrl];
[mp.view setFrame: self.view.bounds];
[self.view addSubview: mp.view];
if ([mp respondsToSelector:#selector(loadState)])
{
// Set movie player layout
[mp setControlStyle:MPMovieControlStyleFullscreen];
[mp setFullscreen:YES];
// May help to reduce latency
[mp prepareToPlay];
// Register that the load state changed (movie is ready)
}//localhost/Dino/golflix2/Classes/videolist.h
else
{
}
[mp play];
}
Here's your fixed code:
- (IBAction) doMovie: (id) sender
{
// set up file name to save it under and play it
NSFileManager *mFile= [NSFileManager defaultManager];
NSString *filename=[ NSHomeDirectory() stringByAppendingPathComponent:#"ted10.mp4"];
// load video
NSURL *movieUrl=[[NSURL alloc] initWithString:#"http://www.besttechsolutions.biz/projects/golfflix/ted.mp4"];
NSError *error = NULL;
NSData *data = [NSData dataWithContentsOfURL:movieUrl];
if( [data writeToFile:filename options: NSDataWritingAtomic error: &error] != YES)
{
NSLog( #"error writing data to file %#", filename );
} else {
// make sure file exist
if ( [mFile fileExistsAtPath:filename]==true )
{
// play it
NSURL *fileUrl=[ NSURL fileURLWithPath:filename];
MPMoviePlayerController * mp=[[MPMoviePlayerController alloc] initWithContentURL: fileUrl];
[mp.view setFrame: self.view.bounds];
[self.view addSubview: mp.view];
// Set movie player layout
[mp setControlStyle:MPMovieControlStyleFullscreen];
[mp setFullscreen:YES];
// May help to reduce latency
[mp prepareToPlay];
[mp play];
}
}
}
1)
Most importantly, you were originally trying to write your movie back to the remote URL. I think what you really wanted to do was write to a local file (or cache).
2)
The file extension (.mp4) gives a hint to the movie player what kind of file is playing. ".dat" is too generic.
3)
Speaking of writing to the local file, don't put it in the home directory. Find the cache directory or somewhere else that's more appropriate.
I am new in Iphone SDK programming
I need to create audio player but without array. Melodies have names "sound1, sound2, sound3..."
My code here:
NSUInteger x;
for (x=1; x<=tuneNums; x++)
{
path = [[NSBundle mainBundle] pathForResource:#"sound%d" ofType:#"wav"];
if([[NSFileManager defaultManager] fileExistsAtPath:path])
{
aSound = [[AVAudioPlayer alloc] initWithContentsOfURL:[NSURL fileURLWithPath:path] error:&error];
[aSound setNumberOfLoops:0];
aSound.delegate = self;
[aSound prepareToPlay];
}
}
All button I have and work great, but only with one mellody:( But how release 4-5 melodies i dont know :(
P.S. Forgive me for my english I'm just out of Siberia
You are allocating an AVAudioPlayer on each cycle, and you get only one 'melody' because that's the one allocated in the last cycle.
As 7KV7 pointed out, you should allocate one AVAudioPlayer when the user presses a button, play the corresponding audio file, and then release/recreate it when another button is pressed.
Something like:
- (void)button1Pressed:(id)sender {
// release the current player
if(aSound) {
[aSound release], aSound = nil;
}
// create a new player with the first file
aSound = [[AVAudioPlayer alloc] initWithContentsOfURL:[NSURL fileURLWithPath:path] error:&error];
[aSound setNumberOfLoops:0];
aSound.delegate = self;
[aSound prepareToPlay];
}
How to determine which audio file to play when a button is pressed is up to you. If you are going to have only four audio files, the simplest way is to have a fixed number of buttonPressed selectors (e.g. button1Pressed, button2Pressed) and associate them to your four buttons.
if i got you right you should add the method-
- (void)audioPlayerDidFinishPlaying:(AVAudioPlayer *)player successfully:(BOOL)flag{
[player release];
}
and don't forget to set your view controller as the player delegate.
aSound.delegate=self;
What is the simplest way to play a looping sound in an iPhone app?
Probably the easiest solution would be to use an AVAudioPlayer with the numberOfLoops: set to a negative integer.
// *** In your interface... ***
#import <AVFoundation/AVFoundation.h>
...
AVAudioPlayer *testAudioPlayer;
// *** Implementation... ***
// Load the audio data
NSString *soundFilePath = [[NSBundle mainBundle] pathForResource:#"sample_name" ofType:#"wav"];
NSData *sampleData = [[NSData alloc] initWithContentsOfFile:soundFilePath];
NSError *audioError = nil;
// Set up the audio player
testAudioPlayer = [[AVAudioPlayer alloc] initWithData:sampleData error:&audioError];
[sampleData release];
if(audioError != nil) {
NSLog(#"An audio error occurred: \"%#\"", audioError);
}
else {
[testAudioPlayer setNumberOfLoops: -1];
[testAudioPlayer play];
}
// *** In your dealloc... ***
[testAudioPlayer release];
You should also remember to set the appropriate audio category. (See the AVAudioSession setCategory:error: method.)
Finally, you'll need to add the AVFoundation library to your project. To do this, alt click on your project's target in the Groups & Files column in Xcode, and select "Get Info". Then select the General tab, click the + in the bottom "Linked Libraries" pane and select "AVFoundation.framework".
The easiest way would be to use an AVAudioPlayer set to an infinite number of loops (or finite if that's what you need).
Something like:
NSString *path = [[NSBundle mainBundle] pathForResource:#"yourAudioFileName" ofType:#"mp3"];
NSURL *file = [[NSURL alloc] initFileURLWithPath:path];
AVAudioPlayer *_player = [[AVAudioPlayer alloc] initWithContentsOfURL:file error:nil];
[file release];
_player.numberOfLoops = -1;
[_player prepareToPlay];
[_player play];
This will simply loop whatever audio file you have specified indefinitely.
Set the number of loops to any positive integer if you have a finite number of times you want the audio file to loop.
Hope this helps.
Cheers.
HI guys, i am developing a ebook reader. There are some audio files which needs to be played upon clicking on a icon. The audio just plays fine for the first time.. But, when i press the home button of the app and return into the audio player, the audio is being played twice... The number keeps increasing by 1 every time i press the home button and come back to the audio player.... Please help me with ur inputs.... by debugging i found that this loop is running multiple times... Can anyone tell me the reason for it??
-(void)StartPlayingFileWithNotification:(NSNotification *)notifcation{
// Load the array with the sample file
NSString *f = [[notifcation userInfo] valueForKey:#"audiopath"];
NSURL *fileURL = [[NSURL alloc] initFileURLWithPath: f];
if(fileURL == nil){
GLogError(#"%#",#"File Not Found");
return;
}else {
GLogInfo(#"%#",#"Got audio file");
}
if (self.player != nil) {
if (self.player.playing) {
[self.player stop];
}
[player release];
player = nil;
}
self.player = [[AVAudioPlayer alloc] initWithContentsOfURL:fileURL error:nil];
if (self.player)
{
fileName.text = [NSString stringWithFormat: #"%# (%d ch.)", [[player.url relativePath] lastPathComponent], player.numberOfChannels, nil];
[self updateViewForPlayerInfo:player];
player.numberOfLoops = 0;
player.delegate = self;
[player play];
[self updateViewForPlayerState:player];
}
[fileURL release];
}
Sounds like you are creating new views (or other objects) containing your audio player without checking to see if the previous one is still around and running. You could either check on activate before creating another one, or clean up the old one when the app resigns active.
Hey guys how can I make an app keep playing an mp3 after pressed the hold/power button.
Here is the code I use for preparing the AVAudioPlayer:
- (void)PrepareAudio:(int)index
{
NSString *soundFilePath = [[NSBundle mainBundle] pathForResource:[NSString stringWithFormat:#"%#",[_Audio objectAtIndex:Game]] ofType:#"mp3"];
NSURL *newURL = [[NSURL alloc] initFileURLWithPath: soundFilePath];
MusicPlayer = [[AVAudioPlayer alloc] initWithContentsOfURL: newURL error: nil];
[newURL release];
[MusicPlayer setVolume: 1.5];
}
And this is the code when I press the button play:
- (IBAction)PushPlay: (id)sender
{
if(!MusicPlayer.playing)
[MusicPlayer play];
}
Best Regards
Carlos Vargas
If you are holding long enough to turn the device off, then there is no way. If you are pressing the button to lock the screen, the music can be played. Why don't you put some code up and let us see what you have tried. Hint: The answer lies within the Audio playback categories.