Skip to content

Commit 2b79d7e

Browse files
author
Diogo Simao Marques
committed
VLCNowPlayingTemplateObserver: Display the queue instead of skipping to the next media
The button at the top-right hand corner now displays the medias next in queue instead of skipping to the next media at it is described in the documentation. The play queue is also updated according to the shuffle state.
1 parent 4ba4c5f commit 2b79d7e

File tree

4 files changed

+69
-6
lines changed

4 files changed

+69
-6
lines changed

Resources/en.lproj/Localizable.strings

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -596,6 +596,7 @@
596596
"PLAY_NEXT_IN_QUEUE_LABEL" = "Play next in queue";
597597
"APPEND_TO_QUEUE_HINT" = "Append to queue";
598598
"APPEND_TO_QUEUE_LABEL" = "Append to queue";
599+
"QUEUE_LABEL" = "Queue";
599600

600601
"DISPLAY_AS" = "Display as";
601602

Sources/CarPlay/VLCCarPlaySceneDelegate.m

Lines changed: 60 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,13 +25,16 @@
2525
#pragma clang diagnostic push
2626
#pragma clang diagnostic ignored "-Wpartial-availability"
2727

28-
@interface VLCCarPlaySceneDelegate() <CPTemplateApplicationSceneDelegate, CPMediaLibraryObserverDelegate>
28+
@interface VLCCarPlaySceneDelegate() <CPTemplateApplicationSceneDelegate, CPMediaLibraryObserverDelegate, CPListTemplateDelegate>
2929
{
3030
CPInterfaceController *_interfaceController;
3131
CarPlayMediaLibraryObserver *_mediaLibraryObserver;
3232
VLCNowPlayingTemplateObserver *_nowPlayingTemplateObserver;
3333
VLCCarPlayArtistsController *_artistsController;
3434
VLCCarPlayPlaylistsController *_playlistsController;
35+
CPListTemplate *_playQueueTemplate;
36+
CPListSection *_section;
37+
VLCPlaybackService *_playbackService;
3538
}
3639

3740
@end
@@ -51,6 +54,11 @@ - (void)templateApplicationScene:(CPTemplateApplicationScene *)templateApplicati
5154
_nowPlayingTemplateObserver = [VLCNowPlayingTemplateObserver new];
5255
[[CPNowPlayingTemplate sharedTemplate] addObserver:_nowPlayingTemplateObserver];
5356
[_nowPlayingTemplateObserver configureNowPlayingTemplate];
57+
58+
_playbackService = [VLCPlaybackService sharedInstance];
59+
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(displayPlayQueueTemplate) name:VLCDisplayPlayQueueCarPlay object:nil];
60+
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(resetPlayQueueTemplate) name:VLCPlaybackServicePlaybackDidStop object:nil];
61+
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(resetPlayQueueTemplate) name:VLCPlaybackServiceShuffleModeUpdated object:nil];
5462
}
5563

5664
- (void)templateApplicationScene:(CPTemplateApplicationScene *)templateApplicationScene
@@ -61,6 +69,9 @@ - (void)templateApplicationScene:(CPTemplateApplicationScene *)templateApplicati
6169
_mediaLibraryObserver = nil;
6270
[[CPNowPlayingTemplate sharedTemplate] removeObserver:_nowPlayingTemplateObserver];
6371
_nowPlayingTemplateObserver = nil;
72+
_playQueueTemplate = nil;
73+
_section = nil;
74+
_playbackService = nil;
6475
}
6576

6677
- (CPTabBarTemplate *)generateRootTemplate
@@ -87,6 +98,54 @@ - (void)templatesNeedUpdate
8798
[_interfaceController setRootTemplate:[self generateRootTemplate] animated:YES];
8899
}
89100

101+
- (CPListSection *)createListSection
102+
{
103+
VLCMediaList *mediaList = _playbackService.isShuffleMode ? _playbackService.shuffledList : _playbackService.mediaList;
104+
NSInteger mediaListCount = mediaList.count;
105+
NSMutableArray<CPListItem *> *items = [NSMutableArray new];
106+
107+
for (NSInteger index = 0; index < mediaListCount; index++) {
108+
VLCMLMedia *media = [VLCMLMedia mediaForPlayingMedia:[mediaList mediaAtIndex:index]];
109+
CPListItem *listItem = [[CPListItem alloc] initWithText:media.title detailText:media.artist.name];
110+
111+
[items addObject:listItem];
112+
}
113+
114+
return [[CPListSection alloc] initWithItems:items];
115+
}
116+
117+
- (void)listTemplate:(CPListTemplate *)listTemplate didSelectListItem:(CPListItem *)item completionHandler:(void (^)(void))completionHandler
118+
{
119+
VLCMediaList *mediaList = _playbackService.isShuffleMode ? _playbackService.shuffledList : _playbackService.mediaList;
120+
NSIndexPath *index = [listTemplate indexPathForItem:item];
121+
if (index.row >= mediaList.count) {
122+
return;
123+
}
124+
125+
[_playbackService playItemAtIndex:index.row];
126+
127+
dispatch_async(dispatch_get_main_queue(), ^{
128+
[self->_interfaceController popTemplateAnimated:YES];
129+
});
130+
}
131+
132+
- (void)displayPlayQueueTemplate
133+
{
134+
if (!_playQueueTemplate) {
135+
_section = [self createListSection];
136+
_playQueueTemplate = [[CPListTemplate alloc] initWithTitle:NSLocalizedString(@"QUEUE_LABEL", "") sections:@[_section]];
137+
_playQueueTemplate.delegate = self;
138+
}
139+
140+
[_interfaceController pushTemplate:_playQueueTemplate animated:YES];
141+
}
142+
143+
- (void)resetPlayQueueTemplate
144+
{
145+
_playQueueTemplate = nil;
146+
_section = nil;
147+
}
148+
90149
@end
91150

92151
#pragma clang diagnostic pop

Sources/CarPlay/VLCNowPlayingTemplateObserver.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,8 @@
1515

1616
NS_ASSUME_NONNULL_BEGIN
1717

18+
extern NSString *const VLCDisplayPlayQueueCarPlay;
19+
1820
@interface VLCNowPlayingTemplateObserver : NSObject <CPNowPlayingTemplateObserver>
1921

2022
- (void)configureNowPlayingTemplate;

Sources/CarPlay/VLCNowPlayingTemplateObserver.m

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,8 @@
1818
#pragma clang diagnostic push
1919
#pragma clang diagnostic ignored "-Wpartial-availability"
2020

21+
NSString *const VLCDisplayPlayQueueCarPlay = @"VLCDisplayPlayQueueCarPlay";
22+
2123
@implementation VLCNowPlayingTemplateObserver
2224

2325
- (instancetype)init
@@ -54,12 +56,10 @@ - (void)configureNowPlayingTemplate
5456
reportedRepeatType = MPRepeatTypeAll;
5557
vlcRepeatMode = VLCRepeatAllItems;
5658
break;
57-
5859
case VLCRepeatAllItems:
5960
reportedRepeatType = MPRepeatTypeOff;
6061
vlcRepeatMode = VLCDoNotRepeat;
6162
break;
62-
6363
default:
6464
reportedRepeatType = MPRepeatTypeOne;
6565
vlcRepeatMode = VLCRepeatCurrentItem;
@@ -96,7 +96,10 @@ - (void)playbackDidMoveOnToNextItem:(NSNotification *)aNotification
9696

9797
- (void)nowPlayingTemplateUpNextButtonTapped:(CPNowPlayingTemplate *)nowPlayingTemplate
9898
{
99-
[[VLCPlaybackService sharedInstance] next];
99+
// When CarPlay calls this method on your observer, you should push an instance of CPListTemplate—other template
100+
// types are not supported when Now Playing is the visible template—on to your navigation stack that displays a
101+
// list of upcoming or queued content (cf. CPNowPlayingTemplate documentation)
102+
[[NSNotificationCenter defaultCenter] postNotificationName:VLCDisplayPlayQueueCarPlay object:self];
100103
}
101104

102105
- (void)playModeUpdated:(NSNotification *)aNotification
@@ -109,11 +112,9 @@ - (void)playModeUpdated:(NSNotification *)aNotification
109112
case VLCRepeatCurrentItem:
110113
reportedRepeatType = MPRepeatTypeOne;
111114
break;
112-
113115
case VLCRepeatAllItems:
114116
reportedRepeatType = MPRepeatTypeAll;
115117
break;
116-
117118
default:
118119
reportedRepeatType = MPRepeatTypeOff;
119120
}

0 commit comments

Comments
 (0)