Skip to content

How to Make an App: iPhone Lock Screen Image

If your app plays music, you may want to handle the remove audio control events. And you might also want to display applicable info like album art and the track name.

It’s not complicated, you mainly just need to know when to update it and what’s available to update. I use a method called updateNowPlaying.

  1. First make sure you’re dealing w/ iOS 5.
  2. Then create your image and trackname.
  3. Use those two items in an array and a matching array of key values (here’s a list of all the key options).
  4. Create a dictionary of the objects and keys.
  5. Set the now playing info (the dictionary from above) in the now playing info center.

 

[sourcecode]
-(void)updateNowPlaying;
{
/* make sure the have iOS 5 by checking for the applicable class. */
// Step 1: Check for iOS 5
if ([MPNowPlayingInfoCenter class]) 
{
// Step 2: image and track name
UIImage *musicImage = [UIImage imageNamed:@"logo.png"];
MPMediaItemArtwork *albumArt = [[MPMediaItemArtwork alloc]
initWithImage:musicImage];

NSString *trackName = [musicFiles objectAtIndex:curAudioFileIndex];

// Step 3: Create arrays
NSArray *objs = [NSArray arrayWithObjects:
trackName,
albumArt, nil];

NSArray *keys = [NSArray arrayWithObjects:
MPMediaItemPropertyTitle,
MPMediaItemPropertyArtwork, nil];

// Step 4: Create dictionary.
NSDictionary *currentTrackInfo = [NSDictionary dictionaryWithObjects:objs forKeys:keys];

// Step 5: Set now playing info
[MPNowPlayingInfoCenter defaultCenter].nowPlayingInfo = currentTrackInfo;
}
}
[/sourcecode]

11 thoughts on “How to Make an App: iPhone Lock Screen Image”

  1. looking for a way to use a remote control with a music player app and I want the pause button to do a fade-out?

      1. Nope that is something completely different but thank you. I am wanting to use the play/pause to press play to start the music and press pause to fade out the music. My problem is I can listen for the pause and then I have to un-pause before sending the fade method. This creates a small but noticeable hiccup. I am looking for a better way.

          1. Well I think it would help to override play/pause but this code is similar to what I am using and it lets you know when the pause button has been pushed but by then the music has paused. I have to un-pause and then fade causing a hiccup. I would have thought it was impossible as I looked everywhere but I did find an App that is doing it. Of course he does not want to reveal how 🙂

            1. My understanding is that in the remoteControlReceivedWithEvent: method you are told what the user tapped (eg., play/pause) and then you programmatically start/stop/pause the music. Given that, the music sdn’t already be paused???

              Apple’s example seems to imply this too given their playOrStop call for that event:
              https://developer.apple.com/library/ios/#documentation/EventHandling/Conceptual/EventHandlingiPhoneOS/RemoteControl/RemoteControl.html

              So if you fade out the music over X seconds and then have a timer that pauses the music after X seconds it seems like it wd work???

              1. Yes the music is paused and I can receive that event. The problem is I don’t want it to pause, I want to fade out the track. So far to do this I have to un-pause the track and then call the fade method which causes an audible hiccup.

                I have a fade method that will fade out over x seconds. I am looking for a smooth fade out.

                Thanks again for trying!

                1. I just opened a project using the remove controls method. Here’s the top of it (below). I commented out the contents of the case for UIEventSubtypeRemoteControlTogglePlayPause – w/o that if/else, when I tapped the play/pause buttons on the lock screen, the music did not stop. Then I changed it to set the volume instead and that worked.

                  So I think you could put in the fade code/call into that case w/ an actual ‘pause’ call after the fade.

                  – (void)remoteControlReceivedWithEvent:(UIEvent *)event
                  {
                  switch(event.subtype) {
                  case UIEventSubtypeRemoteControlTogglePlayPause:
                  if([UtilAudio isPlaying])
                  [UtilAudio pause];
                  else
                  [UtilAudio continuePlaying];
                  break;

                  1. Are you testing with an actual remote control and dock?
                    The UIEvent I had tried but does not work for me so I use the method from the Apple Music App sample. You will see that when pause is received, I then re-start play and then fade. If I comment out the pause, then the remote still sends a pause and I lose control and cannot fade.

                    – (void) registerMediaPlayerNotifications{
                    NSNotificationCenter *notificationCenter = [NSNotificationCenter defaultCenter];

                    [notificationCenter addObserver: self
                    selector: @selector (handle_NowPlayingItemChanged:)
                    name: MPMusicPlayerControllerNowPlayingItemDidChangeNotification
                    object: musicPlayer];

                    [notificationCenter addObserver: self
                    selector: @selector (handle_PlaybackStateChanged:)
                    name: MPMusicPlayerControllerPlaybackStateDidChangeNotification
                    object: musicPlayer];

                    [notificationCenter addObserver: self
                    selector: @selector (handle_VolumeChanged:)
                    name: MPMusicPlayerControllerVolumeDidChangeNotification
                    object: musicPlayer];

                    [musicPlayer beginGeneratingPlaybackNotifications];
                    }

                    – (void) handle_PlaybackStateChanged: (id) notification {

                    MPMusicPlaybackState playbackState = [musicPlayer playbackState];

                    if (playbackState == MPMusicPlaybackStateSeekingForward){
                    //Stops additional movement of the playback point, returning the playback state to what it was prior to seeking.
                    [self endSeeking];
                    return;
                    }

                    if (playbackState == MPMusicPlaybackStateSeekingBackward){
                    [self performSelector:@selector(playPrevious) withObject:nil afterDelay:0.0];
                    }

                    if (playbackState == MPMusicPlaybackStatePaused) {

                    [playPauseButton setImage:[UIImage imageNamed:@”BlackPlayButton.png”] forState:UIControlStateNormal];
                    [musicPlayer play];
                    [self pauseFadeMethod];
                    }
                    else
                    {
                    [musicPlayer pause];
                    [playPauseButton setImage:[UIImage imageNamed:@”BlackPlayButton.png”] forState:UIControlStateNormal];
                    return;
                    }
                    }
                    [playPauseButton setImage:[UIImage imageNamed:@”BlackPlayButton.png”] forState:UIControlStateNormal];
                    }

                    if (playbackState == MPMusicPlaybackStatePlaying) {
                    [self performSelector:@selector(playPlaying) withObject:nil afterDelay:0.0];
                    }

                    if (playbackState == MPMusicPlaybackStateStopped) {
                    [playPauseButton setImage:[UIImage imageNamed:@”BlackPlayButton.png”] forState:UIControlStateNormal];
                    }
                    }

                      1. I had tried beginReceivingRemoteControlEvents and it did nothing so maybe it doesn’t work with a dock and remote. Not sure why it is called ReceivingRemoteControlEvents because nothing was received unless I did something wrong, I did follow the documentation, at least I thought I did, and tried if a few different times but it never worked for me.

              Comments are closed.