Many usages are needed to support other deprecations and some
can be replaced by the recommended direct alternative.
Also replace links to deprecated/redirected dev site
PiperOrigin-RevId: 601795998
The default notification provider was still using the legacy
compat MediaStyle instead of our own Media3 one. They are fully
equivalent in their implementation and API and can be swapped out
easily.
PiperOrigin-RevId: 600797920
Due to poor isolation between the session tests, in particular the
static state in `MediaSession.SESSION_ID_TO_SESSION_MAP`, an unreleased
session at the end of one test can cause subsequent tests to fail with
obscure errors like `Session ID must be unique`.
#minor-release
PiperOrigin-RevId: 600737697
Some player method calls sent from MediaControllers accept int
or float values with a very clear API contract that disallows
some values. Filtering by these values early avoids calling a
Player implementation with invalid values.
PiperOrigin-RevId: 600413993
Moves setting bitmapFactory options from BitmapLoader to DatasourceBitmapLoader
BitmapLoader is a general interface for bitmap loading that could use loading implementations other that BitmapFactory, with the rise of Glide being a loader of choice. It's best to correct this interface so that it remains generic
We can't deprecate easily because the other loadBitmap method in that case has a default implementation that relies on the first one, so the change is still breaking. BitmapLoader is public api in common, but it's @UnstableAPI and hasn't been around for very long (be38670391 added it), so it seems this is the best way forward.
PiperOrigin-RevId: 597897098
When the media notification controller is requested for a session
with `getConnectedControllerForSession` and the `Future` is not null
but not yet completed, the `Future` was returned either way. This was
reported as creating a race condition between the notification
being requested for update the very first time, and the media
notification controller having completed connecting to the session.
Returning null from `getConnectedControllerForSession` when the
`Future` is available but not yet done fixes the problem. This is
safe because for the case when a notification update is dropped,
the media notification controller will trigger the update as soon
as the connection completes.
Issue: androidx/media#917
#minor-release
PiperOrigin-RevId: 595699929
When the 'when' timer of the notification is disabled
`DefaultMediaNotificationProvider` may set `C.TIME_UNSET`
as the time. Users reported problems on some devices with
this and the docs ask for an event time that probably
shouldn't be a negative number.
This change sets `0L` instead of `C.TIME_UNSET` when the
timer is disabled.
Issue: androidx/media#903
#minor-release
PiperOrigin-RevId: 594451074
When broadcasting a notifyChildrenChanged event, the task for legacy
controllers was sent to the broadcasting callback. This would
technically work, but because the subscription list is maintained
with specific controllers, the broadcast controller isn't subscribed
and hence the call wasn't executed.
This change calls the overloaded method for a specific controller
for each connected controller. Making sure (only) subscribed
controllers are notified.
Issue: androidx/media#644
PiperOrigin-RevId: 590904037
An app that uses the `MediaSession` without a `MediaSessionService` may
want to connect a media notification controller on it own. To avoid apps
using a string literal, the key should be exposed as public.
PiperOrigin-RevId: 589875603
This change adds `MediaController.getSessionExtras()` through
which a controller can access the session extras.
The session extras can be set for the entire session when
building the session. This can be overridden for specific
controllers in `MediaSession.Callback.onConnect`.
PiperOrigin-RevId: 584430419
Both interfaces are not really needed as the methods can be called
on the respective classes directly. This also avoid error-prone
situations where classes define to/fromBundle methods with parameters
that should be used instead of the parameter-less version.
Also deprecate all existing CREATOR static instances and make the
corresponding fromBundle method public where needed.
PiperOrigin-RevId: 579189766
BundleableUtil is the only class that really depends on the type
inheritence from Bundleable. However, it only needs this as a way
to define Function<T, Bundle> and Function<Bundle, T>, which could
just be passed in as parameters as it's already done for some of
these methods.
Also rename the class to BundleCollectionUtil accordingly.
PiperOrigin-RevId: 578791946
Android Studio removed some nested imports, but I think the extra
qualification at the usage site is actually mostly helpful, so I'm
leaving it as-is.
PiperOrigin-RevId: 578518880
The toBundle method should only be used for remote processes,
because there is a separate method for in-process bundling.
Renaming the method makes this more explicit and less error-prone.
PiperOrigin-RevId: 578456532
This change moves the handling of any media button event into
`MediaSessionImpl.onMediaButtonEvent(intent)`. This includes
the double click handling from `MediaSessionLegacyStub`.
The advantage is that everything is in one place which allows
to offer `MediaSession.Callback.onMediaButtonEvent` with which
an app can override the default implementation and handle media
buttons in a custom way.
Media button events can originate from various places:
- Delivered to `MediaSessionService.onStartCommand(Intent)`
- A `PendingIntent` from the notification below API 33
- An `Intent` sent to the `MediaButtonReceiver` by the system dispatched
to the service
- Delivered to `MediaSessionCompat.Callback.onMediaButtonEvent(Intent)`
implemented by `MediaSessionLegacyStub` during the session is active
- Bluetooth (headset/remote control)
- Apps/system using `AudioManager.dispatchKeyEvent(KeyEvent)`
- Apps/system using `MediaControllerCompat.dispatchKeyEvent(keyEvent)`
Issue: androidx/media#12
Issue: androidx/media#159
Issue: androidx/media#216
Issue: androidx/media#249
#minor-release
PiperOrigin-RevId: 575231251
Player methods shouldn't be called if they are not available and the
entry point to the playback resumption flow only checks
COMMAND_PLAY_PAUSE.
#minor-release
PiperOrigin-RevId: 574834148
If an app rejects the connection of the internal media notification manager
the session should behave like without the the media notification controller.
The legacy System UI controller should not be hidden or even rejected to
connect in such a case.
#minor-release
PiperOrigin-RevId: 574807901
This replaces the SimpleBitmapLoader that can now be deprecated
as it's fully unused and doesn't provide any additional functionality.
#minor-release
PiperOrigin-RevId: 574454636
Media button event coming from the `MediaSessionService` are delegated
to the `MediaSessionImpl` and then sent to the session by using the
`MediaSessionStub` directly instead of using the `MediaController`
API.
Splitting the `MediaController.Listener` and `Player.Listener` in
`MediaNotificationManager` got reverted, and both listener are set to the
controller as before. This reverts the change that introduced a
different timing behaviour. It still holds, that a listener
registered on a `MediaController` that calls a method like `play()` is
called immediately and before the call has arrived at the player. This
change works around this behaviour from the library side by calling
`MediaSessionStub` directly with a `ControllerInfo`.
#minor-release
PiperOrigin-RevId: 573918850
Android Auto shows a queue button when the queue is not empty.
Apps were able to remove this queue button with the legacy API
by not setting the queue of the session.
After this change, removing `COMMAND_GET_TIMELINE` from the commands
of the media notification controller or the session player sets the
queue in the platform session to null.
#minor-release
Issue: androidx/media#339
PiperOrigin-RevId: 573813558
PlayerInfo bundling is costly and we can add a shortcut for
in-process binder calls where we store the direct object
reference in a live Binder object that can be written to the
Bundle instead of the individual data fields.
#minor-release
PiperOrigin-RevId: 572816784
A few methods in PlayerInfo and related classes combine filtering
information with bundling in one method. This makes it impossible
to use just the filtering for example and it's also easier to reason
about than two dedicated methods. This change splits these methods
into two parts accordingly.
PiperOrigin-RevId: 572592458
When the controller of the `MediaNotificationManager` is disconnected,
the session is removed from the service without checking whether the
session hasn't already been removed. This caused flakiness in `MediaSessionServiceTest.addSession()`.
Because there is a public API `MediaSessionService.removeSession()`,
the controller can't make an assumption whether the session is still
contained in the service when being disconnected.
#minor-release
PiperOrigin-RevId: 572568350
Interrupting the main thread in particular may be dangerous
as the flag is not cleared after handling the current message.
#minor-release
PiperOrigin-RevId: 572259422
Future.isDone and getDone doesn't imply the Future was successful
and it may have been cancelled or failed.
In case where we handle failure, we should also handle cancellation
to avoid CancellationException to bubble up unchecked.
In demo app code where we use isDone for field initialization, we
want to crash in the failure case (usually security exception where
the connection is disallowed), but we want to gracefully handle
cancellation. Cancellation of these variables usually happens in
Activity.onDestroy/onStop, but methods may be called after this point.
#minor-release
PiperOrigin-RevId: 572178018
The library already maintains the subscribed controllers internally. This
change adds `MediaLibrarySession.getSubscribedControllers(mediaId)` to
access subscribed controllers for a given media ID.
To accept a subscription, `MediaLibraryService.Callback.onSubscribe` is
required to return `RESULT_SUCCESS`. So far, this isn't the case for the
default implementation of the library.
This change implements `Callback.onSubscribe` to conditionally
provide `RESULT_SUCCESS`. The default calls `Callback.onGetItem(mediaId)` to
assess the availability of the media item. If the app retruns `RESULT_SUCCESS`
with a browsable item, the subscription is accepted. If receiving a valid item
fails, the subscription is rejected.
Issue: androidx/media#561
PiperOrigin-RevId: 568925079