MediaSession2: Pull out Command/CommandGroup from the MediaSession2

Bug: 74648408
Test: Build
Change-Id: I0a3d1ab6320c7b276e7b1defdccf9fa371ae02c0
This commit is contained in:
Jaewan Kim
2018-03-27 08:32:25 +09:00
parent ab715ec20b
commit 3b15124ecc
7 changed files with 512 additions and 457 deletions

View File

@@ -25,9 +25,7 @@ import android.app.PendingIntent;
import android.content.Context;
import android.media.MediaPlaylistAgent.RepeatMode;
import android.media.MediaPlaylistAgent.ShuffleMode;
import android.media.MediaSession2.Command;
import android.media.MediaSession2.CommandButton;
import android.media.MediaSession2.CommandGroup;
import android.media.MediaSession2.ControllerInfo;
import android.media.MediaSession2.ErrorCode;
import android.media.session.MediaSessionManager;
@@ -56,7 +54,7 @@ import java.util.concurrent.Executor;
* When controlling {@link MediaSessionService2}, the {@link MediaController2} would be
* available only if the session service allows this controller by
* {@link MediaSession2.SessionCallback#onConnect(MediaSession2, ControllerInfo)} for the service.
* Wait {@link ControllerCallback#onConnected(MediaController2, CommandGroup)} or
* Wait {@link ControllerCallback#onConnected(MediaController2, SessionCommandGroup2)} or
* {@link ControllerCallback#onDisconnected(MediaController2)} for the result.
* <p>
* A controller can be created through token from {@link MediaSessionManager} if you hold the
@@ -83,7 +81,7 @@ public class MediaController2 implements AutoCloseable {
* @param allowedCommands commands that's allowed by the session.
*/
public void onConnected(@NonNull MediaController2 controller,
@NonNull CommandGroup allowedCommands) { }
@NonNull SessionCommandGroup2 allowedCommands) { }
/**
* Called when the session refuses the controller or the controller is disconnected from
@@ -102,7 +100,8 @@ public class MediaController2 implements AutoCloseable {
* Called when the session set the custom layout through the
* {@link MediaSession2#setCustomLayout(ControllerInfo, List)}.
* <p>
* Can be called before {@link #onConnected(MediaController2, CommandGroup)} is called.
* Can be called before {@link #onConnected(MediaController2, SessionCommandGroup2)} is
* called.
*
* @param controller the controller for this event
* @param layout
@@ -126,7 +125,7 @@ public class MediaController2 implements AutoCloseable {
* @param commands newly allowed commands
*/
public void onAllowedCommandsChanged(@NonNull MediaController2 controller,
@NonNull CommandGroup commands) { }
@NonNull SessionCommandGroup2 commands) { }
/**
* Called when the session sent a custom command.
@@ -137,7 +136,7 @@ public class MediaController2 implements AutoCloseable {
* @param receiver
*/
public void onCustomCommand(@NonNull MediaController2 controller,
@NonNull Command command, @Nullable Bundle args,
@NonNull SessionCommand2 command, @Nullable Bundle args,
@Nullable ResultReceiver receiver) { }
/**
@@ -687,7 +686,7 @@ public class MediaController2 implements AutoCloseable {
* @param args optional argument
* @param cb optional result receiver
*/
public void sendCustomCommand(@NonNull Command command, @Nullable Bundle args,
public void sendCustomCommand(@NonNull SessionCommand2 command, @Nullable Bundle args,
@Nullable ResultReceiver cb) {
mProvider.sendCustomCommand_impl(command, args, cb);
}

View File

@@ -33,8 +33,6 @@ import android.media.update.ApiLoader;
import android.media.update.MediaSession2Provider;
import android.media.update.MediaSession2Provider.BuilderBaseProvider;
import android.media.update.MediaSession2Provider.CommandButtonProvider;
import android.media.update.MediaSession2Provider.CommandGroupProvider;
import android.media.update.MediaSession2Provider.CommandProvider;
import android.media.update.MediaSession2Provider.ControllerInfoProvider;
import android.media.update.ProviderCreator;
import android.net.Uri;
@@ -45,7 +43,6 @@ import android.os.ResultReceiver;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.util.List;
import java.util.Set;
import java.util.concurrent.Executor;
/**
@@ -84,248 +81,6 @@ import java.util.concurrent.Executor;
public class MediaSession2 implements AutoCloseable {
private final MediaSession2Provider mProvider;
/**
* Command code for the custom command which can be defined by string action in the
* {@link Command}.
*/
public static final int COMMAND_CODE_CUSTOM = 0;
/**
* Command code for {@link MediaController2#play()}.
* <p>
* Command would be sent directly to the player if the session doesn't reject the request
* through the {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYBACK_PLAY = 1;
/**
* Command code for {@link MediaController2#pause()}.
* <p>
* Command would be sent directly to the player if the session doesn't reject the request
* through the {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYBACK_PAUSE = 2;
/**
* Command code for {@link MediaController2#stop()}.
* <p>
* Command would be sent directly to the player if the session doesn't reject the request
* through the {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYBACK_STOP = 3;
/**
* Command code for {@link MediaController2#skipToNextItem()}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the {@link SessionCallback#onCommandRequest(
* MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SKIP_NEXT_ITEM = 4;
/**
* Command code for {@link MediaController2#skipToPreviousItem()}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the {@link SessionCallback#onCommandRequest(
* MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SKIP_PREV_ITEM = 5;
/**
* Command code for {@link MediaController2#prepare()}.
* <p>
* Command would be sent directly to the player if the session doesn't reject the request
* through the {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYBACK_PREPARE = 6;
/**
* Command code for {@link MediaController2#fastForward()}.
*/
public static final int COMMAND_CODE_SESSION_FAST_FORWARD = 7;
/**
* Command code for {@link MediaController2#rewind()}.
*/
public static final int COMMAND_CODE_SESSION_REWIND = 8;
/**
* Command code for {@link MediaController2#seekTo(long)}.
* <p>
* Command would be sent directly to the player if the session doesn't reject the request
* through the {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYBACK_SEEK_TO = 9;
/**
* Command code for both {@link MediaController2#setVolumeTo(int, int)}.
* <p>
* Command would set the device volume or send to the volume provider directly if the session
* doesn't reject the request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYBACK_SET_VOLUME = 10;
/**
* Command code for both {@link MediaController2#adjustVolume(int, int)}.
* <p>
* Command would adjust the device volume or send to the volume provider directly if the session
* doesn't reject the request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYBACK_ADJUST_VOLUME = 11;
/**
* Command code for {@link MediaController2#skipToPlaylistItem(MediaItem2)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SKIP_TO_PLAYLIST_ITEM = 12;
/**
* Command code for {@link MediaController2#setShuffleMode(int)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SET_SHUFFLE_MODE = 13;
/**
* Command code for {@link MediaController2#setRepeatMode(int)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SET_REPEAT_MODE = 14;
/**
* Command code for {@link MediaController2#addPlaylistItem(int, MediaItem2)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYLIST_ADD_ITEM = 15;
/**
* Command code for {@link MediaController2#addPlaylistItem(int, MediaItem2)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYLIST_REMOVE_ITEM = 16;
/**
* Command code for {@link MediaController2#replacePlaylistItem(int, MediaItem2)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYLIST_REPLACE_ITEM = 17;
/**
* Command code for {@link MediaController2#getPlaylist()}. This will expose metadata
* information to the controller.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYLIST_GET_LIST = 18;
/**
* Command code for {@link MediaController2#setPlaylist(List, MediaMetadata2)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SET_LIST = 19;
/**
* Command code for {@link MediaController2#getPlaylistMetadata()}. This will expose
* metadata information to the controller.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYLIST_GET_LIST_METADATA = 20;
/**
* Command code for {@link MediaController2#updatePlaylistMetadata(MediaMetadata2)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SET_LIST_METADATA = 21;
/**
* Command code for {@link MediaController2#playFromMediaId(String, Bundle)}.
*/
public static final int COMMAND_CODE_SESSION_PLAY_FROM_MEDIA_ID = 22;
/**
* Command code for {@link MediaController2#playFromUri(Uri, Bundle)}.
*/
public static final int COMMAND_CODE_SESSION_PLAY_FROM_URI = 23;
/**
* Command code for {@link MediaController2#playFromSearch(String, Bundle)}.
*/
public static final int COMMAND_CODE_SESSION_PLAY_FROM_SEARCH = 24;
/**
* Command code for {@link MediaController2#prepareFromMediaId(String, Bundle)}.
*/
public static final int COMMAND_CODE_SESSION_PREPARE_FROM_MEDIA_ID = 25;
/**
* Command code for {@link MediaController2#prepareFromUri(Uri, Bundle)}.
*/
public static final int COMMAND_CODE_SESSION_PREPARE_FROM_URI = 26;
/**
* Command code for {@link MediaController2#prepareFromSearch(String, Bundle)}.
*/
public static final int COMMAND_CODE_SESSION_PREPARE_FROM_SEARCH = 27;
/**
* Command code for {@link MediaController2#setRating(String, Rating2)}.
* @hide
*/
public static final int COMMAND_CODE_SESSION_SET_RATING = 28;
/**
* Command code for {@link android.media.MediaLibraryService2.MediaLibrarySession} specific
* functions. With or without this, a {@link MediaSession2} that isn't
* {@link android.media.MediaLibraryService2.MediaLibrarySession} would automatically reject
* the calls.
*
* @see android.media.MediaLibraryService2.MediaLibrarySession
* @see MediaBrowser2
* @hide
*/
// TODO(jaewan): Remove
public static final int COMMAND_CODE_BROWSER = 29;
// TODO(jaewan): Add javadoc
public static final int COMMAND_CODE_LIBRARY_GET_CHILDREN = 29;
public static final int COMMAND_CODE_LIBRARY_GET_ITEM = 30;
public static final int COMMAND_CODE_LIBRARY_GET_LIBRARY_ROOT = 31;
public static final int COMMAND_CODE_LIBRARY_GET_SEARCH_RESULT = 32;
public static final int COMMAND_CODE_LIBRARY_SEARCH = 33;
public static final int COMMAND_CODE_LIBRARY_SUBSCRIBE = 34;
public static final int COMMAND_CODE_LIBRARY_UNSUBSCRIBE = 35;
/**
* @hide
*/
@@ -428,155 +183,6 @@ public class MediaSession2 implements AutoCloseable {
@NonNull MediaItem2 item);
}
/**
* Define a command that a {@link MediaController2} can send to a {@link MediaSession2}.
* <p>
* If {@link #getCommandCode()} isn't {@link #COMMAND_CODE_CUSTOM}), it's predefined command.
* If {@link #getCommandCode()} is {@link #COMMAND_CODE_CUSTOM}), it's custom command and
* {@link #getCustomCommand()} shouldn't be {@code null}.
*/
public static final class Command {
private final CommandProvider mProvider;
public Command(int commandCode) {
mProvider = ApiLoader.getProvider().createMediaSession2Command(
this, commandCode, null, null);
}
public Command(@NonNull String action, @Nullable Bundle extras) {
if (action == null) {
throw new IllegalArgumentException("action shouldn't be null");
}
mProvider = ApiLoader.getProvider().createMediaSession2Command(
this, COMMAND_CODE_CUSTOM, action, extras);
}
/**
* @hide
*/
public CommandProvider getProvider() {
return mProvider;
}
public int getCommandCode() {
return mProvider.getCommandCode_impl();
}
public @Nullable String getCustomCommand() {
return mProvider.getCustomCommand_impl();
}
public @Nullable Bundle getExtras() {
return mProvider.getExtras_impl();
}
/**
* @return a new Bundle instance from the Command
* @hide
*/
public Bundle toBundle() {
return mProvider.toBundle_impl();
}
@Override
public boolean equals(Object obj) {
if (!(obj instanceof Command)) {
return false;
}
return mProvider.equals_impl(((Command) obj).mProvider);
}
@Override
public int hashCode() {
return mProvider.hashCode_impl();
}
/**
* @return a new Command instance from the Bundle
* @hide
*/
public static Command fromBundle(@NonNull Bundle command) {
return ApiLoader.getProvider().fromBundle_MediaSession2Command(command);
}
}
/**
* Represent set of {@link Command}.
*/
public static final class CommandGroup {
private final CommandGroupProvider mProvider;
public CommandGroup() {
mProvider = ApiLoader.getProvider().createMediaSession2CommandGroup(this, null);
}
public CommandGroup(@Nullable CommandGroup others) {
mProvider = ApiLoader.getProvider().createMediaSession2CommandGroup(this, others);
}
/**
* @hide
*/
public CommandGroup(@NonNull CommandGroupProvider provider) {
mProvider = provider;
}
public void addCommand(@NonNull Command command) {
mProvider.addCommand_impl(command);
}
public void addCommand(int commandCode) {
// TODO(jaewna): Implement
}
public void addAllPredefinedCommands() {
mProvider.addAllPredefinedCommands_impl();
}
public void removeCommand(@NonNull Command command) {
mProvider.removeCommand_impl(command);
}
public void removeCommand(int commandCode) {
// TODO(jaewan): Implement.
}
public boolean hasCommand(@NonNull Command command) {
return mProvider.hasCommand_impl(command);
}
public boolean hasCommand(int code) {
return mProvider.hasCommand_impl(code);
}
public @NonNull Set<Command> getCommands() {
return mProvider.getCommands_impl();
}
/**
* @hide
*/
public @NonNull CommandGroupProvider getProvider() {
return mProvider;
}
/**
* @return new bundle from the CommandGroup
* @hide
*/
public @NonNull Bundle toBundle() {
return mProvider.toBundle_impl();
}
/**
* @return new instance of CommandGroup from the bundle
* @hide
*/
public static @Nullable CommandGroup fromBundle(Bundle commands) {
return ApiLoader.getProvider().fromBundle_MediaSession2CommandGroup(commands);
}
}
/**
* Callback to be called for all incoming commands from {@link MediaController2}s.
* <p>
@@ -597,9 +203,9 @@ public class MediaSession2 implements AutoCloseable {
* @param controller controller information.
* @return allowed commands. Can be {@code null} to reject connection.
*/
public @Nullable CommandGroup onConnect(@NonNull MediaSession2 session,
public @Nullable SessionCommandGroup2 onConnect(@NonNull MediaSession2 session,
@NonNull ControllerInfo controller) {
CommandGroup commands = new CommandGroup();
SessionCommandGroup2 commands = new SessionCommandGroup2();
commands.addAllPredefinedCommands();
return commands;
}
@@ -621,23 +227,23 @@ public class MediaSession2 implements AutoCloseable {
* @param controller controller information.
* @param command a command. This method will be called for every single command.
* @return {@code true} if you want to accept incoming command. {@code false} otherwise.
* @see #COMMAND_CODE_PLAYBACK_PLAY
* @see #COMMAND_CODE_PLAYBACK_PAUSE
* @see #COMMAND_CODE_PLAYBACK_STOP
* @see #COMMAND_CODE_PLAYLIST_SKIP_NEXT_ITEM
* @see #COMMAND_CODE_PLAYLIST_SKIP_PREV_ITEM
* @see #COMMAND_CODE_PLAYBACK_PREPARE
* @see #COMMAND_CODE_SESSION_FAST_FORWARD
* @see #COMMAND_CODE_SESSION_REWIND
* @see #COMMAND_CODE_PLAYBACK_SEEK_TO
* @see #COMMAND_CODE_PLAYLIST_SKIP_TO_PLAYLIST_ITEM
* @see #COMMAND_CODE_PLAYLIST_ADD_ITEM
* @see #COMMAND_CODE_PLAYLIST_REMOVE_ITEM
* @see #COMMAND_CODE_PLAYLIST_GET_LIST
* @see #COMMAND_CODE_PLAYBACK_SET_VOLUME
* @see SessionCommand2#COMMAND_CODE_PLAYBACK_PLAY
* @see SessionCommand2#COMMAND_CODE_PLAYBACK_PAUSE
* @see SessionCommand2#COMMAND_CODE_PLAYBACK_STOP
* @see SessionCommand2#COMMAND_CODE_PLAYLIST_SKIP_NEXT_ITEM
* @see SessionCommand2#COMMAND_CODE_PLAYLIST_SKIP_PREV_ITEM
* @see SessionCommand2#COMMAND_CODE_PLAYBACK_PREPARE
* @see SessionCommand2#COMMAND_CODE_SESSION_FAST_FORWARD
* @see SessionCommand2#COMMAND_CODE_SESSION_REWIND
* @see SessionCommand2#COMMAND_CODE_PLAYBACK_SEEK_TO
* @see SessionCommand2#COMMAND_CODE_PLAYLIST_SKIP_TO_PLAYLIST_ITEM
* @see SessionCommand2#COMMAND_CODE_PLAYLIST_ADD_ITEM
* @see SessionCommand2#COMMAND_CODE_PLAYLIST_REMOVE_ITEM
* @see SessionCommand2#COMMAND_CODE_PLAYLIST_GET_LIST
* @see SessionCommand2#COMMAND_CODE_SET_VOLUME
*/
public boolean onCommandRequest(@NonNull MediaSession2 session,
@NonNull ControllerInfo controller, @NonNull Command command) {
@NonNull ControllerInfo controller, @NonNull SessionCommand2 command) {
return true;
}
@@ -660,7 +266,7 @@ public class MediaSession2 implements AutoCloseable {
/**
* Called when a controller sent a custom command through
* {@link MediaController2#sendCustomCommand(Command, Bundle, ResultReceiver)}.
* {@link MediaController2#sendCustomCommand(SessionCommand2, Bundle, ResultReceiver)}.
*
* @param session the session for this event
* @param controller controller information
@@ -669,7 +275,7 @@ public class MediaSession2 implements AutoCloseable {
* @param cb optional result receiver
*/
public void onCustomCommand(@NonNull MediaSession2 session,
@NonNull ControllerInfo controller, @NonNull Command customCommand,
@NonNull ControllerInfo controller, @NonNull SessionCommand2 customCommand,
@Nullable Bundle args, @Nullable ResultReceiver cb) { }
/**
@@ -680,7 +286,7 @@ public class MediaSession2 implements AutoCloseable {
* @param controller controller information
* @param mediaId media id
* @param extras optional extra bundle
* @see #COMMAND_CODE_SESSION_PLAY_FROM_MEDIA_ID
* @see SessionCommand2#COMMAND_CODE_SESSION_PLAY_FROM_MEDIA_ID
*/
public void onPlayFromMediaId(@NonNull MediaSession2 session,
@NonNull ControllerInfo controller, @NonNull String mediaId,
@@ -697,7 +303,7 @@ public class MediaSession2 implements AutoCloseable {
* @param controller controller information
* @param query query string. Can be empty to indicate any suggested media
* @param extras optional extra bundle
* @see #COMMAND_CODE_SESSION_PLAY_FROM_SEARCH
* @see SessionCommand2#COMMAND_CODE_SESSION_PLAY_FROM_SEARCH
*/
public void onPlayFromSearch(@NonNull MediaSession2 session,
@NonNull ControllerInfo controller, @NonNull String query,
@@ -711,7 +317,7 @@ public class MediaSession2 implements AutoCloseable {
* @param controller controller information
* @param uri uri
* @param extras optional extra bundle
* @see #COMMAND_CODE_SESSION_PLAY_FROM_URI
* @see SessionCommand2#COMMAND_CODE_SESSION_PLAY_FROM_URI
*/
public void onPlayFromUri(@NonNull MediaSession2 session,
@NonNull ControllerInfo controller, @NonNull Uri uri,
@@ -735,7 +341,7 @@ public class MediaSession2 implements AutoCloseable {
* @param controller controller information
* @param mediaId media id to prepare
* @param extras optional extra bundle
* @see #COMMAND_CODE_SESSION_PREPARE_FROM_MEDIA_ID
* @see SessionCommand2#COMMAND_CODE_SESSION_PREPARE_FROM_MEDIA_ID
*/
public void onPrepareFromMediaId(@NonNull MediaSession2 session,
@NonNull ControllerInfo controller, @NonNull String mediaId,
@@ -759,7 +365,7 @@ public class MediaSession2 implements AutoCloseable {
* @param controller controller information
* @param query query string. Can be empty to indicate any suggested media
* @param extras optional extra bundle
* @see #COMMAND_CODE_SESSION_PREPARE_FROM_SEARCH
* @see SessionCommand2#COMMAND_CODE_SESSION_PREPARE_FROM_SEARCH
*/
public void onPrepareFromSearch(@NonNull MediaSession2 session,
@NonNull ControllerInfo controller, @NonNull String query,
@@ -783,7 +389,7 @@ public class MediaSession2 implements AutoCloseable {
* @param controller controller information
* @param uri uri
* @param extras optional extra bundle
* @see #COMMAND_CODE_SESSION_PREPARE_FROM_URI
* @see SessionCommand2#COMMAND_CODE_SESSION_PREPARE_FROM_URI
*/
public void onPrepareFromUri(@NonNull MediaSession2 session,
@NonNull ControllerInfo controller, @NonNull Uri uri, @Nullable Bundle extras) { }
@@ -1142,7 +748,7 @@ public class MediaSession2 implements AutoCloseable {
}
/**
* Button for a {@link Command} that will be shown by the controller.
* Button for a {@link SessionCommand2} that will be shown by the controller.
* <p>
* It's up to the controller's decision to respect or ignore this customization request.
*/
@@ -1162,7 +768,8 @@ public class MediaSession2 implements AutoCloseable {
*
* @return command or {@code null}
*/
public @Nullable Command getCommand() {
public @Nullable
SessionCommand2 getCommand() {
return mProvider.getCommand_impl();
}
@@ -1221,7 +828,7 @@ public class MediaSession2 implements AutoCloseable {
mProvider = ApiLoader.getProvider().createMediaSession2CommandButtonBuilder(this);
}
public @NonNull Builder setCommand(@Nullable Command command) {
public @NonNull Builder setCommand(@Nullable SessionCommand2 command) {
return mProvider.setCommand_impl(command);
}
@@ -1358,7 +965,8 @@ public class MediaSession2 implements AutoCloseable {
* expanded row: layout[5] layout[6] layout[7] layout[8] layout[9]
* main row: layout[3] layout[1] layout[0] layout[2] layout[4]
* <p>
* This API can be called in the {@link SessionCallback#onConnect(MediaSession2, ControllerInfo)}.
* This API can be called in the {@link SessionCallback#onConnect(
* MediaSession2, ControllerInfo)}.
*
* @param controller controller to specify layout.
* @param layout ordered list of layout.
@@ -1375,7 +983,7 @@ public class MediaSession2 implements AutoCloseable {
* @param commands new allowed commands
*/
public void setAllowedCommands(@NonNull ControllerInfo controller,
@NonNull CommandGroup commands) {
@NonNull SessionCommandGroup2 commands) {
mProvider.setAllowedCommands_impl(controller, commands);
}
@@ -1385,7 +993,7 @@ public class MediaSession2 implements AutoCloseable {
* @param command a command
* @param args optional argument
*/
public void sendCustomCommand(@NonNull Command command, @Nullable Bundle args) {
public void sendCustomCommand(@NonNull SessionCommand2 command, @Nullable Bundle args) {
mProvider.sendCustomCommand_impl(command, args);
}
@@ -1396,8 +1004,9 @@ public class MediaSession2 implements AutoCloseable {
* @param args optional argument
* @param receiver result receiver for the session
*/
public void sendCustomCommand(@NonNull ControllerInfo controller, @NonNull Command command,
@Nullable Bundle args, @Nullable ResultReceiver receiver) {
public void sendCustomCommand(@NonNull ControllerInfo controller,
@NonNull SessionCommand2 command, @Nullable Bundle args,
@Nullable ResultReceiver receiver) {
// Equivalent to the MediaController.sendCustomCommand(Action action, ResultReceiver r);
mProvider.sendCustomCommand_impl(controller, command, args, receiver);
}
@@ -1543,7 +1152,8 @@ public class MediaSession2 implements AutoCloseable {
* <li>{@link MediaItem2} specified by {@link #setPlaylist(List, MediaMetadata2)} doesn't
* have {@link DataSourceDesc}</li>
* <li>{@link MediaController2#addPlaylistItem(int, MediaItem2)} is called and accepted
* by {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)}.
* by {@link SessionCallback#onCommandRequest(
* MediaSession2, ControllerInfo, SessionCommand2)}.
* In that case, an item would be added automatically without the data source.</li>
* </ul>
* <p>
@@ -1555,9 +1165,9 @@ public class MediaSession2 implements AutoCloseable {
* @param helper a data source missing helper.
* @throws IllegalStateException when the helper is set when the playlist agent is set
* @see #setPlaylist(List, MediaMetadata2)
* @see SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, Command)
* @see #COMMAND_CODE_PLAYLIST_ADD_ITEM
* @see #COMMAND_CODE_PLAYLIST_REPLACE_ITEM
* @see SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, SessionCommand2)
* @see SessionCommand2#COMMAND_CODE_PLAYLIST_ADD_ITEM
* @see SessionCommand2#COMMAND_CODE_PLAYLIST_REPLACE_ITEM
*/
public void setOnDataSourceMissingHelper(@NonNull OnDataSourceMissingHelper helper) {
mProvider.setOnDataSourceMissingHelper_impl(helper);

View File

@@ -0,0 +1,336 @@
/*
* Copyright 2018 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package android.media;
import android.annotation.NonNull;
import android.annotation.Nullable;
import android.content.Context;
import android.media.update.ApiLoader;
import android.media.update.MediaSession2Provider;
import android.media.MediaSession2.ControllerInfo;
import android.media.MediaSession2.SessionCallback;
import android.net.Uri;
import android.os.Bundle;
import java.util.List;
/**
* @hide
* Define a command that a {@link MediaController2} can send to a {@link MediaSession2}.
* <p>
* If {@link #getCommandCode()} isn't {@link #COMMAND_CODE_CUSTOM}), it's predefined command.
* If {@link #getCommandCode()} is {@link #COMMAND_CODE_CUSTOM}), it's custom command and
* {@link #getCustomCommand()} shouldn't be {@code null}.
*/
public final class SessionCommand2 {
/**
* Command code for the custom command which can be defined by string action in the
* {@link SessionCommand2}.
*/
public static final int COMMAND_CODE_CUSTOM = 0;
/**
* Command code for {@link MediaController2#play()}.
* <p>
* Command would be sent directly to the player if the session doesn't reject the request
* through the {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo,
* SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYBACK_PLAY = 1;
/**
* Command code for {@link MediaController2#pause()}.
* <p>
* Command would be sent directly to the player if the session doesn't reject the request
* through the {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo,
* SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYBACK_PAUSE = 2;
/**
* Command code for {@link MediaController2#stop()}.
* <p>
* Command would be sent directly to the player if the session doesn't reject the request
* through the {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo,
* SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYBACK_STOP = 3;
/**
* Command code for {@link MediaController2#skipToNextItem()}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the {@link SessionCallback#onCommandRequest(
* MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SKIP_NEXT_ITEM = 4;
/**
* Command code for {@link MediaController2#skipToPreviousItem()}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the {@link SessionCallback#onCommandRequest(
* MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SKIP_PREV_ITEM = 5;
/**
* Command code for {@link MediaController2#prepare()}.
* <p>
* Command would be sent directly to the player if the session doesn't reject the request
* through the {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo,
* SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYBACK_PREPARE = 6;
/**
* Command code for {@link MediaController2#fastForward()}.
*/
public static final int COMMAND_CODE_SESSION_FAST_FORWARD = 7;
/**
* Command code for {@link MediaController2#rewind()}.
*/
public static final int COMMAND_CODE_SESSION_REWIND = 8;
/**
* Command code for {@link MediaController2#seekTo(long)}.
* <p>
* Command would be sent directly to the player if the session doesn't reject the request
* through the {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo,
* SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYBACK_SEEK_TO = 9;
/**
* Command code for both {@link MediaController2#setVolumeTo(int, int)}.
* <p>
* Command would set the device volume or send to the volume provider directly if the session
* doesn't reject the request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_SET_VOLUME = 10;
/**
* Command code for both {@link MediaController2#adjustVolume(int, int)}.
* <p>
* Command would adjust the device volume or send to the volume provider directly if the session
* doesn't reject the request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_ADJUST_VOLUME = 11;
/**
* Command code for {@link MediaController2#skipToPlaylistItem(MediaItem2)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SKIP_TO_PLAYLIST_ITEM = 12;
/**
* Command code for {@link MediaController2#setShuffleMode(int)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SET_SHUFFLE_MODE = 13;
/**
* Command code for {@link MediaController2#setRepeatMode(int)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SET_REPEAT_MODE = 14;
/**
* Command code for {@link MediaController2#addPlaylistItem(int, MediaItem2)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYLIST_ADD_ITEM = 15;
/**
* Command code for {@link MediaController2#addPlaylistItem(int, MediaItem2)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYLIST_REMOVE_ITEM = 16;
/**
* Command code for {@link MediaController2#replacePlaylistItem(int, MediaItem2)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYLIST_REPLACE_ITEM = 17;
/**
* Command code for {@link MediaController2#getPlaylist()}. This will expose metadata
* information to the controller.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYLIST_GET_LIST = 18;
/**
* Command code for {@link MediaController2#setPlaylist(List, MediaMetadata2)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SET_LIST = 19;
/**
* Command code for {@link MediaController2#getPlaylistMetadata()}. This will expose
* metadata information to the controller.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYLIST_GET_LIST_METADATA = 20;
/**
* Command code for {@link MediaController2#updatePlaylistMetadata(MediaMetadata2)}.
* <p>
* Command would be sent directly to the playlist agent if the session doesn't reject the
* request through the
* {@link SessionCallback#onCommandRequest(MediaSession2, ControllerInfo, SessionCommand2)}.
*/
public static final int COMMAND_CODE_PLAYLIST_SET_LIST_METADATA = 21;
/**
* Command code for {@link MediaController2#playFromMediaId(String, Bundle)}.
*/
public static final int COMMAND_CODE_SESSION_PLAY_FROM_MEDIA_ID = 22;
/**
* Command code for {@link MediaController2#playFromUri(Uri, Bundle)}.
*/
public static final int COMMAND_CODE_SESSION_PLAY_FROM_URI = 23;
/**
* Command code for {@link MediaController2#playFromSearch(String, Bundle)}.
*/
public static final int COMMAND_CODE_SESSION_PLAY_FROM_SEARCH = 24;
/**
* Command code for {@link MediaController2#prepareFromMediaId(String, Bundle)}.
*/
public static final int COMMAND_CODE_SESSION_PREPARE_FROM_MEDIA_ID = 25;
/**
* Command code for {@link MediaController2#prepareFromUri(Uri, Bundle)}.
*/
public static final int COMMAND_CODE_SESSION_PREPARE_FROM_URI = 26;
/**
* Command code for {@link MediaController2#prepareFromSearch(String, Bundle)}.
*/
public static final int COMMAND_CODE_SESSION_PREPARE_FROM_SEARCH = 27;
/**
* Command code for {@link MediaController2#setRating(String, Rating2)}.
*/
public static final int COMMAND_CODE_SESSION_SET_RATING = 28;
// TODO(jaewan): Add javadoc
public static final int COMMAND_CODE_LIBRARY_GET_CHILDREN = 29;
public static final int COMMAND_CODE_LIBRARY_GET_ITEM = 30;
public static final int COMMAND_CODE_LIBRARY_GET_LIBRARY_ROOT = 31;
public static final int COMMAND_CODE_LIBRARY_GET_SEARCH_RESULT = 32;
public static final int COMMAND_CODE_LIBRARY_SEARCH = 33;
public static final int COMMAND_CODE_LIBRARY_SUBSCRIBE = 34;
public static final int COMMAND_CODE_LIBRARY_UNSUBSCRIBE = 35;
// TODO(jaewan): Rename and move provider
private final MediaSession2Provider.CommandProvider mProvider;
public SessionCommand2(int commandCode) {
mProvider = ApiLoader.getProvider().createMediaSession2Command(
this, commandCode, null, null);
}
public SessionCommand2(@NonNull String action, @Nullable Bundle extras) {
if (action == null) {
throw new IllegalArgumentException("action shouldn't be null");
}
mProvider = ApiLoader.getProvider().createMediaSession2Command(
this, COMMAND_CODE_CUSTOM, action, extras);
}
/**
* @hide
*/
public MediaSession2Provider.CommandProvider getProvider() {
return mProvider;
}
public int getCommandCode() {
return mProvider.getCommandCode_impl();
}
public @Nullable String getCustomCommand() {
return mProvider.getCustomCommand_impl();
}
public @Nullable Bundle getExtras() {
return mProvider.getExtras_impl();
}
/**
* @return a new Bundle instance from the Command
* @hide
*/
public Bundle toBundle() {
return mProvider.toBundle_impl();
}
@Override
public boolean equals(Object obj) {
if (!(obj instanceof SessionCommand2)) {
return false;
}
return mProvider.equals_impl(((SessionCommand2) obj).mProvider);
}
@Override
public int hashCode() {
return mProvider.hashCode_impl();
}
/**
* @return a new Command instance from the Bundle
* @hide
*/
public static SessionCommand2 fromBundle(@NonNull Bundle command) {
return ApiLoader.getProvider().fromBundle_MediaSession2Command(command);
}
}

View File

@@ -0,0 +1,106 @@
/*
* Copyright 2018 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package android.media;
import android.annotation.NonNull;
import android.annotation.Nullable;
import android.content.Context;
import android.media.update.ApiLoader;
import android.media.update.MediaSession2Provider;
import android.os.Bundle;
import java.util.Set;
/**
* @hide
* Represent set of {@link SessionCommand2}.
*/
public final class SessionCommandGroup2 {
// TODO(jaewan): Rename and move provider
private final MediaSession2Provider.CommandGroupProvider mProvider;
public SessionCommandGroup2() {
mProvider = ApiLoader.getProvider().createMediaSession2CommandGroup(this, null);
}
public SessionCommandGroup2(@Nullable SessionCommandGroup2 others) {
mProvider = ApiLoader.getProvider().createMediaSession2CommandGroup(this, others);
}
/**
* @hide
*/
public SessionCommandGroup2(@NonNull MediaSession2Provider.CommandGroupProvider provider) {
mProvider = provider;
}
public void addCommand(@NonNull SessionCommand2 command) {
mProvider.addCommand_impl(command);
}
public void addCommand(int commandCode) {
// TODO(jaewna): Implement
}
public void addAllPredefinedCommands() {
mProvider.addAllPredefinedCommands_impl();
}
public void removeCommand(@NonNull SessionCommand2 command) {
mProvider.removeCommand_impl(command);
}
public void removeCommand(int commandCode) {
// TODO(jaewan): Implement.
}
public boolean hasCommand(@NonNull SessionCommand2 command) {
return mProvider.hasCommand_impl(command);
}
public boolean hasCommand(int code) {
return mProvider.hasCommand_impl(code);
}
public @NonNull
Set<SessionCommand2> getCommands() {
return mProvider.getCommands_impl();
}
/**
* @hide
*/
public @NonNull MediaSession2Provider.CommandGroupProvider getProvider() {
return mProvider;
}
/**
* @return new bundle from the CommandGroup
* @hide
*/
public @NonNull Bundle toBundle() {
return mProvider.toBundle_impl();
}
/**
* @return new instance of CommandGroup from the bundle
* @hide
*/
public static @Nullable SessionCommandGroup2 fromBundle(Bundle commands) {
return ApiLoader.getProvider().fromBundle_MediaSession2CommandGroup(commands);
}
}

View File

@@ -21,7 +21,7 @@ import android.media.AudioAttributes;
import android.media.MediaController2.PlaybackInfo;
import android.media.MediaItem2;
import android.media.MediaMetadata2;
import android.media.MediaSession2.Command;
import android.media.SessionCommand2;
import android.media.Rating2;
import android.media.SessionToken2;
import android.net.Uri;
@@ -56,7 +56,7 @@ public interface MediaController2Provider extends TransportControlProvider {
void rewind_impl();
void setRating_impl(String mediaId, Rating2 rating);
void sendCustomCommand_impl(Command command, Bundle args, ResultReceiver cb);
void sendCustomCommand_impl(SessionCommand2 command, Bundle args, ResultReceiver cb);
List<MediaItem2> getPlaylist_impl();
void setPlaylist_impl(List<MediaItem2> list, MediaMetadata2 metadata);
MediaMetadata2 getPlaylistMetadata_impl();

View File

@@ -23,10 +23,10 @@ import android.media.MediaMetadata2;
import android.media.MediaPlayerBase;
import android.media.MediaPlaylistAgent;
import android.media.MediaSession2;
import android.media.MediaSession2.Command;
import android.media.SessionCommand2;
import android.media.MediaSession2.CommandButton;
import android.media.MediaSession2.CommandButton.Builder;
import android.media.MediaSession2.CommandGroup;
import android.media.SessionCommandGroup2;
import android.media.MediaSession2.ControllerInfo;
import android.media.MediaSession2.OnDataSourceMissingHelper;
import android.media.MediaSession2.SessionCallback;
@@ -55,10 +55,10 @@ public interface MediaSession2Provider extends TransportControlProvider {
List<ControllerInfo> getConnectedControllers_impl();
void setCustomLayout_impl(ControllerInfo controller, List<CommandButton> layout);
void setAudioFocusRequest_impl(AudioFocusRequest afr);
void setAllowedCommands_impl(ControllerInfo controller, CommandGroup commands);
void sendCustomCommand_impl(ControllerInfo controller, Command command, Bundle args,
void setAllowedCommands_impl(ControllerInfo controller, SessionCommandGroup2 commands);
void sendCustomCommand_impl(ControllerInfo controller, SessionCommand2 command, Bundle args,
ResultReceiver receiver);
void sendCustomCommand_impl(Command command, Bundle args);
void sendCustomCommand_impl(SessionCommand2 command, Bundle args);
void addPlaylistItem_impl(int index, MediaItem2 item);
void removePlaylistItem_impl(MediaItem2 item);
void replacePlaylistItem_impl(int index, MediaItem2 item);
@@ -72,6 +72,7 @@ public interface MediaSession2Provider extends TransportControlProvider {
void setOnDataSourceMissingHelper_impl(OnDataSourceMissingHelper helper);
void clearOnDataSourceMissingHelper_impl();
// TODO(jaewan): Rename and move provider
interface CommandProvider {
int getCommandCode_impl();
String getCustomCommand_impl();
@@ -82,25 +83,26 @@ public interface MediaSession2Provider extends TransportControlProvider {
int hashCode_impl();
}
// TODO(jaewan): Rename and move provider
interface CommandGroupProvider {
void addCommand_impl(Command command);
void addCommand_impl(SessionCommand2 command);
void addAllPredefinedCommands_impl();
void removeCommand_impl(Command command);
boolean hasCommand_impl(Command command);
void removeCommand_impl(SessionCommand2 command);
boolean hasCommand_impl(SessionCommand2 command);
boolean hasCommand_impl(int code);
Set<Command> getCommands_impl();
Set<SessionCommand2> getCommands_impl();
Bundle toBundle_impl();
}
interface CommandButtonProvider {
Command getCommand_impl();
SessionCommand2 getCommand_impl();
int getIconResId_impl();
String getDisplayName_impl();
Bundle getExtras_impl();
boolean isEnabled_impl();
interface BuilderProvider {
Builder setCommand_impl(Command command);
Builder setCommand_impl(SessionCommand2 command);
Builder setIconResId_impl(int resId);
Builder setDisplayName_impl(String displayName);
Builder setEnabled_impl(boolean enabled);

View File

@@ -35,6 +35,8 @@ import android.media.MediaSession2.SessionCallback;
import android.media.MediaSessionService2;
import android.media.MediaSessionService2.MediaNotification;
import android.media.Rating2;
import android.media.SessionCommand2;
import android.media.SessionCommandGroup2;
import android.media.SessionToken2;
import android.media.VolumeProvider2;
import android.media.update.MediaLibraryService2Provider.LibraryRootProvider;
@@ -67,12 +69,12 @@ public interface StaticProvider {
ViewGroupProvider superProvider, ViewGroupProvider privateProvider,
@Nullable AttributeSet attrs, int defStyleAttr, int defStyleRes);
CommandProvider createMediaSession2Command(MediaSession2.Command instance,
CommandProvider createMediaSession2Command(SessionCommand2 instance,
int commandCode, String action, Bundle extra);
MediaSession2.Command fromBundle_MediaSession2Command(Bundle bundle);
CommandGroupProvider createMediaSession2CommandGroup(
MediaSession2.CommandGroup instance, MediaSession2.CommandGroup others);
MediaSession2.CommandGroup fromBundle_MediaSession2CommandGroup(Bundle bundle);
SessionCommand2 fromBundle_MediaSession2Command(Bundle bundle);
CommandGroupProvider createMediaSession2CommandGroup(SessionCommandGroup2 instance,
SessionCommandGroup2 others);
SessionCommandGroup2 fromBundle_MediaSession2CommandGroup(Bundle bundle);
ControllerInfoProvider createMediaSession2ControllerInfo(Context context,
MediaSession2.ControllerInfo instance, int uid, int pid,
String packageName, IInterface callback);