title: Playing audio with controls in iOS
body: <p>I've made an app with <code>tab bar,nav bar and table view</code>. </p>
  
  <p>In the table view you can choose to listen to some audio.</p>
  
  <p>New view opens and there I have some controls like: play,pause,volume slider, progress slider, label with the current time. </p>
  
  <p>It works, but not perfect. 
  I can play the audio, I can pause the audio, I can also use the slider to skip forward or back. But now:</p>
  
  <p><strong>When I hit the Back button on the navbar, the song keeps playing. That's ok, but when I go back to the view again, the timer and the slider reset themselves. I can't pause the song, just need to wait util it stops playing.</strong></p>
  
  <p>Also, when I hit play, go back to the table view, choose another file to play, the first <strong>file won't stop playing</strong>.</p>
  
  <p>Here is the Audio1DetailViewController.h code:</p>
  
  <pre><code>     #import &lt;UIKit/UIKit.h&gt;
       #import &lt;AVFoundation/AVFoundation.h&gt;
  
       @interface Audio1DetailViewController: UIViewController &lt;AVAudioPlayerDelegate&gt; {
  
       IBOutlet UISlider *volumeControl; 
       IBOutlet UILabel  *timerLabel; 
       IBOutlet UISlider *progressBar; 
  
       AVAudioPlayer *audioPlayer;
       NSTimer *playbackTimer; 
  
       }
  
       @property (nonatomic, retain) IBOutlet UISlider *volumeControl;
       @property (nonatomic, retain) IBOutlet UILabel *timerLabel;
       @property (nonatomic, retain) IBOutlet UISlider *progressBar;
       @property (nonatomic, retain) NSTimer  *playbackTimer; 
       @property (nonatomic, retain) AVAudioPlayer *audioPlayer;
       -(IBAction) playAudio;
       -(IBAction) stopAudio;
       -(IBAction) adjustVolume;
       -(IBAction) sliderChanged;
  
       @end
  </code></pre>
  
  <p>Here is the Audio1DetailViewController.m code:</p>
  
  <pre><code>     #import "Audio1DetailViewController.h"
  
  
       @implementation Audio1DetailViewController
  
       @synthesize volumeControl, timerLabel, playbackTimer, progressBar, audioPlayer;
  
       -(void)playAudio
       {
       playbackTimer = [NSTimer scheduledTimerWithTimeInterval:1.0
       target:self
       selector:@selector(updateTime)
       userInfo:nil
       repeats:YES];
       [audioPlayer play];
       }
       -(void)stopAudio
       {
       [playbackTimer invalidate];
       [audioPlayer stop];
       }
       -(void)adjustVolume
       {
       if (audioPlayer != nil)
       {
       audioPlayer.volume = volumeControl.value;
       }
       }
  
       -(void)updateTime
       {
       float minutes = floor(audioPlayer.currentTime/60);
       float seconds = audioPlayer.currentTime - (minutes * 60);
  
       float duration_minutes = floor(audioPlayer.duration/60);
       float duration_seconds = 
       audioPlayer.duration - (duration_minutes * 60);
  
       NSString *timeInfoString = [[NSString alloc] 
       initWithFormat:@"%0.0f.%0.0f / %0.0f.%0.0f",
       minutes, seconds, 
       duration_minutes, duration_seconds];
  
       timerLabel.text = timeInfoString;
       [timeInfoString release];
       }
  
       - (void)viewDidLoad {
       [super viewDidLoad];
       NSURL *url = [NSURL fileURLWithPath:[[NSBundle mainBundle]
       pathForResource:@"001Fatiha"
       ofType:@"MP3"]];
  
       NSError *error;
       audioPlayer = [[AVAudioPlayer alloc]
       initWithContentsOfURL:url
       error:&amp;error];
  
       [[AVAudioSession sharedInstance] setCategory:AVAudioSessionCategoryPlayback error:nil];
       [[AVAudioSession sharedInstance] setActive: YES error: nil];
  
       if (error)
       {
       NSLog(@"Error in audioPlayer: %@", 
       [error localizedDescription]);
       } else {
       audioPlayer.delegate = self;
       [audioPlayer prepareToPlay];
       }
  
  
       playbackTimer = [NSTimer scheduledTimerWithTimeInterval:1 target:self
       selector:@selector(updateSlider) userInfo:nil repeats:YES];
  
       progressBar.maximumValue = audioPlayer.duration;
       // Set the valueChanged target
       [progressBar addTarget:self action:@selector(sliderChanged:) forControlEvents:
       UIControl EventValueChanged];
       }
  
       - (void)updateSlider {
       // Update the slider about the music time
       progressBar.value = audioPlayer.currentTime;
       }
  
       - (IBAction)sliderChanged:(UISlider *)sender {
       // Fast skip the music when user scroll the UISlider
       [audioPlayer stop];
       [audioPlayer setCurrentTime:progressBar.value];
       [audioPlayer prepareToPlay];
       [audioPlayer play];
       }
  
       -(void)audioPlayerDidFinishPlaying:
       (AVAudioPlayer *)player successfully:(BOOL)flag
       {
       }
  
  
       -(void)audioPlayerDecodeErrorDidOccur:
       (AVAudioPlayer *)player error:(NSError *)error
       {
       }
       -(void)audioPlayerBeginInterruption:(AVAudioPlayer *)player
       {
       }
       -(void)audioPlayerEndInterruption:(AVAudioPlayer *)player
       {
       }
  
       -(void)viewDidUnload {
       audioPlayer = nil;
       volumeControl = nil;
  
       }
  
       -(void)dealloc {
       [audioPlayer release];
       [volumeControl release];
       [playbackTimer release];
       [super dealloc];
       }
  
       @end
  </code></pre>
  
  <p>Here is the AudioTableViewController.h</p>
  
  <pre><code>     #import &lt;UIKit/UIKit.h&gt;
  
       @class Audio1DetailViewController;
  
  
       @interface AudioTableViewController : UITableViewController 
       &lt;UITableViewDelegate,UITableViewDataSource&gt;{
  
  
       IBOutlet UITableView *audioTableView;
       NSMutableArray *audioArray;
       Audio1DetailViewController *audio1DetailViewController;        
       }
  
       @property (nonatomic, retain) NSMutableArray *audioArray;
       @property (nonatomic, retain) Audio1DetailViewController *audio1DetailViewController;
  
       @end
  </code></pre>
  
  <p>And the AudioTableViewController.m</p>
  
  <pre><code>    #import "AudioTableViewController.h"
      #import "Audio1DetailViewController.h"
  
      #import "DEQAppDelegate.h"
  
      @implementation AudioTableViewController
      @synthesize audioArray;
      @synthesize audio1DetailViewController;
  
      - (id)initWithStyle:(UITableViewStyle)style
      {
          self = [super initWithStyle:style];
          if (self) {
              // Custom initialization
      {
          return self;
      }
  
      - (void)didReceiveMemoryWarning
      {
          // Releases the view if it doesn't have a superview.
          [super didReceiveMemoryWarning];
  
          // Release any cached data, images, etc that aren't in use.
      }
  
      #pragma mark - View lifecycle
  
      - (void)viewDidLoad{
          [super viewDidLoad];
          self.title = NSLocalizedString(@"Audio", @"Audio");
          self.audioArray = [[NSArray alloc] initWithObjects:
                            @"1. Het Begin",  @"2. De Mensen", //etcetera                      
                    nil];
          // Uncomment the following line to preserve selection between presentations.
          self.clearsSelectionOnViewWillAppear = NO;
  
          // Uncomment the following line to display an Edit button in the navigation bar for this
          view controller.
          // self.navigationItem.rightBarButtonItem = self.editButtonItem;
      }
  
      - (void)viewDidUnload
      {
          [super viewDidUnload];
          // Release any retained subviews of the main view.
          self.audioArray = nil;
      }
  
      - (void)viewWillAppear:(BOOL)animated
      {
          [super viewWillAppear:animated];
      }
  
      - (void)viewDidAppear:(BOOL)animated
      {
          [super viewDidAppear:animated];
      }
  
      - (void)viewWillDisappear:(BOOL)animated
      {
          [super viewWillDisappear:animated];
      }
  
      - (void)viewDidDisappear:(BOOL)animated
      {
          [super viewDidDisappear:animated];
      }
  
      - (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
      {
          // Return YES for supported orientations
          return (interfaceOrientation == UIInterfaceOrientationPortrait);
      }
  
      #pragma mark - Table view data source
  
      - (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
      {
      #warning Potentially incomplete method implementation.
          // Return the number of sections.
          return 1;
      }
  
      - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
      {
      #warning Incomplete method implementation.
          // Return the number of rows in the section.
          return [self.audioArray count];
      }
  
      - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:
        (NSIndexPath *)indexPath
      {
          static NSString *CellIdentifier = @"Cell";
  
          UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
          if (cell == nil) {
              cell = [[[UITableViewCell alloc] initWithStyle:
          UITableViewCellStyleDefaultreuseIdentifier:CellIdentifier] autorelease];
          }
  
          // Configure the cell...
          cell.textLabel.text = [self.audioArray objectAtIndex:[indexPath row]];
  
          return cell;
      }
  
      #pragma mark - Table view delegate
  
      - (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
      {
          // Navigation logic may go here. Create and push another view controller.
  
          NSUInteger row = indexPath.row;
  
          if (row == 0) 
          {
       Audio1DetailViewController *audio1DetailViewController =[[Audio1DetailViewController alloc]
       initWithNibName:@"Audio1DetailViewController" bundle:nil]; 
       audio1DetailViewController.title = @"Audio";
       [self.navigationController pushViewController:audio1DetailViewController animated:YES];   
       [audio1DetailViewController release];
  
          }
  
          if (row == 1) 
          {
              //etcetera
          }
  
      }
      - (void)dealloc{
          [audioArray release];
          [super dealloc];
      }
  
      @end
  </code></pre>