1ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown/* 2ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * Copyright (C) 2013 The Android Open Source Project 3ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * 4ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * Licensed under the Apache License, Version 2.0 (the "License"); 5ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * you may not use this file except in compliance with the License. 6ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * You may obtain a copy of the License at 7ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * 8ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * http://www.apache.org/licenses/LICENSE-2.0 9ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * 10ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * Unless required by applicable law or agreed to in writing, software 11ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * distributed under the License is distributed on an "AS IS" BASIS, 12ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * See the License for the specific language governing permissions and 14ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * limitations under the License. 15ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown */ 16ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 17ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brownpackage com.example.android.supportv7.media; 18ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 191636d4634299cba990966c01dbb577275ab8273cJae Seoimport android.app.PendingIntent; 20ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brownimport android.content.Context; 21ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brownimport android.content.Intent; 22ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brownimport android.content.IntentFilter; 23ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brownimport android.content.IntentFilter.MalformedMimeTypeException; 245d429bc3a8195d6f37cf2f7da0935972950539b4RoboErikimport android.content.IntentSender; 25ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brownimport android.content.res.Resources; 267578fad97dcd3b4b390652f37a30d805538980f5Chong Zhangimport android.media.AudioManager; 27ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brownimport android.media.MediaRouter; 28ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brownimport android.net.Uri; 29ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brownimport android.os.Bundle; 30def582a5836579a3fadabfdbe4413cb1652bf098Aurimas Liutikasimport android.util.Log; 31def582a5836579a3fadabfdbe4413cb1652bf098Aurimas Liutikas 32ac5fe7c617c66850fff75a9fce9979c6e5674b0fAurimas Liutikasimport androidx.mediarouter.media.MediaControlIntent; 33ac5fe7c617c66850fff75a9fce9979c6e5674b0fAurimas Liutikasimport androidx.mediarouter.media.MediaRouteDescriptor; 34ac5fe7c617c66850fff75a9fce9979c6e5674b0fAurimas Liutikasimport androidx.mediarouter.media.MediaRouteProvider; 35ac5fe7c617c66850fff75a9fce9979c6e5674b0fAurimas Liutikasimport androidx.mediarouter.media.MediaRouteProviderDescriptor; 36ac5fe7c617c66850fff75a9fce9979c6e5674b0fAurimas Liutikasimport androidx.mediarouter.media.MediaRouter.ControlRequestCallback; 37ac5fe7c617c66850fff75a9fce9979c6e5674b0fAurimas Liutikasimport androidx.mediarouter.media.MediaSessionStatus; 381636d4634299cba990966c01dbb577275ab8273cJae Seo 391636d4634299cba990966c01dbb577275ab8273cJae Seoimport com.example.android.supportv7.R; 408e006e629800b4a2643416f97bca2711af728837Jeff Brown 4155e47d370890d3cbdab82857090c42df734ba276Jeff Brownimport java.util.ArrayList; 42bc89096eeed02fd163eaed46b88364486c76c4feJeff Brown 43ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown/** 44ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * Demonstrates how to create a custom media route provider. 45ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * 46ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * @see SampleMediaRouteProviderService 47ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown */ 48ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brownfinal class SampleMediaRouteProvider extends MediaRouteProvider { 49ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown private static final String TAG = "SampleMediaRouteProvider"; 50ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 51ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown private static final String FIXED_VOLUME_ROUTE_ID = "fixed"; 52a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private static final String VARIABLE_VOLUME_BASIC_ROUTE_ID = "variable_basic"; 53a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private static final String VARIABLE_VOLUME_QUEUING_ROUTE_ID = "variable_queuing"; 54a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private static final String VARIABLE_VOLUME_SESSION_ROUTE_ID = "variable_session"; 551636d4634299cba990966c01dbb577275ab8273cJae Seo 56ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown private static final int VOLUME_MAX = 10; 57ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 58ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown /** 59ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * A custom media control intent category for special requests that are 60ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * supported by this provider's routes. 61ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown */ 62ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown public static final String CATEGORY_SAMPLE_ROUTE = 6355e47d370890d3cbdab82857090c42df734ba276Jeff Brown "com.example.android.supportv7.media.CATEGORY_SAMPLE_ROUTE"; 64ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 65ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown /** 6670f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho * A custom media control intent action to take a snapshot. 67ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * </p> 68ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown * 6970f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho * @see #EXTRA_SNAPSHOT 70ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown */ 7170f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho public static final String ACTION_TAKE_SNAPSHOT = 7270f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho "com.example.android.supportv7.media.action.TAKE_SNAPSHOT"; 73cf61a6ed2bfa6141b832fdc40a9fbfb70af91416Chong Zhang 74cf61a6ed2bfa6141b832fdc40a9fbfb70af91416Chong Zhang /** 7570f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho * {@link #ACTION_TAKE_SNAPSHOT} result data: a bitmap containing a snapshot 76cf61a6ed2bfa6141b832fdc40a9fbfb70af91416Chong Zhang * of the currently playing media item 77cf61a6ed2bfa6141b832fdc40a9fbfb70af91416Chong Zhang */ 7870f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho public static final String EXTRA_SNAPSHOT = 7970f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho "com.example.android.supportv7.media.extra.SNAPSHOT"; 80ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 81a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private static final ArrayList<IntentFilter> CONTROL_FILTERS_BASIC; 82a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private static final ArrayList<IntentFilter> CONTROL_FILTERS_QUEUING; 83a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private static final ArrayList<IntentFilter> CONTROL_FILTERS_SESSION; 8457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 85ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown static { 8655e47d370890d3cbdab82857090c42df734ba276Jeff Brown IntentFilter f1 = new IntentFilter(); 8755e47d370890d3cbdab82857090c42df734ba276Jeff Brown f1.addCategory(CATEGORY_SAMPLE_ROUTE); 8870f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho f1.addAction(ACTION_TAKE_SNAPSHOT); 8955e47d370890d3cbdab82857090c42df734ba276Jeff Brown 9055e47d370890d3cbdab82857090c42df734ba276Jeff Brown IntentFilter f2 = new IntentFilter(); 9155e47d370890d3cbdab82857090c42df734ba276Jeff Brown f2.addCategory(MediaControlIntent.CATEGORY_REMOTE_PLAYBACK); 9255e47d370890d3cbdab82857090c42df734ba276Jeff Brown f2.addAction(MediaControlIntent.ACTION_PLAY); 9355e47d370890d3cbdab82857090c42df734ba276Jeff Brown f2.addDataScheme("http"); 9455e47d370890d3cbdab82857090c42df734ba276Jeff Brown f2.addDataScheme("https"); 9557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f2.addDataScheme("rtsp"); 9657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f2.addDataScheme("file"); 9755e47d370890d3cbdab82857090c42df734ba276Jeff Brown addDataTypeUnchecked(f2, "video/*"); 9855e47d370890d3cbdab82857090c42df734ba276Jeff Brown 9957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang IntentFilter f3 = new IntentFilter(); 10057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f3.addCategory(MediaControlIntent.CATEGORY_REMOTE_PLAYBACK); 10157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f3.addAction(MediaControlIntent.ACTION_SEEK); 10257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f3.addAction(MediaControlIntent.ACTION_GET_STATUS); 10357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f3.addAction(MediaControlIntent.ACTION_PAUSE); 10457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f3.addAction(MediaControlIntent.ACTION_RESUME); 10557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f3.addAction(MediaControlIntent.ACTION_STOP); 10657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 10757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang IntentFilter f4 = new IntentFilter(); 10857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f4.addCategory(MediaControlIntent.CATEGORY_REMOTE_PLAYBACK); 10957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f4.addAction(MediaControlIntent.ACTION_ENQUEUE); 11057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f4.addDataScheme("http"); 11157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f4.addDataScheme("https"); 11257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f4.addDataScheme("rtsp"); 11357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f4.addDataScheme("file"); 11457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang addDataTypeUnchecked(f4, "video/*"); 11557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 11657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang IntentFilter f5 = new IntentFilter(); 11757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f5.addCategory(MediaControlIntent.CATEGORY_REMOTE_PLAYBACK); 11857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang f5.addAction(MediaControlIntent.ACTION_REMOVE); 11957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 120a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang IntentFilter f6 = new IntentFilter(); 121a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang f6.addCategory(MediaControlIntent.CATEGORY_REMOTE_PLAYBACK); 122a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang f6.addAction(MediaControlIntent.ACTION_START_SESSION); 123a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang f6.addAction(MediaControlIntent.ACTION_GET_SESSION_STATUS); 124a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang f6.addAction(MediaControlIntent.ACTION_END_SESSION); 125a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang 126f515b3268334381e81f7a4eb8283a362b9a6f725Jae Seo CONTROL_FILTERS_BASIC = new ArrayList<>(); 127a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang CONTROL_FILTERS_BASIC.add(f1); 128a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang CONTROL_FILTERS_BASIC.add(f2); 129a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang CONTROL_FILTERS_BASIC.add(f3); 130a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang 131f515b3268334381e81f7a4eb8283a362b9a6f725Jae Seo CONTROL_FILTERS_QUEUING = new ArrayList<>(CONTROL_FILTERS_BASIC); 132a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang CONTROL_FILTERS_QUEUING.add(f4); 133a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang CONTROL_FILTERS_QUEUING.add(f5); 134a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang 135f515b3268334381e81f7a4eb8283a362b9a6f725Jae Seo CONTROL_FILTERS_SESSION = new ArrayList<>(CONTROL_FILTERS_QUEUING); 136a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang CONTROL_FILTERS_SESSION.add(f6); 137ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 138ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 139ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown private static void addDataTypeUnchecked(IntentFilter filter, String type) { 140ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown try { 141ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown filter.addDataType(type); 142ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } catch (MalformedMimeTypeException ex) { 143ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown throw new RuntimeException(ex); 144ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 145ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 146ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 147ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown private int mVolume = 5; 148ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 149ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown public SampleMediaRouteProvider(Context context) { 150ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown super(context); 151ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 152ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown publishRoutes(); 153ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 154ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 155ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown @Override 156ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown public RouteController onCreateRouteController(String routeId) { 157ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown return new SampleRouteController(routeId); 158ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 159ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 160ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown private void publishRoutes() { 161ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown Resources r = getContext().getResources(); 1625d429bc3a8195d6f37cf2f7da0935972950539b4RoboErik Intent settingsIntent = new Intent(Intent.ACTION_MAIN); 1635d429bc3a8195d6f37cf2f7da0935972950539b4RoboErik settingsIntent.setClass(getContext(), SampleMediaRouteSettingsActivity.class); 1645d429bc3a8195d6f37cf2f7da0935972950539b4RoboErik IntentSender is = PendingIntent.getActivity(getContext(), 99, settingsIntent, 1655d429bc3a8195d6f37cf2f7da0935972950539b4RoboErik Intent.FLAG_ACTIVITY_NEW_TASK).getIntentSender(); 166ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 16755e47d370890d3cbdab82857090c42df734ba276Jeff Brown MediaRouteDescriptor routeDescriptor1 = new MediaRouteDescriptor.Builder( 168ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown FIXED_VOLUME_ROUTE_ID, 16955e47d370890d3cbdab82857090c42df734ba276Jeff Brown r.getString(R.string.fixed_volume_route_name)) 170b28eb61b29c0d956a5e504716cdea9f31184a998Jeff Brown .setDescription(r.getString(R.string.sample_route_description)) 171a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .addControlFilters(CONTROL_FILTERS_BASIC) 1727578fad97dcd3b4b390652f37a30d805538980f5Chong Zhang .setPlaybackStream(AudioManager.STREAM_MUSIC) 17355e47d370890d3cbdab82857090c42df734ba276Jeff Brown .setPlaybackType(MediaRouter.RouteInfo.PLAYBACK_TYPE_REMOTE) 17455e47d370890d3cbdab82857090c42df734ba276Jeff Brown .setVolumeHandling(MediaRouter.RouteInfo.PLAYBACK_VOLUME_FIXED) 17555e47d370890d3cbdab82857090c42df734ba276Jeff Brown .setVolume(VOLUME_MAX) 1765d429bc3a8195d6f37cf2f7da0935972950539b4RoboErik .setCanDisconnect(true) 1775d429bc3a8195d6f37cf2f7da0935972950539b4RoboErik .setSettingsActivity(is) 17855e47d370890d3cbdab82857090c42df734ba276Jeff Brown .build(); 17955e47d370890d3cbdab82857090c42df734ba276Jeff Brown 18055e47d370890d3cbdab82857090c42df734ba276Jeff Brown MediaRouteDescriptor routeDescriptor2 = new MediaRouteDescriptor.Builder( 181a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang VARIABLE_VOLUME_BASIC_ROUTE_ID, 182a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang r.getString(R.string.variable_volume_basic_route_name)) 183a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .setDescription(r.getString(R.string.sample_route_description)) 184a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .addControlFilters(CONTROL_FILTERS_BASIC) 185a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .setPlaybackStream(AudioManager.STREAM_MUSIC) 186a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .setPlaybackType(MediaRouter.RouteInfo.PLAYBACK_TYPE_REMOTE) 187a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .setVolumeHandling(MediaRouter.RouteInfo.PLAYBACK_VOLUME_VARIABLE) 188a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .setVolumeMax(VOLUME_MAX) 189a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .setVolume(mVolume) 1905d429bc3a8195d6f37cf2f7da0935972950539b4RoboErik .setSettingsActivity(is) 191a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .build(); 192a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang 193a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang MediaRouteDescriptor routeDescriptor3 = new MediaRouteDescriptor.Builder( 194a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang VARIABLE_VOLUME_QUEUING_ROUTE_ID, 195a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang r.getString(R.string.variable_volume_queuing_route_name)) 196b28eb61b29c0d956a5e504716cdea9f31184a998Jeff Brown .setDescription(r.getString(R.string.sample_route_description)) 197a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .addControlFilters(CONTROL_FILTERS_QUEUING) 198a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .setPlaybackStream(AudioManager.STREAM_MUSIC) 199a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .setPlaybackType(MediaRouter.RouteInfo.PLAYBACK_TYPE_REMOTE) 200a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .setVolumeHandling(MediaRouter.RouteInfo.PLAYBACK_VOLUME_VARIABLE) 201a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .setVolumeMax(VOLUME_MAX) 202a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .setVolume(mVolume) 2035d429bc3a8195d6f37cf2f7da0935972950539b4RoboErik .setCanDisconnect(true) 204a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .build(); 205a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang 206b75af7ac526bff715c04ab79414700125f895663Sungsoo Lim Uri iconUri = Uri.parse("android.resource://com.example.android.supportv7/" 207b75af7ac526bff715c04ab79414700125f895663Sungsoo Lim + R.drawable.ic_android); 208a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang MediaRouteDescriptor routeDescriptor4 = new MediaRouteDescriptor.Builder( 209a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang VARIABLE_VOLUME_SESSION_ROUTE_ID, 210a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang r.getString(R.string.variable_volume_session_route_name)) 211a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .setDescription(r.getString(R.string.sample_route_description)) 212a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .addControlFilters(CONTROL_FILTERS_SESSION) 2137578fad97dcd3b4b390652f37a30d805538980f5Chong Zhang .setPlaybackStream(AudioManager.STREAM_MUSIC) 21455e47d370890d3cbdab82857090c42df734ba276Jeff Brown .setPlaybackType(MediaRouter.RouteInfo.PLAYBACK_TYPE_REMOTE) 21555e47d370890d3cbdab82857090c42df734ba276Jeff Brown .setVolumeHandling(MediaRouter.RouteInfo.PLAYBACK_VOLUME_VARIABLE) 21655e47d370890d3cbdab82857090c42df734ba276Jeff Brown .setVolumeMax(VOLUME_MAX) 21755e47d370890d3cbdab82857090c42df734ba276Jeff Brown .setVolume(mVolume) 21876d965dc41863b33f887db33d283cb7f1523f60dJae Seo .setIconUri(iconUri) 21976d965dc41863b33f887db33d283cb7f1523f60dJae Seo .build(); 22076d965dc41863b33f887db33d283cb7f1523f60dJae Seo 2211636d4634299cba990966c01dbb577275ab8273cJae Seo MediaRouteProviderDescriptor providerDescriptor = new MediaRouteProviderDescriptor.Builder() 22255e47d370890d3cbdab82857090c42df734ba276Jeff Brown .addRoute(routeDescriptor1) 22355e47d370890d3cbdab82857090c42df734ba276Jeff Brown .addRoute(routeDescriptor2) 224a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .addRoute(routeDescriptor3) 225a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang .addRoute(routeDescriptor4) 22655e47d370890d3cbdab82857090c42df734ba276Jeff Brown .build(); 227ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown setDescriptor(providerDescriptor); 228ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 229ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 230ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown private final class SampleRouteController extends MediaRouteProvider.RouteController { 231ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown private final String mRouteId; 232a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private final SessionManager mSessionManager = new SessionManager("mrp"); 233a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private final Player mPlayer; 234a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private PendingIntent mSessionReceiver; 235ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 236ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown public SampleRouteController(String routeId) { 237ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown mRouteId = routeId; 2389a2de97bec8126f8c8c05e9c995f378c5a73319aRoboErik mPlayer = Player.create(getContext(), null, null); 239a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mSessionManager.setPlayer(mPlayer); 240a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mSessionManager.setCallback(new SessionManager.Callback() { 2418e006e629800b4a2643416f97bca2711af728837Jeff Brown @Override 242a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang public void onStatusChanged() { 2438e006e629800b4a2643416f97bca2711af728837Jeff Brown } 2448e006e629800b4a2643416f97bca2711af728837Jeff Brown 2458e006e629800b4a2643416f97bca2711af728837Jeff Brown @Override 246a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang public void onItemChanged(PlaylistItem item) { 247a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang handleStatusChange(item); 2488e006e629800b4a2643416f97bca2711af728837Jeff Brown } 2498e006e629800b4a2643416f97bca2711af728837Jeff Brown }); 250cf61a6ed2bfa6141b832fdc40a9fbfb70af91416Chong Zhang setVolumeInternal(mVolume); 251ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown Log.d(TAG, mRouteId + ": Controller created"); 252ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 253ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 254ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown @Override 255bc89096eeed02fd163eaed46b88364486c76c4feJeff Brown public void onRelease() { 256ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown Log.d(TAG, mRouteId + ": Controller released"); 257a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mPlayer.release(); 258ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 259ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 260ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown @Override 261bc89096eeed02fd163eaed46b88364486c76c4feJeff Brown public void onSelect() { 262ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown Log.d(TAG, mRouteId + ": Selected"); 263a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mPlayer.connect(null); 264ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 265ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 266ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown @Override 267bc89096eeed02fd163eaed46b88364486c76c4feJeff Brown public void onUnselect() { 268ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown Log.d(TAG, mRouteId + ": Unselected"); 269a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mPlayer.release(); 270ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 271ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 272ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown @Override 273bc89096eeed02fd163eaed46b88364486c76c4feJeff Brown public void onSetVolume(int volume) { 274ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown Log.d(TAG, mRouteId + ": Set volume to " + volume); 275a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (!mRouteId.equals(FIXED_VOLUME_ROUTE_ID)) { 276ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown setVolumeInternal(volume); 277ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 278ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 279ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 280ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown @Override 281bc89096eeed02fd163eaed46b88364486c76c4feJeff Brown public void onUpdateVolume(int delta) { 282ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown Log.d(TAG, mRouteId + ": Update volume by " + delta); 283a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (!mRouteId.equals(FIXED_VOLUME_ROUTE_ID)) { 284ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown setVolumeInternal(mVolume + delta); 285ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 286ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 287ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 288ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown @Override 289bc89096eeed02fd163eaed46b88364486c76c4feJeff Brown public boolean onControlRequest(Intent intent, ControlRequestCallback callback) { 290ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown Log.d(TAG, mRouteId + ": Received control request " + intent); 29157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang String action = intent.getAction(); 29257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (intent.hasCategory(MediaControlIntent.CATEGORY_REMOTE_PLAYBACK)) { 29357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang boolean success = false; 29457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (action.equals(MediaControlIntent.ACTION_PLAY)) { 29557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang success = handlePlay(intent, callback); 29657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else if (action.equals(MediaControlIntent.ACTION_ENQUEUE)) { 29757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang success = handleEnqueue(intent, callback); 29857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else if (action.equals(MediaControlIntent.ACTION_REMOVE)) { 29957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang success = handleRemove(intent, callback); 30057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else if (action.equals(MediaControlIntent.ACTION_SEEK)) { 30157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang success = handleSeek(intent, callback); 30257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else if (action.equals(MediaControlIntent.ACTION_GET_STATUS)) { 30357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang success = handleGetStatus(intent, callback); 30457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else if (action.equals(MediaControlIntent.ACTION_PAUSE)) { 30557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang success = handlePause(intent, callback); 30657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else if (action.equals(MediaControlIntent.ACTION_RESUME)) { 30757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang success = handleResume(intent, callback); 30857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else if (action.equals(MediaControlIntent.ACTION_STOP)) { 30957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang success = handleStop(intent, callback); 310a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } else if (action.equals(MediaControlIntent.ACTION_START_SESSION)) { 311a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang success = handleStartSession(intent, callback); 312a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } else if (action.equals(MediaControlIntent.ACTION_GET_SESSION_STATUS)) { 313a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang success = handleGetSessionStatus(intent, callback); 314a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } else if (action.equals(MediaControlIntent.ACTION_END_SESSION)) { 315a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang success = handleEndSession(intent, callback); 316ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 31757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang Log.d(TAG, mSessionManager.toString()); 31857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang return success; 319ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 320ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown 32170f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho if (callback != null && action.equals(ACTION_TAKE_SNAPSHOT) 322ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown && intent.hasCategory(CATEGORY_SAMPLE_ROUTE)) { 32370f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho if (mSessionManager.getCurrentItem() != null) { 32470f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho Bundle data = new Bundle(); 32570f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho data.putParcelable(EXTRA_SNAPSHOT, mPlayer.getSnapshot()); 326fcb6a9d1caaf43ae41f859ebb58a4483b12475a1Jeff Brown callback.onResult(data); 32770f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho } else { 32870f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho callback.onError("Failed to take a snapshot", null); 329ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 330ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown return true; 331ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 332ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown return false; 333ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 33457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 33557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang private void setVolumeInternal(int volume) { 33657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (volume >= 0 && volume <= VOLUME_MAX) { 33757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang mVolume = volume; 33857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang Log.d(TAG, mRouteId + ": New volume is " + mVolume); 3397578fad97dcd3b4b390652f37a30d805538980f5Chong Zhang AudioManager audioManager = 3407578fad97dcd3b4b390652f37a30d805538980f5Chong Zhang (AudioManager)getContext().getSystemService(Context.AUDIO_SERVICE); 3417578fad97dcd3b4b390652f37a30d805538980f5Chong Zhang audioManager.setStreamVolume(AudioManager.STREAM_MUSIC, volume, 0); 34257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang publishRoutes(); 34357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 34457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 34557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 34657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang private boolean handlePlay(Intent intent, ControlRequestCallback callback) { 34757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang String sid = intent.getStringExtra(MediaControlIntent.EXTRA_SESSION_ID); 348a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (sid != null && !sid.equals(mSessionManager.getSessionId())) { 349a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang Log.d(TAG, "handlePlay fails because of bad sid="+sid); 350a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang return false; 35157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 352a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (mSessionManager.hasSession()) { 353a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mSessionManager.stop(); 354a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } 355a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang return handleEnqueue(intent, callback); 35657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 35757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 35857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang private boolean handleEnqueue(Intent intent, ControlRequestCallback callback) { 359a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang String sid = intent.getStringExtra(MediaControlIntent.EXTRA_SESSION_ID); 360a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (sid != null && !sid.equals(mSessionManager.getSessionId())) { 361a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang Log.d(TAG, "handleEnqueue fails because of bad sid="+sid); 36257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang return false; 36357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 36457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 365a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang Uri uri = intent.getData(); 366a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (uri == null) { 367a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang Log.d(TAG, "handleEnqueue fails because of bad uri="+uri); 368a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang return false; 369a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } 37057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 37157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang boolean enqueue = intent.getAction().equals(MediaControlIntent.ACTION_ENQUEUE); 372a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang String mime = intent.getType(); 37357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang long pos = intent.getLongExtra(MediaControlIntent.EXTRA_ITEM_CONTENT_POSITION, 0); 37457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang Bundle metadata = intent.getBundleExtra(MediaControlIntent.EXTRA_ITEM_METADATA); 37557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang Bundle headers = intent.getBundleExtra(MediaControlIntent.EXTRA_ITEM_HTTP_HEADERS); 37657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang PendingIntent receiver = (PendingIntent)intent.getParcelableExtra( 37757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang MediaControlIntent.EXTRA_ITEM_STATUS_UPDATE_RECEIVER); 37857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 37957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang Log.d(TAG, mRouteId + ": Received " + (enqueue?"enqueue":"play") + " request" 38057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang + ", uri=" + uri 381a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang + ", mime=" + mime 38257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang + ", sid=" + sid 38357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang + ", pos=" + pos 38457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang + ", metadata=" + metadata 38557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang + ", headers=" + headers 38657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang + ", receiver=" + receiver); 38770f3627685b55b2bc1b3f0c17c9c30aa3a7fd062Donghyun Cho PlaylistItem item = mSessionManager.add(null, uri, mime, receiver); 38857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (callback != null) { 38957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (item != null) { 39057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang Bundle result = new Bundle(); 39157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang result.putString(MediaControlIntent.EXTRA_SESSION_ID, item.getSessionId()); 39257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang result.putString(MediaControlIntent.EXTRA_ITEM_ID, item.getItemId()); 39357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang result.putBundle(MediaControlIntent.EXTRA_ITEM_STATUS, 39457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang item.getStatus().asBundle()); 39557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang callback.onResult(result); 39657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else { 39757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang callback.onError("Failed to open " + uri.toString(), null); 39857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 39957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 40057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang return true; 40157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 40257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 40357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang private boolean handleRemove(Intent intent, ControlRequestCallback callback) { 40457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang String sid = intent.getStringExtra(MediaControlIntent.EXTRA_SESSION_ID); 405a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (sid == null || !sid.equals(mSessionManager.getSessionId())) { 406a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang return false; 407a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } 408a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang 40957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang String iid = intent.getStringExtra(MediaControlIntent.EXTRA_ITEM_ID); 410a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang PlaylistItem item = mSessionManager.remove(iid); 41157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (callback != null) { 41257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (item != null) { 41357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang Bundle result = new Bundle(); 41457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang result.putBundle(MediaControlIntent.EXTRA_ITEM_STATUS, 41557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang item.getStatus().asBundle()); 41657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang callback.onResult(result); 41757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else { 41857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang callback.onError("Failed to remove" + 41957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang ", sid=" + sid + ", iid=" + iid, null); 42057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 42157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 42257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang return (item != null); 42357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 42457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 42557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang private boolean handleSeek(Intent intent, ControlRequestCallback callback) { 42657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang String sid = intent.getStringExtra(MediaControlIntent.EXTRA_SESSION_ID); 427a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (sid == null || !sid.equals(mSessionManager.getSessionId())) { 428a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang return false; 429a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } 430a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang 43157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang String iid = intent.getStringExtra(MediaControlIntent.EXTRA_ITEM_ID); 43257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang long pos = intent.getLongExtra(MediaControlIntent.EXTRA_ITEM_CONTENT_POSITION, 0); 43357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang Log.d(TAG, mRouteId + ": Received seek request, pos=" + pos); 434a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang PlaylistItem item = mSessionManager.seek(iid, pos); 43557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (callback != null) { 43657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (item != null) { 43757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang Bundle result = new Bundle(); 43857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang result.putBundle(MediaControlIntent.EXTRA_ITEM_STATUS, 43957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang item.getStatus().asBundle()); 44057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang callback.onResult(result); 44157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else { 44257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang callback.onError("Failed to seek" + 44357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang ", sid=" + sid + ", iid=" + iid + ", pos=" + pos, null); 44457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 44557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 44657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang return (item != null); 44757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 44857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 44957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang private boolean handleGetStatus(Intent intent, ControlRequestCallback callback) { 45057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang String sid = intent.getStringExtra(MediaControlIntent.EXTRA_SESSION_ID); 45157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang String iid = intent.getStringExtra(MediaControlIntent.EXTRA_ITEM_ID); 452a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang Log.d(TAG, mRouteId + ": Received getStatus request, sid=" + sid + ", iid=" + iid); 453a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang PlaylistItem item = mSessionManager.getStatus(iid); 45457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (callback != null) { 45557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (item != null) { 45657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang Bundle result = new Bundle(); 45757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang result.putBundle(MediaControlIntent.EXTRA_ITEM_STATUS, 45857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang item.getStatus().asBundle()); 45957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang callback.onResult(result); 46057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else { 46157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang callback.onError("Failed to get status" + 46257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang ", sid=" + sid + ", iid=" + iid, null); 46357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 46457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 46557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang return (item != null); 46657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 46757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 46857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang private boolean handlePause(Intent intent, ControlRequestCallback callback) { 46957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang String sid = intent.getStringExtra(MediaControlIntent.EXTRA_SESSION_ID); 470a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang boolean success = (sid != null) && sid.equals(mSessionManager.getSessionId()); 471a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mSessionManager.pause(); 47257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (callback != null) { 47357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (success) { 474a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang callback.onResult(new Bundle()); 475a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang handleSessionStatusChange(sid); 47657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else { 47757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang callback.onError("Failed to pause, sid=" + sid, null); 47857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 47957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 48057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang return success; 48157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 48257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 48357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang private boolean handleResume(Intent intent, ControlRequestCallback callback) { 48457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang String sid = intent.getStringExtra(MediaControlIntent.EXTRA_SESSION_ID); 485a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang boolean success = (sid != null) && sid.equals(mSessionManager.getSessionId()); 486a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mSessionManager.resume(); 48757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (callback != null) { 48857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (success) { 489a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang callback.onResult(new Bundle()); 490a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang handleSessionStatusChange(sid); 49157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else { 49257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang callback.onError("Failed to resume, sid=" + sid, null); 49357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 49457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 49557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang return success; 49657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 49757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 49857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang private boolean handleStop(Intent intent, ControlRequestCallback callback) { 49957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang String sid = intent.getStringExtra(MediaControlIntent.EXTRA_SESSION_ID); 500a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang boolean success = (sid != null) && sid.equals(mSessionManager.getSessionId()); 501a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mSessionManager.stop(); 50257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (callback != null) { 50357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (success) { 504a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang callback.onResult(new Bundle()); 505a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang handleSessionStatusChange(sid); 50657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } else { 50757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang callback.onError("Failed to stop, sid=" + sid, null); 50857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 50957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 51057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang return success; 51157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 51257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 513a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private boolean handleStartSession(Intent intent, ControlRequestCallback callback) { 514a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang String sid = mSessionManager.startSession(); 515a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang Log.d(TAG, "StartSession returns sessionId "+sid); 516a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (callback != null) { 517a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (sid != null) { 518a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang Bundle result = new Bundle(); 519a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang result.putString(MediaControlIntent.EXTRA_SESSION_ID, sid); 520a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang result.putBundle(MediaControlIntent.EXTRA_SESSION_STATUS, 521a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mSessionManager.getSessionStatus(sid).asBundle()); 522a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang callback.onResult(result); 523a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mSessionReceiver = (PendingIntent)intent.getParcelableExtra( 524a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang MediaControlIntent.EXTRA_SESSION_STATUS_UPDATE_RECEIVER); 525a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang handleSessionStatusChange(sid); 526a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } else { 527a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang callback.onError("Failed to start session.", null); 528a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } 529a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } 530a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang return (sid != null); 531a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } 532a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang 533a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private boolean handleGetSessionStatus(Intent intent, ControlRequestCallback callback) { 534a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang String sid = intent.getStringExtra(MediaControlIntent.EXTRA_SESSION_ID); 535a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang 536a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang MediaSessionStatus sessionStatus = mSessionManager.getSessionStatus(sid); 537a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (callback != null) { 538a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (sessionStatus != null) { 539a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang Bundle result = new Bundle(); 540a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang result.putBundle(MediaControlIntent.EXTRA_SESSION_STATUS, 541a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mSessionManager.getSessionStatus(sid).asBundle()); 542a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang callback.onResult(result); 543a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } else { 544a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang callback.onError("Failed to get session status, sid=" + sid, null); 545a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } 54657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 547a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang return (sessionStatus != null); 54857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 54957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 550a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private boolean handleEndSession(Intent intent, ControlRequestCallback callback) { 551a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang String sid = intent.getStringExtra(MediaControlIntent.EXTRA_SESSION_ID); 552a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang boolean success = (sid != null) && sid.equals(mSessionManager.getSessionId()) 553a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang && mSessionManager.endSession(); 554a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (callback != null) { 555a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (success) { 556a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang Bundle result = new Bundle(); 557a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang MediaSessionStatus sessionStatus = new MediaSessionStatus.Builder( 558a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang MediaSessionStatus.SESSION_STATE_ENDED).build(); 559a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang result.putBundle(MediaControlIntent.EXTRA_SESSION_STATUS, sessionStatus.asBundle()); 560a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang callback.onResult(result); 561a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang handleSessionStatusChange(sid); 562a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mSessionReceiver = null; 563a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } else { 564a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang callback.onError("Failed to end session, sid=" + sid, null); 565a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } 566a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } 567a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang return success; 568a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } 569a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang 570a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private void handleStatusChange(PlaylistItem item) { 57157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (item == null) { 57257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang item = mSessionManager.getCurrentItem(); 57357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 57457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (item != null) { 57557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang PendingIntent receiver = item.getUpdateReceiver(); 57657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang if (receiver != null) { 57757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang Intent intent = new Intent(); 57857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang intent.putExtra(MediaControlIntent.EXTRA_SESSION_ID, item.getSessionId()); 57957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang intent.putExtra(MediaControlIntent.EXTRA_ITEM_ID, item.getItemId()); 58057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang intent.putExtra(MediaControlIntent.EXTRA_ITEM_STATUS, 58157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang item.getStatus().asBundle()); 58257456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang try { 58357456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang receiver.send(getContext(), 0, intent); 58457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang Log.d(TAG, mRouteId + ": Sending status update from provider"); 58557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } catch (PendingIntent.CanceledException e) { 58657456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang Log.d(TAG, mRouteId + ": Failed to send status update!"); 58757456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 58857456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 58957456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 59057456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 59157456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang 592a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang private void handleSessionStatusChange(String sid) { 593a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang if (mSessionReceiver != null) { 594a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang Intent intent = new Intent(); 595a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang intent.putExtra(MediaControlIntent.EXTRA_SESSION_ID, sid); 596a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang intent.putExtra(MediaControlIntent.EXTRA_SESSION_STATUS, 597a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mSessionManager.getSessionStatus(sid).asBundle()); 598a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang try { 599a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang mSessionReceiver.send(getContext(), 0, intent); 600a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang Log.d(TAG, mRouteId + ": Sending session status update from provider"); 601a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } catch (PendingIntent.CanceledException e) { 602a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang Log.d(TAG, mRouteId + ": Failed to send session status update!"); 603a6bf581f7a7a6326505569f0d1215d0ba84779d7Chong Zhang } 60457456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 60557456222f52fbfc1dcfb1b99030aad6acc02ad23Chong Zhang } 606ecdd1b114d4fb36682cdabe205e08e6f68f79f63Jeff Brown } 607e0189a39290c82f8bc1a37e6a52e959159c9a482Jae Seo} 608