Compare commits

...

2958 commits

Author SHA1 Message Date
shahddaghash
76088cd6af Bump Media3 version to 1.5.1
PiperOrigin-RevId: 707576152
(cherry picked from commit c3b58f2434)
2024-12-18 09:26:54 -08:00
shahddaghash
7ae9ddf166 Update release notes for Media3 1.5.1 release
PiperOrigin-RevId: 707558817
(cherry picked from commit 896bd0d330)
2024-12-19 11:21:58 +00:00
tonihei
e4e59cd929 Switch default of async crypto mode to disabled
There are reproducible issues with codec timeouts when using
this API, so we disable it entirely until we know more about
potential fixes and where they are available.

Issue: androidx/media#1641
PiperOrigin-RevId: 707025950
(cherry picked from commit 71f82df57f)
2024-12-17 03:22:51 -08:00
tonihei
508a4258a3 Switch play FGS exemption to use custom action instead of commands
Custom actions are more naturally associated with a user intent
than commands (that are meant to be used for automated inter-app
communication without user interaction).

PiperOrigin-RevId: 705797057
(cherry picked from commit 3bce3af1a3)
2024-12-13 01:41:20 -08:00
Googler
52f9761796 Don't check codec's profile for MV-HEVC video.
Currently as there is no formal support for MV-HEVC within Android framework, the profile is not correctly specified by the underlying codec; just assume the profile obtained from the MV-HEVC sample is supported.

PiperOrigin-RevId: 705164738
(cherry picked from commit 3936c27b6d)
2024-12-11 10:56:06 -08:00
ibaker
de91ebc6ae Add vorbis comment support for track/disc numbering fields, and genre
Only `TRACKNUMBER` and `GENRE` are listed here:
https://xiph.org/vorbis/doc/v-comment.html

The rest are derived from the example in Issue: androidx/media#1958.

It's possible that other formats exist in the wild:
https://hydrogenaud.io/index.php/topic,69292.msg613808.html#msg613808

Issue: androidx/media#1958
PiperOrigin-RevId: 704308788
(cherry picked from commit 12546070ee)
2024-12-09 09:09:53 -08:00
rohks
5d9badcb50 Fix ReplacingCuesResolver.discardCuesBeforeTimeUs to retain active cue
The method previously discarded the cue that was active at `timeUs`,
meaning it had started before but had not ended by `timeUs`.

Issue: androidx/media#1939

PiperOrigin-RevId: 702707611
(cherry picked from commit e927d7b986)
2024-12-04 06:48:43 -08:00
Copybara-Service
121b79ae96 Merge pull request #1943 from DolbyLaboratories:dlb/ac4-ajoc/dev
PiperOrigin-RevId: 702281314
(cherry picked from commit e4993779db)
2024-12-03 04:04:52 -08:00
ibaker
fa9689ef9a Clarify CommandButton javadoc around iconResId and ICON_UNDEFINED
PiperOrigin-RevId: 701898620
(cherry picked from commit 77d33645cc)
2024-12-02 02:56:34 -08:00
Copybara-Service
f5bbb39e90 Merge pull request #1823 from MGaetan89:remove_outdated_sdk_check
PiperOrigin-RevId: 700706152
(cherry picked from commit bff5523bb6)
2024-11-27 08:16:02 -08:00
ibaker
fd0c04b3a0 Recommend ForwardingSimpleBasePlayer in ForwardingPlayer javadoc
Also add an explicit warning about how fiddly `ForwardingPlayer` can be
to use correctly.

PiperOrigin-RevId: 700698032
(cherry picked from commit 60133b0c7e)
2024-11-27 07:40:13 -08:00
ibaker
8a1e6e59b0 Bump IMA dependency to 3.35.1
The previous version (3.33.0) is known to have some bugs, and the latest
version (3.36.0) is also known to be buggy.

PiperOrigin-RevId: 700657484
(cherry picked from commit 6cf3004d62)
2024-11-27 04:53:38 -08:00
ibaker
f91d5208b5 MP3: Use bytes field from VBRI frame instead of deriving from ToC
The previous code assumed that the `VBRI` Table of Contents (ToC)
covers all the MP3 data in the file. In a file with an invalid VBRI ToC
where this isn't the case, this results in playback silently stopping
mid-playback (and either advancing to the next item, or continuing to
count up the playback clock forever). This change considers the `bytes`
field to determine the end of the MP3 data, in addition to deriving it
from the ToC. If they disagree we log a warning and take the max value.
This is because we handle accidentally reading non-MP3 data at the end
(or hitting EoF) better than stopping reading valid MP3 data partway
through.

Issue: androidx/media#1904

#cherrypick

PiperOrigin-RevId: 700319250
(cherry picked from commit 46578ee0a6)
2024-12-18 14:19:41 +00:00
ibaker
989c8f4fdb MP3: Exclude VBRI frame from ToC position calculations
The current code assumes that the first Table of Contents segment
includes the `VBRI` frame, but I don't think this is correct and it
should only include real/audible MP3 ata - so this change updates the
logic to assume the first ToC segment starts at the frame **after** the
`VBRI` frame.

Issue: androidx/media#1904

PiperOrigin-RevId: 700269811
(cherry picked from commit f257e5511f)
2024-11-26 02:32:09 -08:00
ibaker
7abfa764e1 Add MP3 test asset with VBRI frame
This was hand-crafted with a 4-entry ToC by modifying
`bear-vbr-xing-header.mp3` in a hex editor.

The output difference from 117 samples to 116 samples is due to the
calculation in `VbriSeeker` assuming that the ToC includes the VBRI
frame itself, which I don't think is correct (fix is in a follow-up
change).

Issue: androidx/media#1904

#cherrypick

PiperOrigin-RevId: 700254516
(cherry picked from commit 3eb36d67bd)
2024-11-26 01:29:40 -08:00
ibaker
f34abbb29f Add pixel aspect ratio to Format.toLogString
#cherrypick

PiperOrigin-RevId: 698770714
(cherry picked from commit 827966b7a4)
2024-12-17 18:24:31 +00:00
michaelkatz
8d791fd836 Rollback of 854566dbfe
PiperOrigin-RevId: 698730105
(cherry picked from commit 5282fe3125)
2024-12-17 18:24:29 +00:00
sheenachhabra
05921514b7 Manage all color value conversions in ColorInfo class
This CL also aligns supported color space in `media3 common` and `media3 muxer`.

Earlier `muxer` would take even those values which are considered invalid
in `media3` in general.

Earlier muxer would throw if a given `color standard` is not recognized
but with the new change, it will rather put default `unspecified` value.

#cherrypick

PiperOrigin-RevId: 698683312
(cherry picked from commit 407bc4fec9)
2024-12-17 18:24:14 +00:00
Copybara-Service
6fbd3be9c5 Merge pull request #1277 from consp1racy:patch-1
PiperOrigin-RevId: 694095488
(cherry picked from commit 19d71266ec)
2024-12-17 18:24:14 +00:00
sheenachhabra
92166828e1 Make error messages unique in Boxes.java
PiperOrigin-RevId: 692920946
(cherry picked from commit c3e72a87e5)
2024-12-17 18:24:14 +00:00
sheenachhabra
0ceaa17bf5 Add an API to disable sample batching in Mp4Muxer
Mp4Muxer caches the samples and then writes them in batches.
The new API allows disabling the batching and writing sample
immediately.

PiperOrigin-RevId: 689352771
(cherry picked from commit f181855c5e)
2024-12-17 18:24:14 +00:00
Shahd AbuDaghash
df887a9422 Merge branch 'release' into release-1.5.0 2024-11-25 14:47:51 +00:00
shahddaghash
cc8439db93 Bump Media3 version to 1.5.0
PiperOrigin-RevId: 698761734
(cherry picked from commit 73c4bb6e1f)
2024-11-21 06:44:25 -08:00
shahddaghash
46a5f0f9b2 Merge release notes for media3 1.5.0 stable release
PiperOrigin-RevId: 698713460
(cherry picked from commit e5110e6442)
2024-11-21 15:35:44 +00:00
shahddaghash
f63069e266 Move misplaced release note to Unreleased changes section
PiperOrigin-RevId: 698426838
(cherry picked from commit cf4488aa1f)
2024-11-21 15:20:23 +00:00
ibaker
8bab42334e Bump media3 version to 1.5.0-rc02
PiperOrigin-RevId: 696912494
(cherry picked from commit cbb8e2f1e6)
2024-11-19 11:11:51 +00:00
tianyifeng
737fdd8693 Deflake the DefaultPreloadManagerTest
From [ the last change in `DefaultPreloadManagerTest`](2b54b1ebbe), the preloadManager began to use a separate `preloadThread` in `release_returnZeroCount_sourcesAndRendererCapabilitiesListReleased`, which unveils a bug in `PreloadMediaSource`. When `PreloadMediaSource.releasePreloadMediaSource` is called, `preloadHandler` will post a `Runnable` on the preload looper to release the internal resources. Before this `Runnable` is executed, it is possible that the [`stopPreloading`](https://github.com/androidx/media/blob/main/libraries/exoplayer/src/main/java/androidx/media3/exoplayer/source/preload/PreloadMediaSource.java#L442) method is executed just as the result of preloading has completed. This is expected to remove the posted `Runnable`s for further preloading, however, the posted `Runnable` for releasing will also be removed from the message queue.

Ideally we should use `postDelayed(runnable, token, delayMillis)` to post the runnables so that the token will be useful to identify which messages to remove in `removeCallbacksAndMessages(token)`, but that `postDelayed` method is only available from API 28. So in this change we are using a separate handler for releasing, and then the call of `preloadHandler.removeCallbacksAndMessages` won't impact the runnable for releasing.

#cherrypick

PiperOrigin-RevId: 696894483
(cherry picked from commit 0143884cd7)
2024-11-19 11:11:51 +00:00
ibaker
fd02ee182c Release notes for 1.5.0-rc01
PiperOrigin-RevId: 696879276
(cherry picked from commit c50867c81d)
2024-11-19 11:11:48 +00:00
ibaker
ef90f501bf Don't assume MP4 keyframe metadata is correct for CEA re-ordering
The content in Issue: androidx/media#1863 has every sample incorrectly marked as a
sync sample in the MP4 metadata, which results in flushing the
re-ordering queue on every sample, so nothing gets re-ordered, so the
subtitles are garbled.

There are currently two "uses" for this call on every keyframe:
1. It offers a safety valve if we don't read a `maxNumReorderSamples`
value from the video. Without this, the queue will just keep growing
and end up swallowing all subtitle data (similar to the bug fixed by
39c734963f).

2. When we do read (or infer) a `maxNumReorderSamples` it means we can
emit samples from the queue slightly earlier - but this is pretty
marginal, given i think the max possible value for
`maxNumReorderSamples` is 16, so the most benefit we would get is 16
frames (~0.53s at 30fps) - in most cases we will have more than 0.5s
of buffer ahead of the playback position, so the subtitles will still
get shown at the right time with no problem.

(1) is resolved in this change by setting the queue size to zero (no
reordering) if we don't have a value for `maxNumReorderSamples`.

(2) has minimal impact, so we just accept it.

We may be able to inspect the NAL unit to determine IDR vs non-IDR
instead - we will consider this as a follow-up change, but given the
minimal impact of (2) we may not pursue this.

PiperOrigin-RevId: 696583702
(cherry picked from commit e6448f3498)
2024-11-19 11:04:53 +00:00
Copybara-Service
47f3aab231 Merge pull request #1265 from DolbyLaboratories:dlb/ac4-level4/dev_new2
PiperOrigin-RevId: 696157037
(cherry picked from commit 74611bbdc0)
2024-11-19 11:04:53 +00:00
tianyifeng
57d0721fd6 Resolve the memory leaks in demo short-form app
Issue: androidx/media#1839
PiperOrigin-RevId: 696080063
(cherry picked from commit c3d4722197)
2024-11-19 11:04:53 +00:00
ibaker
a46716c0e9 Handle C.TIME_END_OF_SOURCE buffer timestamps in CeaDecoder
The behaviour was changed in 1.4.0 with 0f42dd4752,
so that the buffer timestamp is compared to `outputStartTimeUs` when
deciding whether to discard a "decode only" buffer before decoding
(instead of the deprecated/removed `isDecodeOnly` property). This breaks
when the buffer timestamp is `TIME_END_OF_SOURCE` (which is
`Long.MIN_VALUE`), because `TIME_END_OF_SOURCE < outputStartTimeUs` is
always true, so the end-of-stream buffer is never passed to the decoder
and on to `TextRenderer` where it is used to
[set `inputStreamEnded = true`](40f187e4b4/libraries/exoplayer/src/main/java/androidx/media3/exoplayer/text/TextRenderer.java (L434-L436))
and so playback hangs.

Issue: androidx/media#1863
PiperOrigin-RevId: 695767247
(cherry picked from commit 19b38c83b6)
2024-11-19 11:04:52 +00:00
bachinger
f109a8167b Fix supportedCommands in MediaMetadata
#cherrypick

PiperOrigin-RevId: 695304782
(cherry picked from commit fa790bd73c)
2024-11-19 11:04:52 +00:00
ibaker
0e37bd08be Re-define 'max size' of SEI queue to operate on unique timestamps
This ensures it works correctly when there are multiple SEI messages per
sample and the max size is set from e.g. H.264's
`max_num_reorder_frames`.

PiperOrigin-RevId: 694526152
(cherry picked from commit 53953dd377)
2024-11-19 11:04:52 +00:00
tianyifeng
dba31108a3 Release internal components on preload thread in DefaultPreloadManager
The `RendererCapabilities` and `TrackSelector` objects are accessed on the preload thread during the preloading, when releasing them, they need to be released on the same thread. Otherwise, it is possible that they have already released on the application thread, while the PreloadMediaSource still tries to access them on the preload thread before the source is released.

#cherrypick

PiperOrigin-RevId: 694173131
(cherry picked from commit 2b54b1ebbe)
2024-11-19 11:04:52 +00:00
rohks
461a1fa037 Fix wrong class name in error message of MediaExtractorCompatTest
PiperOrigin-RevId: 693685232
(cherry picked from commit 3d51b36e99)
2024-11-19 11:04:52 +00:00
rohks
09be7b0b25 Move MediaExtractorCompatTest from test/ to androidTest/
The test has been moved to an instrumentation test as it relies on APIs that vary by SDK version. Robolectric’s emulation lacks sufficient realism in some cases, which impacts test accuracy. By using an instrumentation test, we ensure that the tests run in a real Android environment, providing reliable results for SDK-dependent APIs.

PiperOrigin-RevId: 692933259
(cherry picked from commit 261ca326c5)
2024-11-19 11:04:52 +00:00
sheenachhabra
761cf4a001 Fix color info conversion in vpccBox method
The color space should be used to determine the color
primaries and matrix coefficients, not the video range.

PiperOrigin-RevId: 688489212
(cherry picked from commit 31ece8cbd2)
2024-11-19 11:04:52 +00:00
ivanbuper
ca010231a8 Fix incorrect Media3 1.5.0-rc01 release notes
PiperOrigin-RevId: 697626185
(cherry picked from commit fff6e2e169)
2024-11-18 16:12:23 +00:00
tonihei
caf7c2b7f1 Fix position tracking bug for inaccurate audio processors
If audio processors report a drifting position, we currently update
the media position parameters to correct this drift. However, this
means we pass in the wrong value to
audioProcessorChain.getMediaDuration, which reuqires the time since
the last flush.

To fix this problem, we can instead save the drift seperately and
apply it where needed.

PiperOrigin-RevId: 692202219
(cherry picked from commit 06718c5df3)
2024-11-05 13:10:08 +00:00
Copybara-Service
7839f420ab Merge pull request #1225 from Kekelic:support-for-parsing-rtsp-packets-with-header-extension
PiperOrigin-RevId: 692156233
(cherry picked from commit 4910b2cdc0)
2024-11-05 13:10:08 +00:00
tonihei
aad746b05c Annotate parameters in RepeatModeUtil
PiperOrigin-RevId: 692129684
(cherry picked from commit 544d7aa2dc)
2024-11-05 13:10:08 +00:00
rohks
664dc6e482 Add missing DefaultRenderersFactoryTest for decoder extensions
Added `DefaultRenderersFactoryTest` for `IAMF`, `AV1`, and `MIDI` decoder extensions.

PiperOrigin-RevId: 691381816
(cherry picked from commit 27de9f02e0)
2024-11-05 13:10:08 +00:00
tonihei
4b6e886ad2 Improve position estimate when transitioning to another checkpoint
When transitioning to the next media position parameter checkpoint
we estimate the position because the audio processor chain no longer
provides access to the actual playout duration.

The estimate using the declared speed and the last checkpoint may
have drifted over time, so we currently estimate relative to the
next checkpoint, which is closer and presumably provides a better
estimate. However, this assumes that these checkpoint are perfectly
aligned without any position jumps.

The current approach has two issues:
 - The next checkpoint may include a position jump by design, e.g.
   if it was set for a new item in the playlist and the duration of
   the current item wasn't perfectly accurate.
 - The sudden switch between two estimation methods may cause a jump
   in the output position, which is visible when we add new media
   position checkpoints to the queue, not when we actually reach the
   playback position of the checkpoint.

We can fix both issues by taking a slightly different approach:
 - Continuously monitor the estimate using the current checkpoint. If
   it starts drifting, we can adjust it directly. This way the estimate
   is always aligned with the actual position.
 - The change above means we can safely switch to using the estimate
   based on the previous checkpoint. This way we don't have to make
   assumptions about the next checkpoint and any position jumps will
   only happen when we actually reach this checkpoint (which is more
   what a user expects to see, e.g. at a playlist item transition).

Issue: androidx/media#1698
PiperOrigin-RevId: 690979859
(cherry picked from commit 7c0cffdca8)
2024-11-05 13:10:06 +00:00
rohks
7ec61f13ce Fix handling of cues that exceed total duration in MatroskaExtractor
Adjusted logic to accurately calculate sizes and durations for the last valid cue point when cue timestamps are greater than the total duration.

Fixes the issue where the reported duration of the MKV file was greater than the total duration specified by the duration element. Verified this using `mkvinfo` and `mediainfo` tools.

PiperOrigin-RevId: 690961276
(cherry picked from commit b1f2efd218)
2024-11-05 13:09:10 +00:00
ibaker
c44d509ea8 Remove // Do nothing overrides from EventLogger
These methods are marked `default` on the `AnalyticsListener` interface
with an empty implementation, so there's no need to override them just
to re-define the empty implementation.

PiperOrigin-RevId: 689416584
(cherry picked from commit 757f223d8a)
2024-11-05 13:09:10 +00:00
ibaker
8ca80a6b71 Remove some un-needed proguard-rules.txt symlinks
PiperOrigin-RevId: 689344803
(cherry picked from commit b36de302f7)
2024-11-05 13:09:10 +00:00
ibaker
26cbf9444d DataSourceContractTest: Tighten assertions around 'not found' URIs
This change:
1. Updates `DataSourceContractTest` to allow multiple "not found"
   resources, and to include additional info (e.g. headers) on them.
2. Updates the contract test to assert that `DataSource.getUri()`
   returns the expected (non-null) value for "not found" resources
   between the failed `open()` call and a subsequent `close()` call.
   The `DataSource` is 'open' at this point (since it needs to be
   'closed' later), so `getUri()` must return non-null.
    * This change also fixes some implementations to comply with this
      contract. It also renames some imprecisely named `opened`
      booleans that **don't** track whether the `DataSource` is open
      or not.
3. Updates the contract test assertions to enforce that
   `DataSource.getResponseHeaders()` returns any headers associated
   with the 'not found' resource.
4. Configures `HttpDataSourceTestEnv` to provide both 404 and "server
   not found" resources, with the former having expected headers
   associated with it.

PiperOrigin-RevId: 689316121
(cherry picked from commit 4a406be1bf)
2024-11-05 13:09:10 +00:00
Copybara-Service
08e55d81ef Merge pull request #1794 from stevemayhew:p-fix-ntp-time-update-main
PiperOrigin-RevId: 689121191
(cherry picked from commit b5615d5e91)
2024-11-05 13:08:52 +00:00
tonihei
a44079b516 Removed unused constructor
PiperOrigin-RevId: 688960856
(cherry picked from commit 21526588be)
2024-11-05 12:13:17 +00:00
tonihei
bc7c901969 Suppress not-applicable lint warning
PiperOrigin-RevId: 688948857
(cherry picked from commit dfb7636138)
2024-11-05 12:13:17 +00:00
ibaker
fbbe48cd47 Add missing overrides in DefaultTrackSelector.Parameters.Builder
Also add a test for this to avoid missing any others in future. Also
flesh out the existing test for the deprecated builder, to assert the
return type is correctly updated.

PiperOrigin-RevId: 688948768
(cherry picked from commit 7b66209bca)
2024-11-05 12:13:17 +00:00
rohks
a03bd8248c Fix duration calculation for AVI files
The duration is now correctly calculated as the maximum of all track durations, instead of being overwritten by the last track's value. This aligns with how other Extractor implementations handle durations for multiple tracks.

PiperOrigin-RevId: 688896743
(cherry picked from commit e677c8dccd)
2024-11-05 12:13:17 +00:00
bachinger
57f0c0d368 Fix flakiness of MediaBrowserListenerWithMediaBrowserServiceCompatTest
PiperOrigin-RevId: 688870397
(cherry picked from commit 0038dda3c3)
2024-11-05 12:13:17 +00:00
ibaker
70c7ee2e0c Use Guava's HttpHeaders consistently in HTTP testing machinery
PiperOrigin-RevId: 688576776
(cherry picked from commit cabc541a6f)
2024-11-05 12:13:17 +00:00
jbibik
e6849e082c Align spelling of fullScreen to fullscreen
Currently most of the public APIs use `fullscreen` (apart from the deprecated `PlayerControlView.OnFullScreenModeChangedListener` which will have to remain as is). This code changes mostly private variable naming.

PiperOrigin-RevId: 688559509
(cherry picked from commit ee4f0c40bc)
2024-11-05 12:13:16 +00:00
ibaker
8fdb233a7d DataSourceContractTest: Add expected response headers
PiperOrigin-RevId: 688556440
(cherry picked from commit 219565c15e)
2024-11-05 12:13:16 +00:00
tonihei
b68d455b5e Ensure session extras Bundle is copied at least once
If not copied, the extras Bundle can be accidentally changed by the
app if it modifies the instance passed into MediaSession. On the flip
side, the Bundle should be modifiable once created so that the session
can amend the extras if needed without crashing.

PiperOrigin-RevId: 688485963
(cherry picked from commit d9ca3c734a)
2024-11-05 12:13:16 +00:00
rohks
8304c26e08 Improve error logging for IllegalClippingException
Added start and end time details to the error message for `REASON_START_EXCEEDS_END`, helping to debug cases where the start time exceeds the end time.

PiperOrigin-RevId: 688117440
(cherry picked from commit 0ecd35e24c)
2024-11-05 12:13:16 +00:00
ibaker
6611187316 Test ResolvingDataSource resolveReportedUri functionality
PiperOrigin-RevId: 688102934
(cherry picked from commit 40cd64ab19)
2024-11-05 12:13:16 +00:00
ibaker
ab4dff7530 DataSourceContractTest: Add tests for resolved vs original URI
PiperOrigin-RevId: 688076205
(cherry picked from commit 74bbd7727d)
2024-11-05 12:13:04 +00:00
Copybara-Service
6f42f36c05 Merge pull request #1742 from colinkho:trackselection-playwhenready
PiperOrigin-RevId: 688050467
(cherry picked from commit f2ecca3b6a)
2024-11-05 12:07:18 +00:00
ibaker
eb2ef4d14b Fix some markdown-in-javadoc
PiperOrigin-RevId: 687354846
(cherry picked from commit 49337d9667)
2024-11-05 12:07:18 +00:00
tonihei
2bf0138590 Let FakeTrackSelection extend BaseTrackSelection
This fixes a bug in getIndexInTrackGroup

PiperOrigin-RevId: 687336621
(cherry picked from commit ceac959c29)
2024-11-05 12:07:18 +00:00
ibaker
b2b30249c6 Rename playback thread in MediaSourceTestRunner
This makes it more clearly "the playback thread" when logging its name
during tests. The 'real' playback thread used in
`ExoPlayerImplInternal` is [called
`ExoPlayer:Playback`](49dec5db8b/libraries/exoplayer/src/main/java/androidx/media3/exoplayer/PlaybackLooperProvider.java (L87)).

PiperOrigin-RevId: 687307440
(cherry picked from commit b64bf88272)
2024-11-05 12:07:18 +00:00
ibaker
6537a63f2b Release the Surface at the end of every playback test
Without this an error is logged which obfuscates real test failures.

PiperOrigin-RevId: 687302953
(cherry picked from commit 2f01900e83)
2024-11-05 12:07:17 +00:00
tonihei
e6c24087f8 Remove unneeded @Nullable from PlayerWrapper.legacyExtras
All values passed in via the constructor or setLegacyExtras
are guaranteed to be non-null.

PiperOrigin-RevId: 687245475
(cherry picked from commit 5fffe03312)
2024-11-05 12:07:17 +00:00
bachinger
88a78ade04 Accept resource URIs for command buttons
PiperOrigin-RevId: 687239119
(cherry picked from commit 3e556a4b53)
2024-11-05 12:07:17 +00:00
ibaker
ed6b822ff5 Remove unused Surface from DashPlaybackTest
Follow-up to cb90bb38ee

PiperOrigin-RevId: 687235908
(cherry picked from commit 13d6f37a84)
2024-11-05 12:07:17 +00:00
ibaker
9c15ea5436 Add @ForOverride annotation to DataSourceContractTest
PiperOrigin-RevId: 687223500
(cherry picked from commit 3ba2fa6c07)
2024-11-05 12:07:17 +00:00
bachinger
332aa7d34b Look for METADATA_KEY_ART_URI for legacy media items
PiperOrigin-RevId: 687222830
(cherry picked from commit 08e6f30b68)
2024-11-05 12:07:17 +00:00
ivanbuper
0f739bc5fa Bump Media3 to 1.5.0-rc01
#cherrypick

PiperOrigin-RevId: 692221696
(cherry picked from commit 0b1695124b)
2024-11-01 17:48:21 +00:00
ivanbuper
a8c34ca164 Prepare RELEASENOTES.md for Media3 1.5.0-rc01 release
This change also fixes two notes added incorrectly onto the previous
beta01 release section.

PiperOrigin-RevId: 692169335
(cherry picked from commit 38e1efafc2)
2024-11-01 17:47:49 +00:00
ivanbuper
86c9e0f9f7 Move release note in 1.5.0-beta01 to "Unreleased" section
The item was incorrectly added to the beta01 section in 2a49ffcb23.

#cherrypick

PiperOrigin-RevId: 691876672
(cherry picked from commit f991e1f023)
2024-11-01 12:10:54 +00:00
rohks
fc32b7f281 Refactor OpusDecoderTest to use OpusLibrary.isAvailable()
Replaced the custom `LibraryLoader` instance with `OpusLibrary.isAvailable()` to verify the library loading. This simplifies the code by leveraging the existing library loading mechanism.

#cherrypick

PiperOrigin-RevId: 691457871
(cherry picked from commit 2b27e33784)
2024-10-31 14:41:24 +00:00
ibaker
b6baeb6cb0 Support CEA-608 subtitles in Dolby Vision
Issue: androidx/media#1820

#cherrypick

PiperOrigin-RevId: 691378476
(cherry picked from commit 27371db225)
2024-10-31 14:41:24 +00:00
ibaker
bf15b93b60 Mark ProgressiveMediaSource.setSuppressPrepareError package-private
This method will likely be removed in the next release, and is currently
only needed from within the `source` package.

#cherrypick

PiperOrigin-RevId: 691351449
(cherry picked from commit 08a141328d)
2024-10-31 14:41:24 +00:00
rohks
358a3c62fa Use assumeTrue for libiamf availability check in IamfDecoderTest
This change ensures that the test uses `assumeTrue` to avoid failures when the `libiamf` library is not pre-built.

#cherrypick

PiperOrigin-RevId: 691333564
(cherry picked from commit 129cf8ea72)
2024-10-31 14:41:24 +00:00
rohks
ad09a02810 Fix .gitignore paths for extensions
#cherrypick

PiperOrigin-RevId: 690534708
(cherry picked from commit 84ab67cca3)
2024-10-31 14:41:23 +00:00
ibaker
8d8a5211dd H264Reader: Add missing propagation of max_num_reorder_frames
This method is already called below in the
`else if (sps.isCompleted())` block which applies when
`hasOutputFormat == true`, but this is only ever entered if we are
parsing SPS and PPS NAL units **after** we've emitted a format, which
is only the case if
`DefaultTsPayloadReaderFactory.FLAG_DETECT_ACCESS_UNITS` is set (which
it isn't by default).

The equivalent call in `H265Reader` is already inside the
`if (!hasOutputFormat)` block, so doesn't need a similar fix.

#cherrypick

PiperOrigin-RevId: 689809529
(cherry picked from commit 39c734963f)
2024-10-31 14:41:23 +00:00
rohks
895c69c08f Make minor improvements for IAMF decoder module
- Create `LibiamfAudioRenderer` with `DefaultRenderersFactory` in `ExoPlayerModuleProguard`.
- Remove redundant library availability check from `IamfModuleProguard`.
- Move `proguard-rules.txt` to the root folder.
- Removed unused `cryptoType` parameter from `setLibraries()` method in `IamfLibrary`.
- Added log when `LibiamfAudioRenderer` is loaded in `DefaultRenderersFactory`.
- Annotated missing classes with `@UnstableApi`.
- Check for library availability and throw exception in `IamfDecoder` constructor.

#cherrypick

PiperOrigin-RevId: 689330016
(cherry picked from commit 5f99955f31)
2024-10-31 14:41:23 +00:00
rohks
6d0ef8bfe7 Add support for identifying h263 box in MP4 files for H.263 video
Issue: androidx/media#1821

#cherrypick

PiperOrigin-RevId: 688570141
(cherry picked from commit 7545a8929b)
2024-10-31 14:41:23 +00:00
rohks
cc947dc690 Fix media duration parsing in mdhd box of MP4 files to handle -1 values
Treats the media duration as unknown (`C.TIME_UNSET`) when all bytes are
`-1` to prevent exceptions during playback.

Issue: androidx/media#1819

PiperOrigin-RevId: 688103949
(cherry picked from commit 457bc55a4d)
2024-10-31 14:40:55 +00:00
shahddaghash
7da2161a7b Bump Media3 version to 1.5.0-beta01
PiperOrigin-RevId: 688079507
(cherry picked from commit 5088e87195)
2024-10-21 11:30:12 +00:00
shahddaghash
baadadc07a Fix dropped full stop in release notes
PiperOrigin-RevId: 687252101
(cherry picked from commit 709246ac6a)
2024-10-18 13:59:05 +00:00
shahddaghash
7fee7eab03 Update release notes for Media3 1.5.0-beta01 release
PiperOrigin-RevId: 687243739
(cherry picked from commit 4d711050bb)
2024-10-18 13:58:43 +00:00
tonihei
627b7a3e56 Add media button preferences
This adds the API surface for media button preferences in MediaSession
and MediaController. It closely mimics the existing custom layout
infrastructure (which it will replace eventually).

Compat logic:
 - Session:
     - When converting to platform custom actions, prefer to use
       media button preferences if both are set.
     - When connecting to an older Media3 controller, send the
       media button preferences as custom layout instead.
 - Controller:
     - Maintain a single resolved media button preferences field.
     - For Media3 controller receiving both values, prefer media
       button preferences over custom layouts.

Missing functionality:
 - The conversion from/to custom layout and platform custom actions
   does not take the slot preferences into account yet.

PiperOrigin-RevId: 686950100
2024-10-17 09:54:36 -07:00
tonihei
e851a1419d Add slots to CommandButton
These allow to define preferences for where a button should be
displayed.

PiperOrigin-RevId: 686938126
2024-10-17 09:16:44 -07:00
ibaker
8cb558e875 Add HALF_UP rounding TODO to scaleLargeTimestamp (and its usages)
PiperOrigin-RevId: 686921743
2024-10-17 08:25:03 -07:00
ibaker
64e0397811 De-flake new test for ProgressiveMediaSource.suppressPrepareError
This test was added in b3290eff10

#cherrypick

PiperOrigin-RevId: 686918104
2024-10-17 08:11:01 -07:00
ibaker
49dec5db8b Ignore renderer errors from text/metadata tracks
Before this change:

* With legacy subtitle decoding (at render time), load errors (e.g. HTTP
  404) would result playback completely failing, while parse errors
  (e.g. invalid  WebVTT data) would be silently ignored, so playback
  would continue without subtitles.
* With new subtitle decoding (at extraction time), both load and parse
  errors would result in playback completely failing.

This change means that now neither load nor parse errors in text or
metadata tracks stop playback from continuing. Instead the error'd track
is disabled until the end of the current period.

With new subtitle decoding, both load and parse errors happen during
loading/extraction, and so are emitted to the app via
`MediaSourceEventListener.onLoadError` and
`AnalyticsListener.onLoadError`. With legacy subtitle decoding, only
load errors are emitted via these listeners and parsing errors continue
to be silently ignored.

Issue: androidx/media#1722
PiperOrigin-RevId: 686902979
2024-10-17 07:15:22 -07:00
ibaker
191bc094a5 Propagate events from secondary children in MergingMediaSource
These events are always reported with the primary child period ID,
because this is the same ID used in the parent `MergingMediaSource`'s
Timeline.

This ensures that e.g. loading errors from sideloaded subtitles (which
uses `MergingMediaSource`) are now reported via
`AnalyticsListener.onLoadError`.

It results in non-error events being reported from these children too,
which will result in more `onLoadStarted` and `onLoadCompleted` events
being reported (one for each child).

Issue: androidx/media#1722
PiperOrigin-RevId: 686901439
2024-10-17 07:10:59 -07:00
ibaker
b3290eff10 Allow ProgressiveMediaSource to optionally suppress prepare errors
Use this for sideloaded subtitles, so preparation can still complete
despite an error from e.g. `DataSource.open`. In this case, no subtitle
tracks will be emitted.

Issue: androidx/media#1722
PiperOrigin-RevId: 686888588
2024-10-17 06:20:11 -07:00
ivanbuper
b78395b325 Extract method for calculating expected accumulated truncation error
This is prework for implementing
`RandomParameterizedSpeedChangingAudioProcessorTest`, which depends on
Sonic's resampling algorithm's behaviour.

This is a non-functional refactor.

PiperOrigin-RevId: 686874593
2024-10-17 05:24:04 -07:00
michaelkatz
2a1e71b203 Reduce needless loading period resets in clipping mediasource playlists
When a `SampleQueue` is prepared prior to playback, the start position may be less than the timestamp of the first sample in the queue and still be valid. This scenario can come about with specific clipping values and if all samples are sync samples. Currently, with `ClippingMediaPeriods` around `ProgressiveMediaPeriods`, if the `SampleQueue` has already been reset through the seekTo operation in `onPrepared`, then in the aforementioned scenario the seekTo operation in `handleDiscontinuity` will remove all samples and reset the loading periods unnecessarily.

The solution is that if the `ProgressiveMediaPeriod` has already handled a seekTo operation for the same position and the sample queue has not been read yet, then loading does not need to be reset.

The tests in `MergingPlaylistPlaybackTest` were specifically causing this behavior through its setup of `MergingMediaSources` around clipped `FilteringMediaSources`. Since the video content was not 'all sync samples', there would always be a discontinuity to handle and the audio content being 'all sync samples' would start with samples post start time.

These changes also remove the flakiness from the `MergingPlaylistPlaybackTest`.

PiperOrigin-RevId: 686858444
2024-10-17 04:20:50 -07:00
bachinger
8681109d1f Use SessionError error codes to make lint happy
#cherrypick

PiperOrigin-RevId: 686849343
2024-10-17 03:43:59 -07:00
kimvde
38c27d45f1 Make VideoGraph and VideoFrameProcessor listener methods optional
PiperOrigin-RevId: 686833280
2024-10-17 02:38:03 -07:00
ibaker
d2ccace75c Remove allocator param from MediaSourceTestRunner constructor
Currently every test in the library passes `null` here, which seems to
end up being passed into non-null places in the library. This change
removes the parameter and instead initializes the field to a
`DefaultAllocator` instance in the same way that `DefaultLoadControl`
creates one.

PiperOrigin-RevId: 686823273
2024-10-17 02:00:08 -07:00
shahddaghash
2e61c93dba Remove deprecated DefaultEncoderFactory constructors.
Use `DefaultEncoderFactory.Builder` instead.

PiperOrigin-RevId: 686821388
2024-10-17 01:53:23 -07:00
kimvde
31ef7ff088 Clarify Javadoc of EditedMediaItem.Builder.setDurationUs
PiperOrigin-RevId: 686521901
2024-10-16 08:48:10 -07:00
sheenachhabra
d3b7f7e114 Add VP9 test to Mp4MuxerEndToEndNonParameterizedAndroidTest
The test is currently disabled because the produced dump file
is different on different SDK versions.

PiperOrigin-RevId: 686518799
2024-10-16 08:37:41 -07:00
kimvde
363f71357b Handle output size changes inside DefaultVideoSink
PiperOrigin-RevId: 686507112
2024-10-16 07:59:35 -07:00
ibaker
6afebf4c7d Fix typo in release notes
#cherrypick

PiperOrigin-RevId: 686477355
2024-10-16 05:59:00 -07:00
ibaker
e3f813cf0b Attach a Surface in HlsPlaybackTest.cmcdEnabled_withInitSegment
This ensures that the buffers are correctly marked as `rendered = true`
(and therefore `renderered = false` is meaningful when it's present).

This was accidentally missed in 387153fcf2

PiperOrigin-RevId: 686474869
2024-10-16 05:46:22 -07:00
rohks
692f1c78b3 Add ForwardingTrackOutput implementation
This allows users to extend and customize specific methods of the `TrackOutput` implementation while inheriting default behaviors for others.

PiperOrigin-RevId: 686454360
2024-10-16 04:20:33 -07:00
bachinger
075f311200 Cache children when subscribing
Childrens returned by the legacy service when a Media3
browser connects are cached and returned with the first
`getChildren` call in case the same `paranetid` is
requested.

In any other case the cache is immediately cleared.

#cherrypick

PiperOrigin-RevId: 686157511
2024-10-15 10:40:29 -07:00
rohks
91c56335ef Handle out-of-order frames in endIndices for MP4 with edit list
Updated logic to walk forward in the timestamps array to include all frames within the valid edit duration, accounting for out-of-order frames. This ensures that no frames with timestamps less than `editMediaTime` + `editDuration` are incorrectly excluded.

Issue: androidx/media#1797
PiperOrigin-RevId: 686075680
2024-10-15 06:09:15 -07:00
kimvde
9adb3aaf41 Transformer: add an entry point to disable automatic rotation
PiperOrigin-RevId: 686067527
2024-10-15 05:40:41 -07:00
sheenachhabra
643e16ca8f Handle invalid language codes in Boxes.java
When an invalid language code is give, write default value
instead of throwing.

This behaviour aligns with `MediaMuxer`.

PiperOrigin-RevId: 686066088
2024-10-15 05:36:04 -07:00
bachinger
5a827829b0 Call onChildrenChanged to close the legacy subscription error path
When receiving an error from a legacy `MediaBrowserService` after
having successfully subscribed to a given `parentId`, the callback
needs to be asked to load the children again to receive an error
from the service.

Before this change such an error was dropped as a no-op by Media3
without the `MediaBrowser` giving a chance to react on such an error
being sent by the legacy service.

#cherrypick

PiperOrigin-RevId: 686052969
2024-10-15 04:38:34 -07:00
sheenachhabra
407bd49ed5 Skip audio encoding bitrate setting test on API <= 23
The encoder output format on API 23 does not seem to contain bitrate,
hence the test fails.

PiperOrigin-RevId: 686047480
2024-10-15 04:15:38 -07:00
ibaker
cb90bb38ee Remove unused CapturingRenderersFactory from DASH playback test
The `CapturingRenderersFactory` is only needed if the output is
asserted on, e.g. by using `PlaybackOutput` and
`DumpFileAsserts.assertOutput()`.

PiperOrigin-RevId: 686046545
2024-10-15 04:11:42 -07:00
sheenachhabra
0b47e93df5 Update FragmentedMp4Muxer and Mp4Muxerdocumentation to include VP9
PiperOrigin-RevId: 686041467
2024-10-15 03:53:08 -07:00
Googler
0100f1d902 Boxes: Add edit list box.
PiperOrigin-RevId: 685974308
2024-10-14 23:26:08 -07:00
Copybara-Service
4df9d4e146 Merge pull request #1792 from DolbyLaboratories:dlb/elst-handling/dev
PiperOrigin-RevId: 685851466
2024-10-14 15:20:17 -07:00
kimvde
1084c9ea98 Implement DefaultVideoSink.isReady
PiperOrigin-RevId: 685720088
2024-10-14 08:44:51 -07:00
claincly
adb35ee7c4 Reword javadoc
The old javadoc is, IMO, quite hard to understand, so I simplified it a bit,
and added one example.

PiperOrigin-RevId: 685701916
2024-10-14 07:39:53 -07:00
ibaker
9a23d9a611 Deprecate HlsExtractorFactory.DEFAULT
`HlsExtractorFactory` instances are mutable, so storing one in a static
field is not safe, and can lead to state accidentally/surprisingly being
shared between different player instances.

PiperOrigin-RevId: 685701062
2024-10-14 07:36:10 -07:00
ibaker
4a40fa6451 Update StatsDataSource.lastOpenedUri & responseHeader in finally
This ensures these values are still updated even if the delegate
`DataSource.open()` throws an exception (e.g. an HTTP 404).

PiperOrigin-RevId: 685687810
2024-10-14 06:38:56 -07:00
kimvde
37cd008c01 Remove unnecessary method in VideoFrameRenderControl
PiperOrigin-RevId: 685681192
2024-10-14 06:10:33 -07:00
michaelkatz
1c4ee06ad6 Remove Renderer[] from LoadControl.onTracksSelected
The `DefaultLoadControl` implementation of onTracksSelected only utilizes the `Renderer[]` parameter for use in stream type, of which it can collect from the `ExoTrackSelection[]` parameter.

PiperOrigin-RevId: 685677726
2024-10-14 05:56:24 -07:00
claincly
17c0ff8ba8 Log warnings when Transformer sees unsupported track type
PiperOrigin-RevId: 685649866
2024-10-14 03:54:52 -07:00
shahddaghash
5acb483222 Add export settings to demo-composition
Added UI and logic implementation for the following export settings:
* Output audio MIME type
* Output video MIME type
* Enable debug tracing
* Use Media3 Muxer
* Produce fragmented MP4

The settings are shown in a dialog when `Export` button is clicked.

PiperOrigin-RevId: 685648147
2024-10-14 03:46:05 -07:00
shahddaghash
45d2bc39ae Remove SDK checks for H265 and AV1 in Transformer Demo
For simplicity, the following SDK checks when adding supported video codecs were removed from Transformer demo.
1. Adding H265 for API >= 24.
2. Adding AV1 for API >= 34.

PiperOrigin-RevId: 685634851
2024-10-14 02:45:42 -07:00
kimvde
638eae44ab Remove unnecessary method in VideoFrameRenderControl
PiperOrigin-RevId: 685632001
2024-10-14 02:34:49 -07:00
kimvde
5eeedeacc6 Implement DefaultVideoSink.flush()
This is part of the effort to delegate the rendering of the VideoGraph
output frames to a DefaultVideoSink.

PiperOrigin-RevId: 685622019
2024-10-14 01:53:52 -07:00
kimvde
7dbacdb011 PlaybackVideoGraphWrapper: simplify flushing logic
PiperOrigin-RevId: 685610127
2024-10-14 01:10:07 -07:00
ivanbuper
7e023f915b Use BigDecimal as speed parameter for RandomParameterizedSonicTest
This change simplifies conversions to `BigDecimal` and rounding to a set
number of decimal places.

PiperOrigin-RevId: 684890287
2024-10-11 11:00:44 -07:00
tianyifeng
98dc7f2def Add DefaultPreloadManager.Builder
The `DefaultPreloadManager.Builder` is able to build the `DefaultPreloadManager` and `ExoPlayer` instances with the consistently shared configurations. Apps can:

* Simply setup the `DefaultPreloadManager` and `ExoPlayer` with all default configurations via `build()` and `buildExoPlayer()`;
* Or customize the shared configurations by the setters on `DefaultPreloadManager.Builder` and setup via `build()` and `buildExoPlayer()`;
* Or customize the player-only configurations for `ExoPlayer` via `buildExoPlayer(ExoPlayer.Builder)`.

PiperOrigin-RevId: 684852808
2024-10-11 08:55:25 -07:00
ivanbuper
337e59e733 Move util methods in SpeedChangingAudioProcessorto Util
This CL is prework for implementing
`RandomParameterizedSpeedChangingAudioProcessorTest`, which will build
on logic present in `RandomParameterizedSonicTest`.

This is a non-functional change.

PiperOrigin-RevId: 684838017
2024-10-11 08:02:40 -07:00
ivanbuper
984b0bb31a Avoid dropped output frames on SpeedChangingAudioProcessor
Inconsistent rounding modes between `currentTimeUs` and
`bytesUntilNextSpeedChange` would cause `SpeedChangingAudioProcessor`
to miss calling `queueEndOfStream()` on `SonicAudioProcessor` on a speed
change, and thus the final output samples of that `SonicAudioProcessor`
"configuration" would be missed.

This change is also a partial revert of 971486f5f9, which fixed a hang
of `SpeedChangingAudioProcessor`, but introduced the dropped output
frames issue fixed in this CL (see b/372203420). To avoid reintroducing
the hang, we are now ignoring any mid-sample speed changes and will only
apply speed changes that are effective at a whole sample position.

PiperOrigin-RevId: 684824218
2024-10-11 07:01:59 -07:00
tonihei
73f97c0371 Allow AudioTrack to be provided by a customizable provider
PiperOrigin-RevId: 684800579
2024-10-11 05:23:07 -07:00
rohks
ad0493b90f Re-enable disabled tests in FlacExtractorSeekTest
PiperOrigin-RevId: 684790556
2024-10-11 04:38:25 -07:00
sheenachhabra
a0ccd46653 Skip AACObjectHE encoding on faulty devices
These devices claim to have the AACObjectHE profile but the profile never gets applied.

PiperOrigin-RevId: 684786157
2024-10-11 04:18:52 -07:00
Copybara-Service
019fe0589f Merge pull request #1754 from colinkho:loader-plumbing
PiperOrigin-RevId: 684781854
2024-10-11 04:03:09 -07:00
rohks
c78abaac3f Simplify Flac extension build process
Removed `Android.mk` and `Application.mk`, allowing `CMake` to run directly from the build.gradle file. Users no longer need to check out `NDK` or depend on it, simplifying the usage of the Flac extension.

Also fixed a copy-pasted comment in `CMakeLists.txt` of Opus and IAMF.

PiperOrigin-RevId: 684769561
2024-10-11 03:09:32 -07:00
tonihei
b27cbe60b9 Add release callback and generic class to handle type casting 2024-10-11 11:00:45 +01:00
rohks
a2eda3348b Simplify Opus extension build process
Removed `Android.mk` and `Application.mk`, allowing `CMake` to run directly from the build.gradle file. Users no longer need to check out `NDK` or depend on it, simplifying the usage of the Opus extension.

PiperOrigin-RevId: 684489927
2024-10-10 10:23:26 -07:00
rohks
2640ebd58f Add 16 KB page support for decoder extensions on Android 15
We need to rebuild any native components of the app to prevent crashes on devices with 16 KB page support.

Tested on a device that supports 16 KB pages and runs Android 15, as well as on older Android devices.

Issue: androidx/media#1685
PiperOrigin-RevId: 684488244
2024-10-10 10:18:20 -07:00
rohks
6acddfeee6 Simplify IAMF extension build process
Removed `Android.mk` and `Application.mk`, allowing `CMake` to run directly from the `build.gradle` file. Users no longer need to check out `NDK` or depend on it, simplifying the usage of the IAMF extension.

PiperOrigin-RevId: 684471874
2024-10-10 09:32:25 -07:00
sheenachhabra
1729e11159 Fix version and flags in the ctts box
The version and flags are stored in a single integer,
with the version in the higher 8 bits and the flags in
the lower 24 bits. The version should be 1 and the
flags should be 0.

Surprisingly the incorrect value was ignored by many
players and hence the bug was never caught.
With the bug, the video does not play on
`Samsung Galaxy S22 Ultra` and works well
after fixing the bug.

PiperOrigin-RevId: 684433371
2024-10-10 07:19:24 -07:00
ivanbuper
3818e103e6 Rename timeUs to currentTimeUs
This is a non-functional refactor.

PiperOrigin-RevId: 684408479
2024-10-10 05:36:44 -07:00
bachinger
cbc0ee369f Use connection hints when connecting to MediaBrowserService
Minor improvement to allow an Media3 browser to pass extras
when connecting the initial browser in `MediaControllerImplLegacy`.
Before this change an empty bundle was sent. After this change
the connection hints of the `Media3 browser is used as root hints
of the initial browser that connects when the Media3 browser is
built in `MediaBrowser.buildAsync`.

#cherrypick

PiperOrigin-RevId: 684372552
2024-10-10 03:11:52 -07:00
ibaker
b6d0540059 Use scaleLargeTimestamp in TimestampAdjuster
This helps avoid overflows in intermediate calculations.

Verified the value in the test using `BigInteger`:

```
jshell> BigInteger.valueOf(1L << 52).multiply(BigInteger.valueOf(90000)).divide(BigInteger.valueOf(1000000))
$3 ==> 405323966463344
```

Issue: androidx/media#1763

#cherrypick

PiperOrigin-RevId: 684028178
2024-10-09 07:27:53 -07:00
ibaker
2c46cea088 Use RoundingMode.DOWN in Util.scaleLargeTimestamp and friends
The implementation of these methods was updated from direct java integer
arithmetic in 885ddb167e.
In this change, `RoundingMode.FLOOR` was used to try and maintain
compatibility with java integer division. This was incorrect, because
java integer division uses `DOWN` (i.e. towards zero), rather than
`FLOOR` (i.e. towards negative infinity) semantics.

This change fixes the compatibility.

The dump file changes in this CL relate to tests that exercise edit
list behaviour. This involves manipulating negative timestamps, which
explains why they are impacted by this change.

PiperOrigin-RevId: 684013175
2024-10-09 06:24:26 -07:00
shahddaghash
d5baa4ce59 Add HDR & Resolution Height settings to demo-composition
Added UI and logic implementation for HDR mode and Resolution Height to be used as settings for both previewing and exporting.

PiperOrigin-RevId: 684011852
2024-10-09 06:19:28 -07:00
rohks
c744fe9f8f Recognize IAMF format and enhance channel count constraints
- Updated `DefaultTrackSelector.SpatializerWrapperV32.canBeSpatialized` to handle IAMF format.
- Modified `isAudioFormatWithinAudioChannelCountConstraints` to check for `NO_VALUE` of `channelCount` to improve readability.

Note: `DefaultTrackSelector.SpatializerWrapperV32.canBeSpatialized` is not triggered for the IAMF format due to the unset channel count (`Format.NO_VALUE`). The update ensures completeness.

#cherrypick

PiperOrigin-RevId: 684003980
2024-10-09 05:50:58 -07:00
tonihei
15a6906877 Formatting and javadoc 2024-10-09 13:50:30 +01:00
Colin Kho
2f6d8bf5ba Remove unused import 2024-10-09 13:50:29 +01:00
Colin Kho
10bb2e1501 Allow Injection of custom Executor in ProgressiveMediaSource 2024-10-09 13:50:29 +01:00
Colin Kho
ea837e494b Remove unused Executors import 2024-10-09 13:50:29 +01:00
Colin Kho
f7a1b19001 Allow custom Executor to be supplied to ChunkSampleStream 2024-10-09 13:50:29 +01:00
rohks
4df7216bc0 Prioritize object-based audio in DefaultTrackSelector
Object-based audio is more efficient and flexible than channel-based audio, supporting a broader range of devices. This update makes `DefaultTrackSelector` prefer object-based audio when other factors are equal, ensuring its use whenever possible.

#cherrypick

PiperOrigin-RevId: 683990051
2024-10-09 04:55:36 -07:00
Copybara-Service
5e5d486ef1 Merge pull request #1618 from khouzam:main
PiperOrigin-RevId: 683973733
2024-10-09 03:51:10 -07:00
microkatz
3f44f9a898 Cosmetic changes 2024-10-09 09:41:54 +00:00
shahddaghash
12f34c337e Connect produceFragmentedMp4CheckBox to useMedia3Muxer
Connected `produceFragmentedMp4CheckBox` to `useMedia3Muxer` checkbox since producing fragmented MP4 is contingent on using Media3 Muxer.

1. If both were unchecked, `useMedia3Muxer` gets checked when `produceFragmentedMp4CheckBox` is checked.
2. If both were checked, `produceFragmentedMp4CheckBox` gets unchecked when `useMedia3Muxer` is unchecked.

PiperOrigin-RevId: 683948863
2024-10-09 02:15:03 -07:00
ybai001
3f4a16555d Bugfix: segment_duration and media_time use different unit 2024-10-09 16:54:59 +08:00
ybai001
d73115a927
Merge pull request #12 from androidx/main
Merge from androidx/media main branch
2024-10-09 16:51:13 +08:00
kimvde
e234076fdc DefaultVideoSink: implement set/clearOutputSurfaceInfo
This is part of the effort to handle rendering of the frames output by
the VideoGraph in a DefaultVideoSink

PiperOrigin-RevId: 683939818
2024-10-09 01:47:38 -07:00
bachinger
c4ff07e229 Don't advertise commands that are not available
When calling `MediaController.getCommandButtonForMediaItem(MediaItem)`
command buttons with custom commands that are not available
shouldn't be advertised to the controller when connected to
a Media3 session.

In contrast, when connected to a legacy session, available commands
are not enforced when advertising commands. Similarly, when sending
a custom commands that is referenced by a command button for media
items, sending is permitted without the command being available.

This is required because available commands match to custom actions
in `PlaybackStateCompat` of the legacy session. Adding commands for
media items to custom action of the `PlaybackStateCompat` would
interfere with other use cases.

Issue: androidx/media#1474
#cherrypick
PiperOrigin-RevId: 683717723
2024-10-08 12:14:34 -07:00
ibaker
546d7da2f2 Fix Fmp4Extractor.init to use text transcoding ExtractorOutput
This was missed in da724c8cc4

I tried to write a test for this, but got stuck crafting valid test
data. I was able to create a new fragmented MP4 file containing only a
TTML track:

```shell
$ MP4Box -add simple.ttml -frag 2000 sample_fragmented_ttml.mp4
```

Then I tried naively removing the `ftyp` and `moov` boxes with a hex
editor, but using this in `FragmentedMp4ExtractorNoSniffingTest` gave
me an `EOFException` that I didn't get to the root cause of.

Issue: androidx/media#1779

#cherrypick

PiperOrigin-RevId: 683667850
2024-10-08 10:11:18 -07:00
rohks
72ab282c0d Ignore channelCount and sampleRate values read from iamf box
As per the IAMF spec (https://aomediacodec.github.io/iamf/#iasampleentry-section), `channelCount` and `sampleRate` SHALL be set to `0` and ignored.

#cherrypick

PiperOrigin-RevId: 683648991
2024-10-08 09:18:44 -07:00
microkatz
ae363671b5 Moved supportsFormat functional code to private method 2024-10-08 15:55:39 +00:00
rohks
8f82a15e48 Return early when audioManager is null
Also declare and use `AudioFormat` directly instead of building it later.

PiperOrigin-RevId: 683637116
2024-10-08 08:42:56 -07:00
microkatz
34f50adcd2 Format with google-java-format 2024-10-08 14:43:55 +00:00
Gilles Khouzam
a772e1525c Add a static rendererSupportsFormat method for MCVR
This refactors the `supportsFormat` method on the MediaCodecVideoRenderer to be a static method that can be called from external components to determine if a video format is supported by the device renderers. Since `context` is the only component that is part of the MCVR, it can easily be obtained externally and passed to the method.

This can help optimize format support decisions ahead of time of a player having been instantiated, such as removing unsupported representations from a dash manifest.

This could also be done for the MCAR but would also require passing in the AudioSink and isn't required at this time.
2024-10-08 14:43:55 +00:00
tianyifeng
fd48dd9ce8 Add PlaybackLooperProvider and make it injectable for ExoPlayer
PiperOrigin-RevId: 683607682
2024-10-08 07:07:13 -07:00
ibaker
abfeea518e Ensure consistent ExtractorOutput usage in WebvttExtractor
This change is a no-op, because
`SubtitleTranscodingExtractorOutput.seekMap` forwards directly to the
delegate implementation, but it seems clearer to always use the
wrapper.

Also remove a no-op assignment in `MatroskaExtractor`.

This is a follow-up to Issue: androidx/media#1779 where I manually checked every
implementation of `Extractor.init` for a similar mistake.

#cherrypick

PiperOrigin-RevId: 683607090
2024-10-08 07:04:50 -07:00
kimvde
5f935ef22e DefaultVideoSink: implement initialize() and isInitialized()
The implementation is straightforward as there is nothing to init.

PiperOrigin-RevId: 683596706
2024-10-08 06:25:47 -07:00
Copybara-Service
62864d5475 Merge pull request #1651 from colinkho:mp-cl
PiperOrigin-RevId: 683548885
2024-10-08 03:28:59 -07:00
kimvde
52f08d46c2 Add motion photo support to Transformer
PiperOrigin-RevId: 683540867
2024-10-08 02:57:52 -07:00
tonihei
bd192c17ca Restrict CommandButton.iconUri to content Uris
These Uris are not widely supported yet and were only meant to be
used with content Uris. Restricting this more tightly allows
controllers to use these Uris more easily as they have a stricter
guarentee on what it's needed to load these Uris. Media session
apps with different types of Uris can convert them by setting up
a ContentProvider if needed.

Issue: androidx/media#1783
PiperOrigin-RevId: 683539747
2024-10-08 02:53:49 -07:00
kimvde
7c9fede3ad Add DefaultVideoSink and implement straightforward methods
Other methods will be implemented in follow-up CLs

PiperOrigin-RevId: 683538245
2024-10-08 02:49:44 -07:00
tonihei
bf88128383 Formatting and additional call for preloading period 2024-10-08 10:15:04 +01:00
Colin Kho
7b0f83690c Add LoadingInfo as a parameter to continueLoading on MediaPeriodHolder 2024-10-08 10:15:04 +01:00
kimvde
8d0b82dfc3 PlaybackVideoGraphWrapper: rename VideoSinkImpl to InputVideoSink
PlaybackVideoGraphWrapper will soon contain an input and an output video
sink, as the rendering of the VideoGraph output frames will be handled
by a DefaultVideoSink instance.

PiperOrigin-RevId: 683167795
2024-10-07 07:02:12 -07:00
ivanbuper
af922fbcb0 Fix truncation error accumulation on Sonic's time stretching algorithm
This CL also fixes EOS handling to account for not-yet-copied samples in
`remainingInputToCopyFrameCount`, which would throw off the final output
sample count calculation.

For testing, we allow a tolerance of 0.000017% drift between expected
and actual number of output samples. The value was obtained from running
100 iterations of `timeStretching_returnsExpectedNumberOfSamples()` and
calculating the average delta percentage between expected and actual
number of output samples. Roughly, this means a tolerance of 40 samples
on a 90 min mono stream @48KHz.

PiperOrigin-RevId: 683133461
2024-10-07 04:59:54 -07:00
tonihei
f7af58951d Allow signed TTML region origins
The origin may be negative if the subtitle starts off-screen
but extends into the screen for example.

TTML1 defines `tts:origin` in terms of
[`length`](https://www.w3.org/TR/2018/REC-ttml1-20181108/#style-value-length),
which allows a prefix of `+`, `-` or nothing, and it's the
[same in TTML2](https://www.w3.org/TR/2018/REC-ttml2-20181108/#style-value-length).

PiperOrigin-RevId: 682379845
2024-10-04 10:58:42 -07:00
tonihei
af6ad43ca0 Disable the language/role flag preferences when selecting "none"
Just clearing the overrides only helps if a text override was
previously set. If the text is shown because of app defined track
selection parameters for language or role flags, the "none" button is
currently not working and we need to clear these flags explicitly.

PiperOrigin-RevId: 682373821
2024-10-04 10:42:27 -07:00
tonihei
47021c8777 Account for missing preroll when converting adPodIndex to adGroupIndex
IMA always starts midrolls at index 1. So if there is no preroll ad,
the ad group index in AdPlaybackState is off by 1 all the time, and
may also lead to ArrayIndexOutOfBoundsExceptions when trying to access
the last midroll ad

Issue: androidx/media#1741
PiperOrigin-RevId: 682324368
2024-10-04 08:11:04 -07:00
claincly
b5680e8a65 Make OverlayEffect take a List
Otherwise, it cannot be used with Kotlin `listOf()`.

PiperOrigin-RevId: 682255423
2024-10-04 03:46:41 -07:00
dancho
7b08bedf2c Do not force EOS when decoder has produced all frames
The workaround in ExternalTextureManager.forceSignalEndOfStream
was being applied even when the decoder did output all frames, and only
the GL pipeline was slow.

This change ensures that workaround is not applied when the decoder
has already produced all output frames.

PiperOrigin-RevId: 680471587
2024-09-30 01:50:10 -07:00
sheenachhabra
b0b54ca018 Calculate min timestamp across tracks in the Boxes.moov method
The Boxes.moov method can do the calculation instead of caller doing
it.

PiperOrigin-RevId: 679653033
2024-09-27 11:00:52 -07:00
tonihei
4481b3567e Add workaround for codecs not propagating EOS signal.
If a codec received the EOS signal and already returned the last
output buffer, we should expect the output EOS very quickly. If
it doesn't arrive within 100ms, we can proceed to end the stream
manually without waiting any further to prevent cases where the
codec is completely stuck otherwise.

PiperOrigin-RevId: 679633116
2024-09-27 10:07:10 -07:00
bachinger
287f353c87 Move tests relying on unreleased robolectric changes
#cherrypick

PiperOrigin-RevId: 679589647
2024-09-27 07:57:39 -07:00
bachinger
c6434a8276 Add @CanIgnoreReturnValue to MediaSession.BuilderBase
PiperOrigin-RevId: 679536456
2024-09-27 04:32:55 -07:00
claincly
e0e9f5b057 Increase the maxImage on ImageReader, hoping less flaky tests
PiperOrigin-RevId: 679528425
2024-09-27 04:03:15 -07:00
dancho
b9aed0a937 Have AndroidTestUtil.canEncode mirror VideoSampleExporter
Some devices can encode portrait 720x1080 but not landscape
1080x720. But VideoSampleExporter always prefers encoding
landscape. Have `assumeFormatsSupported` mirror sample exporter
logic more closely

PiperOrigin-RevId: 679495210
2024-09-27 02:01:05 -07:00
tonihei
23e02cce81 Upgrade Guava to 33.3.1
This bugfix release contains a fix for Issue: androidx/media#1700.

PiperOrigin-RevId: 679493263
2024-09-27 01:53:14 -07:00
tonihei
138a8d65ca Get updated buffered position when calling shouldStartPlayback
The buffered position was last updated before the beginning of
the renderer loop in doSomeWork. As the loading happens on a
background thread, it may have progressed further already
depending on how long it took to run the renderer loop.

It's slightly more correct to pass in an updated value to
shouldStartPlayback so that playback can start quicker if the
buffering is particularly fast.

PiperOrigin-RevId: 679203465
2024-09-26 10:33:40 -07:00
tianyifeng
2dde824bde Fix the flakiness in DefaultPreloadManagerTest
We began to use a different preload thread than the main thread in the `DefaultPreloadManagerTest`, then in the test execution, we should also ensure that the events queued on the preload looper have been executed.

Also, there is an edge case also causing flakiness. Assume that `DefaultPreloadManager` is preloading source B, then the app invalidates and triggers another sequence of preloading, say they are A, B and C. There is possibility that source B finishes preloading (started before `invalidate`) when A starting to preload, then `onPreloadSkipped` will be triggered for source B instead of `onPreloadCompleted`. However, the functional block inside of `onPreloadSkipped` is dispatched asynchronously, and by then it's possible that B starts to preload again at the consequence of A being completed, then the functional block just mentioned may think that the current source matches at B, and will advance the current preloading source to C, without informing the `Listener.onPreloadCompleted` for it. As the result, the `Listener.onPreloadCompleted` can never be triggered for B for the second sequence. To fix this, we should prevent the functional block in `onPreloadCompleted`, `onPreloadError`, `onPreloadSkipped` to be even dispatched, when the source doesn't match the current preloading one.

PiperOrigin-RevId: 679145353
2024-09-26 07:47:35 -07:00
samrobinson
45c400c7b5 Clarify compositionPlayer audio test naming.
PiperOrigin-RevId: 679142528
2024-09-26 07:37:52 -07:00
sheenachhabra
5e57734346 Update the comment of WRITE_TO_DEVICE enum
The previous comment was not super clear on how to
replace the dump files in the project directory.

PiperOrigin-RevId: 679136624
2024-09-26 07:17:43 -07:00
michaelkatz
09a5ef505b Assign the C.TRACK_TYPE_METADATA type to icy or vnd.dvb.ait tracks
The MetadataRenderer by default supports icy and vnd.dvb.ait content. Those tracks should therefore be set with the `C.TrackType` `TRACK_TYPE_METADATA` rather than `TRACK_TYPE_UNKNOWN`.

PiperOrigin-RevId: 679132680
2024-09-26 07:02:53 -07:00
sheenachhabra
b6192f7a39 Add AudioEncoderSettings to Transformer
It allows clients to specify the audio encoding profile and bitrate.
This is similar to VideoEncoderSettings.

PiperOrigin-RevId: 679131963
2024-09-26 06:59:53 -07:00
tonihei
f4eef88089 Ensure Media3 play calls get FGS exemption
When a Media3 controller calls play on a Media3 session, the call
is currently not routed through the platform session at all.
This means the usual exemption to start a FGS for media controller
interactions is not triggered.

We can manually ensure this exemption is given by sending a custom
platform command to the session. The Media3 session will never
receive this command as it's not a known Media3 custom command.
Sessions will see a single onConnect call with a platform controller
from the sender app though. We can prevent this on newer versions of
the code by dropping the onCommand call early.

PiperOrigin-RevId: 679115247
2024-09-26 05:57:40 -07:00
claincly
50c879ee21 Remove stale comment
PiperOrigin-RevId: 679082395
2024-09-26 03:55:24 -07:00
bachinger
65962dcb37 Add Builder.setMaxCommandsForMediaItems for browser and controller
The max number of commands for media items of a browser or controller
can be configured with `setMaxCommandsForMediaItems(int)` on
`MediaController.Builder` and `MediaBrowser.Builder`. An app that has
only limited space for displaying commands can hint this limit to the
session.

A session can receive the value of a connected browser or controller
through `getMaxCommandsForMediaItems()` of a `ControllerInfo` that
is passed into every callback method. The session can then pick the most
sensible commands instead of making the browser app truncating the commands
rather randomly.

When a `MediaBrowser` is connected against a legacy `MediaBrowserServiceCompat`,
the max number of commands is automatically added to the root hints. Conversely,
the value passed in with the root hints to `MediaLibraryService` by a legacy
`MediaBrowserCompat`, is read into `ControllerInfo` like for a Media3 browser.

Issue: androidx/media#1474

#cherrypick

PiperOrigin-RevId: 679076506
2024-09-26 03:33:01 -07:00
Googler
020ce7765c Reduce rounding error and stts table entries.
To avoid rounding errors, set the `Rounding mode` of the `uvFromVu` and `vuFromUs` results to `HALF_UP`. This `Rounding mode` rounds numbers towards the "nearest neighbor" unless both neighbors are equidistant, in which case round up.

PiperOrigin-RevId: 679003943
2024-09-25 23:19:20 -07:00
ibaker
2520dd12f9 Fix EMSG typo in HlsChunkSource and ChunkSampleStream
PiperOrigin-RevId: 678870309
2024-09-25 15:33:22 -07:00
bachinger
b8ec6b836b Add interoperability for media item commands
See https://developer.android.com/training/cars/media#custom_browse_actions

- `MediaMetadata.supportedCommands` is converted to an array list of
  strings into the extras of `MediaDescriptionCompat` with `DESCRIPTION_EXTRAS_KEY_CUSTOM_BROWSER_ACTION_ID_LIST` and vice versa.

- The set of media item command buttons of a session is passed in the
root hints to a legacy browser that connects. A Media3 browser connected
to a legacy service, gets the set of all commands after calling
`getLibraryRoot()`.

#cherrypick

PiperOrigin-RevId: 678807473
2024-09-25 12:40:22 -07:00
bachinger
686c3fe7f5 Add media item command buttons for Media3 controllers
Note that unlike the legacy implementation, custom media items
commands can be used for any media items with Media3 API. This
includes `MediaItem` instances that are received from sources
different to `MediaLibraryService` methods.

Hence when connected against a Media3 session these custom commands
can be used with a `MediaController` as well as with a `MediaBrowser`.

Interoperability with `MediaBrowserServiceCompat` will
be added in a follow up CL.

Issue: androidx/media#1474
#cherrypick
PiperOrigin-RevId: 678782860
2024-09-25 11:36:11 -07:00
claincly
0ea63e3fa6 Disable video only on the sequence that has items that disable video
This means we need a custom track selector for each SequencePlayer.

PiperOrigin-RevId: 678779216
2024-09-25 11:28:26 -07:00
tonihei
5879426c07 Check surface validity before configuring it on a codec
This check is also done when setting a surface on ExoPlayerImpl,
but by the time we configure the codec the surface may have become
invalid (e.g. when it is destroyed). Even though we immediately remove
a destroyed surface, we could still accidentally use it before the
removal is processed. To avoid these edge cases, we can simply not
configure the codec with an invalid surface.

PiperOrigin-RevId: 678741425
2024-09-25 09:58:11 -07:00
kimvde
3ec9c99644 Document that the MediaItem's image duration should be set for images
PiperOrigin-RevId: 678702334
2024-09-25 08:04:31 -07:00
kimvde
2dc32360d6 Remove usages of deprecated DefaultDecoderFactory constructor
The constructor was deprecated but usages were not migrated.

PiperOrigin-RevId: 678683678
2024-09-25 07:01:14 -07:00
samrobinson
fa04386863 Enable multi sequence audio preview test.
PiperOrigin-RevId: 678667829
2024-09-25 06:03:23 -07:00
samrobinson
5ab72a3938 Use constants in dump file names for playback test.
PiperOrigin-RevId: 678664730
2024-09-25 05:51:06 -07:00
kimvde
eaec7a4a61 Set MediaItem's image duration for image export
This field will become mandatory

PiperOrigin-RevId: 678656879
2024-09-25 05:23:27 -07:00
kimvde
f83d2b1392 Stop calling setDurationUs when image duration already set
The EditedMediaItem's duration is set to the MediaItem's image duration
by default.

PiperOrigin-RevId: 678597324
2024-09-25 02:02:30 -07:00
samrobinson
fc07ce056a Add safer gap based checks to Transformer API boundary points.
PiperOrigin-RevId: 678278666
2024-09-24 09:23:01 -07:00
tonihei
8b7c8ffb86 Misc cleanup for session token
Improved string representation for legacy token and
import for unambigious class name.

PiperOrigin-RevId: 678256188
2024-09-24 08:16:08 -07:00
samrobinson
076eea283e Adding API and internal export support for audio gaps in sequences.
PiperOrigin-RevId: 678235289
2024-09-24 07:14:59 -07:00
tonihei
43765b7567 Add platform token to Media3 SessionToken
Access is package-private and it will allow the media controller logic
to interact with the underlying platform session directly if needed.

Interop: When a MediaController connects to an older session (before this
change), it won't get the platform token from the session directly.
Many controllers will be set up with a platform or compat token though
and we can simply keep the already known token and use it. The only
cases where we still don't have a platform token in the MediaController
are the cases where the controller is created with a SessionToken based
on a ComponentName.
PiperOrigin-RevId: 678230977
2024-09-24 07:01:39 -07:00
kimvde
d8dc513431 Apply video composition effects in preview
PiperOrigin-RevId: 678207818
2024-09-24 05:46:33 -07:00
kimvde
c19d910f6b Fix EffectPlaybackPixelTest
The tests using createTimestampOverlay() were passing even if the effect
was removed, because the overlay was too small.

PiperOrigin-RevId: 678169395
2024-09-24 03:24:49 -07:00
Copybara-Service
424ecadb66 Merge pull request #1736 from colinkho:msource_list
PiperOrigin-RevId: 677994281
2024-09-23 17:04:39 -07:00
Tianyi Feng
b303498834 Fix the typo in javadoc 2024-09-23 20:53:53 +00:00
Tianyi Feng
508a1d800d Add release note 2024-09-23 20:53:53 +00:00
Colin Kho
31a540953c Add method to MediaSourceEventListener.EventDispatcher to submit events through a lambda function. This allows clients that implement this interface to submit customized event dispatching logic to the EventDispatcher's listeners 2024-09-23 20:53:52 +00:00
bachinger
b884d7ee9b Handle IllegalArgumentException when setting broadcast receiver
Some devices seem to throw an `IllegalArgumentException` when
attempting to set a valid media button broadcast receiver
for playback resumption. This change handles this exception
as a no-op to avoid crashing the app. As a result, playback
resumption with media keys isn't going to work on these
devices.

This change needs to be reverted once the root cause on these
devices has been fixed (see internal bug ref in source).

Issue: androidx/media#1730
PiperOrigin-RevId: 677904243
2024-09-23 12:53:37 -07:00
ibaker
869a91bba8 Remove DemoUtil.ALLOW_CRONET_FOR_NETWORKING
This boolean only exists to be changed in source, but it is now used
as part of a 3-way fallback logic (since adding `HttpEngine`
integration), so it's not really more convenient or clearer to change
this constant than just hack the code of `getHttpDataSourceFactory`
directly.

PiperOrigin-RevId: 677834348
2024-09-23 09:55:55 -07:00
samrobinson
b4436c523c Migrate Media3 EditedMediaItemSequence usages to the Builder.
Removed the unnecessary wrapping of items in an ImmutableList.

PiperOrigin-RevId: 677796662
2024-09-23 08:06:55 -07:00
bachinger
ba1cdba403 Preload first period of next window
Allow apps to preload the first period of the next window in
the playlist of `ExoPlayer`. By default playlist preloading is
disabled. To enable preloading,
`ExoPlayer.setPreloadConfiguration(PreloadConfiguration)` can be
called.

`LoadControl` determines when to preload with its implemenation of `shouldContinuePreloading(timeline, mediaPeriodId, bufferedDurationUs)`.
The implementation in `DefaultLoadControl` allows preloading only when
the player isn't currently loading for playback. Apps can override this
behaviour.

Issue: androidx/media#468
PiperOrigin-RevId: 677786017
2024-09-23 07:32:48 -07:00
ivanbuper
3d3ec85c12 Setup basic testing for Sonic and assert expected sample count drift
This CL adds `SonicTest` and `RandomParameterizedSonicTest` as
initial basic unit testing for `Sonic.java`. The tested scenarios
do not necessarily verify a correct implementation of Sonic, but rather
hope to catch any behaviour change from the current implementation.

The change includes a small fix for a lossy simplification and also
checks whether the output sample count matches the expected drift from
the truncation accumulation error present in Sonic's resampler. This is
important as pre-work for fixing issues with unexpected durations within
`SonicAudioProcessor` and `SpeedChangingAudioProcessor` that cause AV
sync issues for speed changing effects.

This is a partial roll forward of e88d6fe459, which was rolled back in
873d485056.

PiperOrigin-RevId: 677756854
2024-09-23 05:53:58 -07:00
dancho
17e1d37112 Fix GL filtering algorithm used when experimental fix is disabled
When working on SurfaceTexture crop fix, we accidentally switched
to GL_NEAREST resampling.

PiperOrigin-RevId: 677751819
2024-09-23 05:34:30 -07:00
kimvde
be4d31ba87 Prevent ExoPlayer dropping frames in EffectPlaybackPixelTest
Some tests check all the output frames and fail if there are frames
missing.

PiperOrigin-RevId: 677676143
2024-09-23 01:12:40 -07:00
tonihei
5e3dcea1bf Ramp up volume after AudioTrack flush to avoid pop sound
AudioTrack doesn't automatically ramp up the volume after a flush
(only when resuming with play after a pause), which causes audible
pop sounds in most cases. The issue can be avoided by manually
applying a short 20ms volume ramp, the same duration used by the
platform for the automatic volume ramping where available.

Together with the already submitted 6147050b90, this fixes the
unwanted pop sounds for most cases in the desired way. It only
leaves two cases that are not handled perfectly:
 - If the media file itself contains a volume ramp at the beginning,
   we wouldn't need this additional ramping. Given the extremely
   short duration, this seems ignorable and we can treat it as a
   future feature request to mark the beginning of media in a special
   way that can then disable the volume ramping.
 - For seamless period transitions where we keep using the same
   AudioTrack, we may still get a pop sound at the transition. To
   solve this, we'd need a dedicated audio processor to either ramp
   the end of media down and the beginning of the next item up, or
   apply a very short cross-fade. Either way, we need new signalling
   to identify cases where the media originates from the same source
   and this effect should not be applied (e.g. when re-concatenating
   clipped audio snippets from the same file).

PiperOrigin-RevId: 676860234
2024-09-20 08:55:29 -07:00
ibaker
e887614246 Move release note from 1.5.0-alpha01 to 'unreleased'
This was accidentally added in the wrong place in 6bda0da6be

PiperOrigin-RevId: 676841659
2024-09-20 07:48:26 -07:00
Copybara-Service
6d6724db94 Merge pull request #1740 from MGaetan89:fix_shortform_demo_input_type
PiperOrigin-RevId: 676581325
2024-09-19 15:17:07 -07:00
bachinger
6bda0da6be Fix sending custom commands with a media browser
When sending a custom command with `browser.sendCustomCommand` when
connected to a legacy browser service, the custom command was delivered to `MediaSessionCompat.Callback.onCustomAction` instead of the service method
`onCustomAction`. The difference is that the service version can return an
async response with a bundle, while the session callback version doesn't
have a return value.

Hence, the service method was never called and it wasn't possible to send
a reponse or signal an error back to the browser. The resulting
`ListanableFuture` simply always immediately resolved to a success.

This change overrides `ListenableFuture<SessionResult> sendCustomCommand(SessionCommand command, Bundle args)` in
`MediaBrowserImplLegacy` to use the `MediaBrowserCompat` method to send
instead of the `MediaControlleCompat` method that was used by the subclass
`MediaControllerImplLegacy`. This involves the service callback instead of the
session callback and enables `MediaBrowser` to get the actual return value
from the legacy service.

Issue: androidx/media#1474
#cherrypick
PiperOrigin-RevId: 676519314
2024-09-19 12:35:42 -07:00
samrobinson
3c5e764b86 Fix CapturingMuxer writing of final PCM audio sample to dump file.
Last buffer was not flipped, so was writing the garbage data between
limit and capacity, rather than the actual data between position and
limit.

As a result, all PCM audio dump files need updating.

PiperOrigin-RevId: 676452990
2024-09-19 09:52:12 -07:00
samrobinson
75c7ee79d5 Add EditedMediaItemSequence.Builder.
PiperOrigin-RevId: 676422122
2024-09-19 08:23:37 -07:00
Gaëtan Muller
76e3fc06dd
Update activity_main.xml 2024-09-19 11:08:06 +02:00
kimvde
980f24d906 Avoid ImageReader frame drops in EffectPlaybackPixelTest
If this doesn't work, we could make this test resilient to frame drops
by only comparing the frames that weren't dropped.

PiperOrigin-RevId: 676294944
2024-09-19 00:18:46 -07:00
rohks
ecb0024a0b Improve frame rate calculation by using media duration from mdhd box
- Added logic to parse media duration from the `mdhd` box for accurate frame rate calculation.
- Fallbacks to track duration from `tkhd` when `mdhd` contains invalid or missing data.
- Avoids incorrect frame rate calculations in MP4 files with an edit list (`elst`) box.
- Adds frame rate calculations for partially fragmented MP4 files.
- Verified accuracy with tools like `mediainfo` and `ffprobe`.

Issue: androidx/media#1531

**Note**: The slight difference in frame rate values in dump files that aren’t MP4s with an edit list or fragmented MP4s isn’t due to differences in `tkhd` and `mdhd` duration values (which should be identical for non-edited or non-fragmented files). Rather, it’s because they are calculated using different timescales. The `mvhd` box defines a global movie timescale, which is used for the track's `tkhd` duration. Meanwhile, each track’s `mdhd` box defines its own timescale specific to its content type, which we now use for more accurate frame rate calculation.

PiperOrigin-RevId: 676046744
2024-09-18 10:42:11 -07:00
rohks
8799bf4bfe Format Format.frameRate to two decimal places before dumping
PiperOrigin-RevId: 675996979
2024-09-18 08:14:52 -07:00
ibaker
0b86f89498 Guard DrmSession.requiresSecureDecoder calls with state checks
This method is documented that it may only be called in `STATE_OPENED`
or `STATE_OPENED_WITH_KEYS`. It's possible for it to be called in other
states (like `STATE_ERROR`) without this guard.

Previously this didn't cause issues, but since 9d62845c45
we assume that the `sessionId` is non-null in this method, which results
in an `IllegalStateException` when the documented state restriction is
ignored.

PiperOrigin-RevId: 675969256
2024-09-18 06:41:32 -07:00
kimvde
caf70e54db Fix outdated Transformer Javadoc
PiperOrigin-RevId: 675942348
2024-09-18 04:56:51 -07:00
ibaker
3e8ecbf564 Remove @DoNotInline annotations
This is no longer needed now our `compileSdk` implies a new-enough AGP
which does this out-lining automatically via R8. See also
https://issuetracker.google.com/345472586#comment7

There's no plan to remove the `ApiXXX` classes, but no new ones need
to be added.

PiperOrigin-RevId: 675940634
2024-09-18 04:47:39 -07:00
kimvde
2951a2599c Apply all video Composition effects to single sequence exports
PiperOrigin-RevId: 675933601
2024-09-18 04:18:55 -07:00
claincly
fd3d8e1782 Add RATE_UNSET option to encoder performance setting
This is to allow not setting the MediaFormat OPERATING_RATE and PRIORITY
altogether. The current behvaiour, if left the value `UNSET`, it'll apply the
our optimizations, but apps might want to disable this optimization.

PiperOrigin-RevId: 675923909
2024-09-18 03:40:13 -07:00
michaelkatz
f0fb386224 Add workaround for Galaxy Tab S7 FE device PerformancePoint issue
The Galaxy Tab S7 FE has a device issue that causes 60fps secure H264 streams to be marked as unsupported. This CL adds a workaround for this issue by checking the CDD required support for secure H264 in addition to the current check on standard H264. If the provided performance points do not cover the CDD requirement of support 720p H264 at 60fps, then it falls back to using legacy methods for checking frame rate and resolution support.

Issue: androidx/media#1619
PiperOrigin-RevId: 675920968
2024-09-18 03:29:10 -07:00
claincly
69da26935e Fix logic that detects the last media item in Sequence
After the change in a879bc2154, the Sequence won't have repeated
EditedMediaItems. Thus if the sequence is looping, the last EditedMediaItems
in the Sequence object might not corresponds to the last item in the "logical"
sequence.

PiperOrigin-RevId: 675912197
2024-09-18 02:54:11 -07:00
ibaker
3facfbf542 Assert baseDataSourceFactory non-null in DefaultDataSource.Factory
This gives a faster/clearer failure for Issue: androidx/media#1718.

PiperOrigin-RevId: 675896262
2024-09-18 02:00:03 -07:00
hoisie
dc66c9160c Update some APIs to Use real types in ShadowNotificationManager
NotificationChannel and NotificationChannelGroup are public APIs that were
added in Android O, so at this point it is okay to have them appear in API
signatures.

PiperOrigin-RevId: 675756005
2024-09-17 16:47:36 -07:00
Googler
087e75850e Add suitable output checker tests relevant for API 35+ in media3-ui
PiperOrigin-RevId: 675678257
2024-09-17 13:05:43 -07:00
sheenachhabra
acb8e71c6e Set hasMuxedTimestampZero to true only when its muxed
The muxer might not have accepted the first sample, if it
is waiting for audio track.

This bug causes issue when

1. VideoSampleExporter gives first sample (timestamp = 0) to the muxer.
2. Muxer does not write it because its waiting for audio track.
3. The video pipleline has processed all the sample and they are ready
to be consumed.
4. VideoSampleExporter fetches the next available sample from encoder (which is still with timestamp = 0) but it changes its timestamp to last timestamp because VideoSampleExporter thinks it has muxed the sample at timestamp zero, but in reality it hasn't. This is because the flag `hasMuxedTimestampZero` is set when queueing the input, rather than actually muxing the input.

This scenario can happen when video is processed much faster than
the audio.

PiperOrigin-RevId: 675565603
2024-09-17 07:53:22 -07:00
Googler
e1c4ecf2d3 Add suitable output checker tests relevant for API 35+ in ExoPlayerTest
PiperOrigin-RevId: 675547156
2024-09-17 06:45:15 -07:00
rohks
9bc89ae989 Ensure track indices are only added when samples are committed
Previously, track IDs were added to `trackIndicesPerSampleInQueuedOrder`
even when the sample was not committed. This caused issues where attempts
to read samples from the `SampleQueue` returned `C.RESULT_READ_NOTHING`,
which led to an exception being thrown due to the assumption that samples
were available to read.

This fix updates the logic to track sample commits by comparing the write index before and after calling `SampleQueue.sampleMetadata`. Track indices are only added if the sample was committed, ensuring accurate sample handling and avoiding exceptions.

PiperOrigin-RevId: 675526115
2024-09-17 05:27:51 -07:00
ivanbuper
873d485056 Rollback of e88d6fe459
PiperOrigin-RevId: 675525508
2024-09-17 05:25:07 -07:00
kimvde
0ea229d795 Remove limit of 2 sequences in CompositionPlayer
The player supports more than 2 audio sequences

PiperOrigin-RevId: 675493637
2024-09-17 03:20:28 -07:00
Copybara-Service
6632e64007 Merge pull request #1653 from theskyblockman:main
PiperOrigin-RevId: 675277275
2024-09-16 13:52:55 -07:00
oceanjules
25bb8e411b Make setFullscreenButtonState UnstableApi 2024-09-16 20:19:55 +01:00
oceanjules
9b75523fd9 Add and format RELEASENOTES 2024-09-16 20:05:02 +01:00
oceanjules
5536b73a08 Format with google-java-format 2024-09-16 20:05:02 +01:00
theskyblockman
370a4c0035 Deleted redundant check 2024-09-16 20:05:02 +01:00
theskyblockman
c42f53fcc9 Edited condition to exit updateIsFullscreen quickly 2024-09-16 20:05:02 +01:00
theskyblockman
4a4b3a3bc0 - Rephrased/Expanded javadocs for fullscreen methods
- Replaced all occurrences of "FullScreen" to "Fullscreen"
2024-09-16 20:05:02 +01:00
theskyblockman
49af9228db Added public-facing calls to set whether to show [fullScreenButton] or [minimalFullScreenButton] in PlayerView calling PlayerControlView 2024-09-16 20:05:02 +01:00
sheenachhabra
47d45a82ca Change the default value of lastSampleDurationBehavior
to
LAST_SAMPLE_DURATION_BEHAVIOR_SET_FROM_END_OF_STREAM_BUFFER_OR_DUPLICATE_PREVIOUS

This CL also combines LAST_SAMPLE_DURATION_BEHAVIOR_SET_FROM_END_OF_STREAM_BUFFER
and LAST_SAMPLE_DURATION_BEHAVIOR_DUPLICATE_PREVIOUS.

The reason for combining the two enums is that, when the option
to use END_OF_STREAM_BUFFER is selected and if the EOS buffer is
not provided then the muxer anyways fallbacks to duplicate
duration behavior.

The last sample with 0 durations seems less useful so
change the default behavior to non-zero duration.
This will also match the behavior with MediaMuxer.

PiperOrigin-RevId: 675189932
2024-09-16 10:02:10 -07:00
Copybara-Service
0ce6d9620e Merge pull request #1703 from colinkho:fwd-renderer
PiperOrigin-RevId: 675122802
2024-09-16 06:25:27 -07:00
claincly
a879bc2154 Rewrite sequence duration matching on MediaSource level
This simplifies the later handling of speed adjusted media.

PiperOrigin-RevId: 675114587
2024-09-16 05:55:00 -07:00
Rohit Singh
c8aa122e8a Change from internal review 2024-09-16 13:34:21 +01:00
Rohit Singh
11aea9b34b Add RELEASENOTES 2024-09-16 13:15:40 +01:00
Rohit Singh
9975175700 Forward default methods 2024-09-16 13:07:36 +01:00
Rohit Singh
3c6f1f1e77 Add copyright text and move test to correct package 2024-09-16 12:36:03 +01:00
Rohit Singh
8ca12338f6 Format with google-java-format 2024-09-16 12:31:48 +01:00
Colin Kho
62aef96b7d Format code using google java format 2024-09-16 12:31:48 +01:00
Colin Kho
72e39c91c4 Denote ForwardingRenderer as subject to change 2024-09-16 12:31:48 +01:00
Colin Kho
72f26d79f6 Added a forwarding class for Renderer to support composing custom behavior on Metadata & Text Renderers 2024-09-16 12:31:48 +01:00
michaelkatz
e938d27846 Fix typo in release notes
PiperOrigin-RevId: 675070722
2024-09-16 02:54:20 -07:00
Googler
011659b326 Add profile and level for H263 codec.
To support for 3gpp h263 codec in Mp4Muxer currently profile and level is hardcoded and provided to h263 box. Parse profile and level from MediaFormat and use those value to write h263 box.

PiperOrigin-RevId: 675004590
2024-09-15 22:09:38 -07:00
claincly
6c92402fbb Re-enable audio tests
The tests were flaky because CompositionPlayer registers audio sequences'
formats to the audio pipeline in first-come-first-serve order. With the change
in bc8d82355f, the audio format is deterministic.

The test is turned off in 060356ea00

PiperOrigin-RevId: 674261801
2024-09-13 05:44:28 -07:00
tianyifeng
72ae454f67 Use buffered duration from start position to control preload progress
`PreloadMediaSource` allows to have a `startPositionUs` passed when `preload` is called, then in `PreloadControl.onContinueLoadingRequested`, it can be more intuitive to see the buffered duration rather than the absolute buffered position as the preload progress. Similar in `DefaultPreloadManager`, we haven't allowed the apps to set a custom start position for individual sources though, once we add this support, using the "duration from the start position" than the absolute position will be less error-prone, otherwise, it can run into a case that the position that the apps set is smaller than the start position.

PiperOrigin-RevId: 674251362
2024-09-13 05:05:39 -07:00
Copybara-Service
023fd32cb1 Merge pull request #1138 from Lavamancer:bugfix/rtsp_message_util_encoded_authority
PiperOrigin-RevId: 674239756
2024-09-13 04:16:05 -07:00
Googler
ff656012a8 Update the unisoc blocklist
PiperOrigin-RevId: 674101970
2024-09-12 19:33:13 -07:00
claincly
bc8d82355f Block secondary audio processing until primary format is configured
PiperOrigin-RevId: 673961235
2024-09-12 12:42:09 -07:00
ivanbuper
e88d6fe459 Fix truncation error acumulation for Sonic's resampling algorithm
Sonic would accumulate truncation errors on float to int conversions
that caused the final output sample count to drift noticeably, by
hundreds of samples on streams of a few minutes of length. The fix now
keeps track of the truncation error and compensates for it.

Other small fixes include eliminating lossy operations (e.g. int
division) and using doubles instead of floats for resampling where
helpful.

This CL also introduces `SonicParameterizedTest`, which helps test
resampling on an arbitrary number of randomly generated parameters,
with random sample data. `SonicParameterizedTest` uses `BigDecimal`s
for calculating sample count values, as to avoid precision issues with
large sample counts.

PiperOrigin-RevId: 673852768
2024-09-12 08:14:25 -07:00
Googler
3caebbf5ad Fix erroneous use of "cpu_features" in AV1 JNI exports.
`CPU_FEATURES_COMPILED_ANY_ARM_NEON` is always defined when `CPU_FEATURES_ARCH_ARM` is but it can be defined as `0` or `1` ([cpu_features source](8e60d3f9be/include/cpu_features_macros.h (L237-L245))). This patch makes sure to use the value of `CPU_FEATURES_COMPILED_ANY_ARM_NEON` instead of whether it is defined or not.

PiperOrigin-RevId: 673837522
2024-09-12 07:30:47 -07:00
kimvde
ce98b7d379 Rename SequencePlayerRenderersWrapper
Also remove reference to SequencePlayerRenderersWrapper in inner
classes to make them effectively static.

PiperOrigin-RevId: 673720251
2024-09-12 00:52:17 -07:00
microkatz
661f3de325 Added note in release notes 2024-09-12 04:56:57 +00:00
microkatz
61343cd75f Format with google-java-format 2024-09-12 04:47:05 +00:00
Lavamancer
17e0fd22b1 Fixed removal of user info for URLs that contain encoded @ characters 2024-09-12 04:47:05 +00:00
rohks
f133e8d1f2 Fix preroll sample handling for non-keyframe media start positions
When processing edit lists in MP4 files, the media start position may be a non-keyframe. To ensure proper playback, the decoder must preroll to the preceding keyframe, as these preroll samples are essential for decoding but are not rendered.

Issue: google/ExoPlayer#1659

#cherrypick

PiperOrigin-RevId: 673457615
2024-09-11 11:02:39 -07:00
rohks
d9a678483b Refine sample presentation time validation for negative PTS workaround
In case of negative PTS workaround, instead of disallowing all cases where samples are not in presentation order, we now validate that the first sample's presentation time is the smallest. This adjustment allows for correctly applying an offset to ensure all samples have a presentation time >= 0.

#cherrypick

PiperOrigin-RevId: 673434793
2024-09-11 10:04:16 -07:00
rohks
bb3d055191 Do not drop negative timestamp video buffers during transmuxing
Prevents discarding video buffers with key frame which are required for decoding.

#cherrypick

PiperOrigin-RevId: 673375261
2024-09-11 07:00:02 -07:00
kimvde
8271a5f920 Rename CompositingVideoSinkProvider and PreviewAudioPipeline
The components are mirror components for video and audio so they should
have a matching name

PiperOrigin-RevId: 673357081
2024-09-11 05:49:35 -07:00
sheenachhabra
4be5b74366 Read NAL unit data as 4 byte integer
When converting NAL units from AnnexB to Avcc format,
one byte at a time was read. In fact many bytes were read
multiple times due to suboptimal logic.

Changed the logic to read 4 bytes at once and also to avoid
reading same bytes again.

This improved the time taken for writing a batch of 30
samples from 40ms to 20ms.

PiperOrigin-RevId: 673025781
2024-09-10 10:57:22 -07:00
sheenachhabra
35dc10aac8 Fix a bug to read last 3 bytes in AnnexBUtils
In the current implementation due to missing "="
operator, last three bytes were not checked for
000 or 001 sequence.

In sample_no_bframes file, few samples has extra 0 at the end.
It was working fine with the bug because muxer was writing some
harmless 0 at the end.

PiperOrigin-RevId: 672994054
2024-09-10 09:32:56 -07:00
jbibik
8bfa7e2de1 Make StreamVolumeManager take streamType in constructor
Avoids the dispatch of listener notifications of stream type/device volume change during construction of ExoPlayer. That was problematic because we end up blocking on `constructorFinished.blockUninterruptible()`

Issue: androidx/media#1692
PiperOrigin-RevId: 672965552
2024-09-10 08:05:21 -07:00
kimvde
a53ea621bb Stop rejecting frames later in ExternalTextureManager
If the task executor handles an available frame (task submitted in the
SurfaceTexture listener) between the call to registerInputFrame() and
the execution of the task submitted in the method (in this CL), it
should be rejected.

PiperOrigin-RevId: 672903756
2024-09-10 04:29:48 -07:00
sheenachhabra
327b1c8ad8 Move getCodecProfileAndLevel to CodecSpecificDataUtil
`Muxer` module needs to use this method, hence moved to common.

This CL also makes `getHevcProfileAndLevel` public because this is used
in `MediaCodecUtil`.

PiperOrigin-RevId: 671739166
2024-09-06 06:52:29 -07:00
ivanbuper
a1357befff Add Kotlin dependencies to missing_aar_type_workaround.gradle
#cherrypick

PiperOrigin-RevId: 671736852
2024-09-06 06:40:41 -07:00
aquilescanta
4ea58a133e Populate DeviceInfo in CastPlayer using MediaRouter2 info
This enables linking the media session to a routing session.

Issue: androidx/media#1056
PiperOrigin-RevId: 671425490
2024-09-05 10:38:08 -07:00
kimvde
a1d2310170 Fix stuck player after seek
Seeking was causing the player to hang in the following scenario:
1. The surfaceTexture's onFrameAvailableListener is called in
   ExternalTextureManager to notify that a new frame is available.
2. This call submits a task on the GL thread.
3. A seek is performed and DefaultVideoFrameProcessor.flush() is called
   before the task submitted in 2 is executed.
4. DefaultVideoFrameProcessor.flush() flushes the task executor, so that
   the task submitted in 2 never gets executed.
5. Once the seek is over, the first frame is registered and rendered on
   the surface texture.
6. Playback hangs because the onFrameAvailableListener is never called
   for this new frame. This is because surfaceTexture.updateTexImage()
   was never called on the frame that became available in 1.

This fix is making sure that the task submitted in 2 always gets executed.

Issue: androidx/media#1535
PiperOrigin-RevId: 671389215
2024-09-05 08:54:55 -07:00
ibaker
6822818549 Fix Format.toLogString handling of new Format.labels field
Before this, because `Label.toString()` isn't implemented, the logged info
wasn't that useful:

```
labels=[androidx.media3.common.Label@6caac039]
```

With this change it's more useful:

```
labels=[en: english]
```
PiperOrigin-RevId: 671029474
2024-09-04 11:02:36 -07:00
aquilescanta
a00c446529 Do not clear the timeline after the Cast receiver disconnects
The goal is to enable the app to fetch the timeline after a
disconnection in order to prepare and resume local playback.

PiperOrigin-RevId: 671022044
2024-09-04 10:42:53 -07:00
ibaker
87bd9ba585 Make PlayerView Compose workaround opt-in
The workaround causes issues with XML-based shared transitions, so we
can't apply it unilaterally.

Issue: androidx/media#1594

Issue: androidx/media#1237
PiperOrigin-RevId: 670960693
2024-09-04 07:24:27 -07:00
jbibik
c851464063 Add a note on not using PlayerControlView as a standalone component
We have a tracking bug Issue: androidx/media#514 for supporting it, but issues like Issue: androidx/media#1542 still show that users stumble over it.

PiperOrigin-RevId: 670955189
2024-09-04 07:02:17 -07:00
ibaker
0933f561b7 Move MCR CryptoException handling to top-level render() method
Handling for `MediaCodec.CryptoException` was originally added only
around calls to `MediaCodec.queueSecureInputBuffer` and
`queueInputBuffer` (because these are the only methods that can throw
this exception). When asynchronous interaction with `MediaCodec` was
added in <unknown commit>, exceptions from `MediaCodec` started being stored
and bubbled out of **later** interactions with `MediaCodecAdapter`. This
means that `MediaCodecRenderer` can now see `CryptoException` thrown
from a different method, like
`MediaCodecAdapter.dequeueInputBufferIndex()`, and this ends up missing
the `catch (CryptoException)` code in `MediaCodecRenderer`. This results
in an "unexpected runtime error" stack trace like [A].

This change fixes the stack trace to:
1. Make it a "renderer exception" instead of "unexpected runtime error"
2. Include the correct DRM error code -> `@PlaybackException.ErrorCode`
   mapping.

You can see the corrected stack trace below [B].

-----

[A] (synthesized from manually throwing a `CryptoException` from
`AsynchronousMediaCodecBufferEnqueuer#doQueueSecureInputBuffer`)

```
playerFailed [eventTime=11.56, mediaPos=10.35, window=0, period=0, errorCode=ERROR_CODE_UNSPECIFIED
  androidx.media3.exoplayer.ExoPlaybackException: Unexpected runtime error
      at androidx.media3.exoplayer.ExoPlayerImplInternal.handleMessage(ExoPlayerImplInternal.java:729)
      at android.os.Handler.dispatchMessage(Handler.java:103)
      at android.os.Looper.loopOnce(Looper.java:232)
      at android.os.Looper.loop(Looper.java:317)
      at android.os.HandlerThread.run(HandlerThread.java:85)
  Caused by: android.media.MediaCodec$CryptoException: Test error message
      at androidx.media3.exoplayer.mediacodec.AsynchronousMediaCodecBufferEnqueuer.doQueueSecureInputBuffer(AsynchronousMediaCodecBufferEnqueuer.java:232)
      at androidx.media3.exoplayer.mediacodec.AsynchronousMediaCodecBufferEnqueuer.doHandleMessage(AsynchronousMediaCodecBufferEnqueuer.java:196)
      at androidx.media3.exoplayer.mediacodec.AsynchronousMediaCodecBufferEnqueuer.access$000(AsynchronousMediaCodecBufferEnqueuer.java:47)
      at androidx.media3.exoplayer.mediacodec.AsynchronousMediaCodecBufferEnqueuer$1.handleMessage(AsynchronousMediaCodecBufferEnqueuer.java:93)
      at android.os.Handler.dispatchMessage(Handler.java:107)
      at android.os.Looper.loopOnce(Looper.java:232) 
      at android.os.Looper.loop(Looper.java:317) 
      at android.os.HandlerThread.run(HandlerThread.java:85) 
```

[B]

```
Playback error
  androidx.media3.exoplayer.ExoPlaybackException: MediaCodecAudioRenderer error, index=1, format=Format(0, null, null, audio/mp4a-latm, mp4a.40.2, 134359, en, [-1, -1, -1.0, null], [2, 44100]), format_supported=YES
      at androidx.media3.exoplayer.ExoPlayerImplInternal.handleMessage(ExoPlayerImplInternal.java:649)
      at android.os.Handler.dispatchMessage(Handler.java:103)
      at android.os.Looper.loopOnce(Looper.java:232)
      at android.os.Looper.loop(Looper.java:317)
      at android.os.HandlerThread.run(HandlerThread.java:85)
  Caused by: android.media.MediaCodec$CryptoException: Test error message
      at androidx.media3.exoplayer.mediacodec.AsynchronousMediaCodecBufferEnqueuer.doQueueSecureInputBuffer(AsynchronousMediaCodecBufferEnqueuer.java:232)
      at androidx.media3.exoplayer.mediacodec.AsynchronousMediaCodecBufferEnqueuer.doHandleMessage(AsynchronousMediaCodecBufferEnqueuer.java:196)
      at androidx.media3.exoplayer.mediacodec.AsynchronousMediaCodecBufferEnqueuer.access$000(AsynchronousMediaCodecBufferEnqueuer.java:47)
      at androidx.media3.exoplayer.mediacodec.AsynchronousMediaCodecBufferEnqueuer$1.handleMessage(AsynchronousMediaCodecBufferEnqueuer.java:93)
      at android.os.Handler.dispatchMessage(Handler.java:107)
      at android.os.Looper.loopOnce(Looper.java:232) 
      at android.os.Looper.loop(Looper.java:317) 
      at android.os.HandlerThread.run(HandlerThread.java:85) 
```

PiperOrigin-RevId: 670951229
2024-09-04 06:44:21 -07:00
sheenachhabra
e27c7d5d45 Use simpler timestamps in tests for readability
PiperOrigin-RevId: 670907537
2024-09-04 03:35:54 -07:00
rohks
6e1bab03bd Add Mp4PlaybackTest for sample with edit list (edts box)
PiperOrigin-RevId: 670572646
2024-09-03 08:43:33 -07:00
sheenachhabra
a7788e0d60 Rename last sample duration behaviour enums
This is to improve readability.

PiperOrigin-RevId: 670563611
2024-09-03 08:15:23 -07:00
dancho
1c61fbadf7 Downscale bitmaps during decoding in Transformer
Limit input image size in Transformer to be less than 4096x4096.
For very large images, this can reduce memory usage substantially,
and stays away from `GL_MAX_TEXTURE_SIZE` - often 4096

PiperOrigin-RevId: 670555939
2024-09-03 07:53:13 -07:00
ivanbuper
9562c976a9 Bump Media3 version to 1.5.0-alpha01
PiperOrigin-RevId: 670535221
2024-09-03 06:40:01 -07:00
ivanbuper
e16b4fff8d Update release notes for Media3 1.5.0-alpha01 release
PiperOrigin-RevId: 670523759
2024-09-03 06:02:37 -07:00
kimvde
af61c03e09 Move ExoPlayerEffectPlaybackSeekTest out of performance directory
These tests do not test performance. Moving them out of this directory
ensures they are run on emulators and on all physical devices.

PiperOrigin-RevId: 670505992
2024-09-03 04:54:12 -07:00
kimvde
af2f9cb37f Increase ExoplayerEffectPlaybackSeekTest time out
This test will be moved so that it is run on emulators, which are
generally slower to run.

PiperOrigin-RevId: 670495551
2024-09-03 04:13:24 -07:00
sheenachhabra
95f69b649d Use InAppMuxer in tests for API < 25
MediaMuxer doesn't support B-frame before API 25.

The fix is added only in those test which appeared in triage failure.
It can be added to other tests as they are discovered.

PiperOrigin-RevId: 670480966
2024-09-03 03:18:01 -07:00
ivanbuper
ebb550a9f1 Fix WrongConstant lint failure for IamfDecoder#OUTPUT_PCM_ENCODING
To avoid `WrongConstant` failures with methods that expect
`C.@PcmEncoding`, `OUTPUT_PCM_ENCODING` now points to the constant in
`C` instead of `AudioFormat`.

#cherrypick

PiperOrigin-RevId: 670251463
2024-09-02 10:20:55 -07:00
ibaker
4562c781ed Update minSdk values in UtilTest
These were missed when upgrading to both SDK 19 and 21, but they now
cause failures like:

```
Caused by: java.lang.RuntimeException: Failed to parse package buildout/intermediates/apk_for_local_test/debugUnitTest/packageDebugUnitTestForUnitTest/apk-for-local-test.ap_: buildout/intermediates/apk_for_local_test/debugUnitTest/packageDebugUnitTestForUnitTest/apk-for-local-test.ap_ (at Binary XML file line #20): Requires newer sdk version #21 (current version is #19)
    at org.robolectric.shadows.ShadowPackageParser.callParsePackage(ShadowPackageParser.java:61)
    ... 20 more
```

#cherrypick

PiperOrigin-RevId: 670241471
2024-09-02 09:34:15 -07:00
samrobinson
1d9276863c Ensure force silence SampleConsumerWrapper has the right track type.
PiperOrigin-RevId: 670226122
2024-09-02 08:30:46 -07:00
dancho
207684ca66 Prototype frame extraction based on analyzer mode
Make ByteBufferGlEffect public.
Build a speed test, and end to end test that verify
frames can be copied to CPU-accessible ByteBuffer

PiperOrigin-RevId: 670213343
2024-09-02 07:34:33 -07:00
sheenachhabra
0843444a34 Fix order of elements in FrameworkMuxer.java
PiperOrigin-RevId: 670205944
2024-09-02 07:04:00 -07:00
claincly
060356ea00 Temporarily disable multi-sequence audio playback test
Disable assertions and make sure playback passes.

The flake is caused by having different sequences starting with MediaItems of
different audio format, and it's undefined behaviour as to which one CompositionPlayer chooses to use.

PiperOrigin-RevId: 670195113
2024-09-02 06:16:43 -07:00
sheenachhabra
f0fa7640ca Add support for setting video duration in InAppMuxer
Similar support was previously added in FrameworkMuxer.

PiperOrigin-RevId: 670193986
2024-09-02 06:11:32 -07:00
kimvde
748e4e5230 Fix hanging ExoPlayerPlaybackSeekTest
The test uses a video renderer to count the number of frames and could
time out if some frames were dropped.

PiperOrigin-RevId: 670181693
2024-09-02 05:21:01 -07:00
dancho
b3b4c80641 Release the analyzer mode placeholder surface
PiperOrigin-RevId: 670179138
2024-09-02 05:09:30 -07:00
ktrajkovski
b0213c870b Update release notes to contain IAMF support.
PiperOrigin-RevId: 670160408
2024-09-02 03:57:39 -07:00
ibaker
551cbadafc Gracefully handle unexpected non-MP3 trailing data
The `bear-cbr-no-seek-table-trailing-garbage.mp3` test file was generated by appending 150kB of `0xDEADBEEF` onto the end of `bear-cbr-variable-frame-size-no-seek-table.mp3`.

Issue: androidx/media#1563

#cherrypick

PiperOrigin-RevId: 670131828
2024-09-02 02:10:13 -07:00
Copybara-Service
854566dbfe Merge pull request #1371 from v-novaltd:dsparano-exo207
PiperOrigin-RevId: 669352191
2024-08-30 09:35:32 -07:00
samrobinson
5eba716410 Add a composition export dump test with a shorter second sequence.
PiperOrigin-RevId: 669348374
2024-08-30 09:20:58 -07:00
sheenachhabra
4e858f7260 Add support for setting last sample duration in Mp4Muxer
PiperOrigin-RevId: 669340763
2024-08-30 08:53:36 -07:00
microkatz
f1654732a6 Added release note for change 2024-08-30 13:47:43 +00:00
sheenachhabra
791483f2d3 Remove TrackMetadataProvider interface
This interface was used by Boxes.moov. This CL removes the interface and just uses the Track object directly.

Since Track is package-private it seems fine to use it directly.
The drawback with interface is that, with every new field addition in the
Track class, we need to update the interface as well (if we need to access that field for moov box).

PiperOrigin-RevId: 669295399
2024-08-30 05:47:07 -07:00
sheenachhabra
613c7a6aa7 Change adjustLastSampleDuration() to getLastSampleDurationVu()
This is a no-op change.

PiperOrigin-RevId: 669283958
2024-08-30 04:55:40 -07:00
dancho
dc9854cc5b Add GlRect helper class
Adds a class that represents an image rectangle
in OpenGL coordinate convention.

android.graphics.Rect puts (0, 0) as the top-left corner:
it enforces `Rect.top <= Rect.bottom` and this matches
`android.graphics.Bitmap` coordinates: docs https://developer.android.com/reference/android/graphics/Rect

This is different from OpenGL coordinates where (0, 0) is
at the bottom-left corner. I.e. GlRect.bottom <= GlRect.top: docs https://registry.khronos.org/OpenGL-Refpages/es3.0/html/glReadPixels.xhtml

The reason for this change is to allow a public API GlRect
getScaledRegion() which selects a region of pixels of a GL texture
to be copied to CPU memory.

PiperOrigin-RevId: 669231826
2024-08-30 01:13:22 -07:00
sheenachhabra
388d1f17b9 Clean up comments in Boxes.java
The CL aims to

1. Shorten unnecessary lengthy chatty comments.
2. Remove dead TODOs.
3. nit fixes for comment style consistency.
4. Remove usage of "we" in the comments.
5. Media3 muxer does not need to mention the behaviour of framework muxer
unless its required for some purpose, so remove them.

PiperOrigin-RevId: 668985875
2024-08-29 10:37:38 -07:00
Copybara-Service
39ed9cf88d Merge pull request #1652 from MiSikora:ms/vtt-speaker
PiperOrigin-RevId: 668976037
2024-08-29 10:08:13 -07:00
Ian Baker
c78ac6e784 Remove intdef value list from javadoc 2024-08-29 16:45:10 +01:00
Copybara-Service
68f55461c0 Merge pull request #1659 from colinkho:drm-util
PiperOrigin-RevId: 668919756
2024-08-29 06:51:13 -07:00
kimvde
37561c829f Fix and refactor logic to remove all frames in ExternalTextureManager
The existing logic was not working sometimes because:

1. The repeated scheduling in releaseAllFramesFromMediaCodec was
starving the thread on which the SurfaceTexture frameAvailableListener
was called.

2. The case where a pending frame arrives on the surface after flush
finishes executing was not handled.

The consequence of both problems is that availableFrameCount ended up
being > pendingFrames.size().

PiperOrigin-RevId: 668916256
2024-08-29 06:37:20 -07:00
Copybara-Service
e30161656e Merge pull request #1667 from JaroslavHerber:patch-1
PiperOrigin-RevId: 668905162
2024-08-29 05:57:59 -07:00
tonihei
41a56daab7 Code formatting 2024-08-29 13:48:41 +01:00
Colin Kho
a509033a5c Correct grammar and format javadoc on DrmUtil.executePost 2024-08-29 13:19:27 +01:00
Colin Kho
4ee34cc00e Refactor HttpMediaDrmCallback's executePost into a shared utility method within DrmUtil 2024-08-29 13:19:27 +01:00
Jaro
02fa4b0f9c Remove obsolete semicolon 2024-08-29 12:25:19 +01:00
ibaker
05cbbffbd7 Add a space in the ParserException message
PiperOrigin-RevId: 668870991
2024-08-29 03:51:40 -07:00
kimvde
3587afc9d7 Move CompositionPlayerSeekTest out of performance directory
These tests do not test performance. Moving them out of this directory
ensures they are run on emulators and on more than 1 physical device.

PiperOrigin-RevId: 668859017
2024-08-29 03:14:12 -07:00
Ian Baker
4d9ad5a6e0 Add release note 2024-08-29 10:27:10 +01:00
Ian Baker
a4aa975a26 Reformat and tweak javadoc 2024-08-29 10:25:06 +01:00
Michał Sikora
cd47e2a134 Remove redundant test 2024-08-29 10:25:06 +01:00
Michał Sikora
24bbe6d921 Rename VTT voice span speakerName to name 2024-08-29 10:25:06 +01:00
Michał Sikora
ce52fc77ec Remove VTT voice span classes 2024-08-29 10:25:06 +01:00
Michał Sikora
108a5ca2f5 Remove language span marker interface 2024-08-29 10:25:06 +01:00
Michał Sikora
d6f08a6237 Add VTT voice spans to cues 2024-08-29 10:25:06 +01:00
tonihei
e8664dbc8e Report initial discontinuity for DASH periods that require preroll
DASH periods don't have to start at the beginning of a segment. In
these cases, they should report an initial discontinuity to let the
player know it needs to expect preroll data (e.g. to flush renderers)

This information is only available in the ChunkSampleStream after
loading the initialization data, so we need to check the sample
streams and tell them to only report discontinuities at the very
beginning of playback. All other position resets are triggered by
the player itself and don't need this method.

Issue: androidx/media#1440
PiperOrigin-RevId: 668831563
2024-08-29 01:57:15 -07:00
kimvde
8367e420ad Import correct nullable annotation
PiperOrigin-RevId: 668521379
2024-08-28 10:54:29 -07:00
dancho
5c2dc7ed4e Add ByteBufferGlEffect.Image for easier format conversion
PiperOrigin-RevId: 668506831
2024-08-28 10:22:01 -07:00
kimvde
070e8217ac Report swallowed exceptions in ExternalTextureManager
The error was swallowed if
ExternalTextureManager.removeAllSurfaceTextureFrames was throwing.

PiperOrigin-RevId: 668480565
2024-08-28 09:14:53 -07:00
tianyifeng
c2e81052e8 Fix flakiness in ExoPlayerTest
In the flaky test `ExoPlayerTest.loading_withLargeAllocationCausingOom_playsRemainingMediaAndThenThrows`, it is indeterministic that when the message `MSG_IO_EXCEPTION` from the loader thread will arrive on the playback looper. If it arrives after `MSG_PERIOD_PREPARED`, then the period can continue loading and get the three samples written to the `SampleQueue` before the intentional OOM surfacing to the `ExoPlayerImplInternal`, otherwise, the OOM will be detected by `ExoPlayerImplInternal` very early and the player disallows to load three samples, which will cause the assertion to fail.

As we are expecting the three samples to play until the playback fails, we should assume that the `Loader` encounters the OOM after those samples loaded, thus we need to put this trigger a bit later until the `SampleStreamItem`s are handled by the `FakeSampleStream`. This could be checked by the return value of `FakeMediaPeriod.continueLoading` (super class implementation). However, `FakeMediaPeriod.continueLoading` originally always returns `true`, which is not aligned with the javadoc of `MediaPeriod.continueLoading`:

"return `true` if progress was made, meaning that `getNextLoadPositionUs()` will return a different value than prior to the call, `false` otherwise."

then we should also modify that logic.

PiperOrigin-RevId: 668438316
2024-08-28 07:16:29 -07:00
microkatz
0ac26c4004 Format with google-java-format 2024-08-28 12:41:49 +00:00
Daniele Sparano
7473156853 Fix output pixel aspect ratio and add test for it 2024-08-28 12:41:49 +00:00
Daniele Sparano
f0463bff8a Set pixel aspect ratio from output media format if set 2024-08-28 12:41:49 +00:00
samrobinson
9c5ea4f1ba Assert silent bytes are 0 in AudioGraphInputTest
PiperOrigin-RevId: 668403467
2024-08-28 05:18:37 -07:00
samrobinson
84f4c7bbcc Create and assert against dump files in ParameterizedAudioExportTest.
PiperOrigin-RevId: 668002146
2024-08-27 08:43:27 -07:00
sheenachhabra
ebd60acc95 Rename LAST_FRAME_DURATION_BEHAVIOR to LAST_SAMPLE_DURATION_BEHAVIOR
The original idea was to set duration for the last video frame, but this behavior actually applies to all tracks.

PiperOrigin-RevId: 667990099
2024-08-27 08:08:25 -07:00
tonihei
d0676245b5 Add AnalyticsListener.onRendererReadyChanged
This callback allows listeners to track when individual renderers
allow or prevent playback from being ready. For example, this is useful
to figure out which renderer blocked the playback the longest.

PiperOrigin-RevId: 667970933
2024-08-27 07:08:42 -07:00
claincly
36d61000fd Reorder the assetions in tests
So it's more clear what's actually broke in the error log.

PiperOrigin-RevId: 667964963
2024-08-27 06:43:58 -07:00
kimvde
a4d0735d4c Fix player hanging when seeking at MediaItem transition
Before this CL, the video sink was stuck if a flush was executed:
- after VideoSink.onInputStreamChanged, which is setting
  pendingInputStreamBufferPresentationTimeUs and
- before the previous stream was fully rendered.

This is because pendingInputStreamBufferPresentationTimeUs was not reset
to TIME_UNSET when flushing the sink, so that the sink was still waiting
for the last frame of the previous stream to be rendered in
handleInputFrame/Bitmap.

PiperOrigin-RevId: 667924517
2024-08-27 04:00:46 -07:00
dancho
c4930c4bb6 Default to OpenGL 3.0 context in DVFP
OpenGL ES 3.0 likely can be used since Android 18.
Moving to a higher version context more often can make
sharing GL context easier for apps

PiperOrigin-RevId: 667915331
2024-08-27 03:23:54 -07:00
dancho
563eb963fd Make ByteBufferConcurrentEffect asynchronous
* Changes to GlUtil to manage Pixel Buffer Objects and asynchronous
GPU -> CPU glReadPixels
* Make ByteBufferConcurrentEffect non-blocking

PiperOrigin-RevId: 667908805
2024-08-27 02:58:51 -07:00
sheenachhabra
52aeffbb3b Remove TODO for empty samples in muxer
There is no reason to write the empty samples so keep
the behaviour same as MediaMuxer

PiperOrigin-RevId: 667495861
2024-08-26 01:28:13 -07:00
claincly
2b031484fe Allow looping sequences in CompositionPlayer
PiperOrigin-RevId: 666793658
2024-08-23 07:54:13 -07:00
dancho
ee93a9832e Add ByteBufferGlEffect for easier non-GPU video effects
* new ByteBufferGlEffect GlEffect that enables API users to
implement an effect that accesses video frame data via CPU-mapped ByteBuffer
* ByteBufferConcurrentEffect responsible for reading
video frame data in CPU-accessible ByteBuffer

PiperOrigin-RevId: 666375594
2024-08-22 09:18:32 -07:00
tianyifeng
c35a9d62ba Bump media3 version to 1.4.1
PiperOrigin-RevId: 666347191
(cherry picked from commit 829cad6912)
2024-08-22 15:16:35 +00:00
tianyifeng
517762c087 Update release notes for 1.4.1 bug fix release
PiperOrigin-RevId: 666328660
(cherry picked from commit 1994ccdea8)
2024-08-22 15:13:14 +00:00
tianyifeng
829cad6912 Bump media3 version to 1.4.1
#cherrypick

PiperOrigin-RevId: 666347191
2024-08-22 07:49:33 -07:00
kak
0060ff2028 Automated Code Change
PiperOrigin-RevId: 666338281
2024-08-22 07:19:57 -07:00
tianyifeng
1994ccdea8 Update release notes for 1.4.1 bug fix release
#cherrypick

PiperOrigin-RevId: 666328660
2024-08-22 06:45:59 -07:00
dancho
6e0e2d0cee Add QueuingGlShaderProgram for effects that run outside GL context
Implement a QueuingGlShaderProgram which queues up OpenGL frames and allows
asynchronous execution of effects that operate on video frames without a
performance penalty.

PiperOrigin-RevId: 666326611
2024-08-22 06:38:28 -07:00
tonihei
6f0cb539d0 Add util method BaseRenderer.getStreamOffsetUs
This simplifies the common pattern of saving this offset in
onStreamChanged to use it at a later point.

PiperOrigin-RevId: 666226263
2024-08-22 00:53:04 -07:00
kimvde
4ba9f59492 Improve logic to wait for a seek in CompositionPlayerSeekTest
The logic was assuming that the shader program was only flushed when
seeking. This is true if a single renderer is used but, with multiple
renderers, the shader program can be flushed at the transition.

This change is necessary to make the test pass for prewarming because 2
video renderers will be used in that case.

PiperOrigin-RevId: 666215967
2024-08-22 00:15:30 -07:00
Googler
6b56f12f15 AtomParser: Update initialization data to CodecPrivate format for Vp9
PiperOrigin-RevId: 666188937
2024-08-21 22:33:28 -07:00
tianyifeng
410b26fba1 Detect SampleStream error after PreloadMediaPeriod has prepared
Per the javadoc, the method `MediaPeriod.maybeThrowPrepareError` is only allowed to be called before the period has completed preparation. For later errors in loading the streams, `SampleStream.maybeThrowError` will be called instead.

PiperOrigin-RevId: 665831430
2024-08-21 05:16:42 -07:00
kimvde
059ad62377 Add timeout to CountDownLatch awaits
This is to avoid tests hanging forever

PiperOrigin-RevId: 665826507
2024-08-21 05:02:18 -07:00
tianyifeng
88b640136a Allow playback regardless buffered duration when loading fails
It is possible for playback to be stuck when there is failure in loading further data, while the player is required to load more due to the buffered duration being under `DefaultLoadControl.bufferForPlayback`. Therefore, we check if there is any loading error in `isLoadingPossible`, so that the player will allow the playback of the existing data rather than waiting forever for the data that can never be loaded.

Issue: androidx/media#1571
PiperOrigin-RevId: 665801674
(cherry picked from commit 351593a250)
2024-08-21 11:38:36 +00:00
tianyifeng
9b39e3514f Update translations
#cherrypick

PiperOrigin-RevId: 663705597
(cherry picked from commit 1ffc962fde)
2024-08-21 11:35:55 +00:00
ibaker
b184677b7b Check WV version before relying on MediaDrm.requiresSecureDecoder
This method was added in API 31 (S) but it's non-functional
(incorrectly, silently, returns `false`) on the Widevine plugin version
(`16.0`) from R (API 30), which some devices up to at least API 34 are
still using.

This results in ExoPlayer incorrectly selecting an insecure decoder for
L1 secure content, and subsequently calling
`MediaCodec.queueInputBuffer` instead of `queueSecureInputBuffer`,
which is not supported and generates the following error:
> Operation not supported in this configuration: ERROR_DRM_CANNOT_HANDLE

Issue: androidx/media#1603

#cherrypick

PiperOrigin-RevId: 662852176
(cherry picked from commit ca455ee858)
2024-08-21 11:35:55 +00:00
tianyifeng
f139d709c7 Handle preload callbacks asynchronously in PreloadMediaSource
When there is an exception thrown from the `LoadTask`, the `Loader` will call `Loader.Callback.onLoadError`. Some implementations of `onLoadError` method may call `MediaPeriod.onContinueLoadingRequested`, and in the `PreloadMediaSource`, its `PreloadMediaPeriodCallback` will be triggered and then it can further call `continueLoading` if it finds needed. However the above process is currently done synchronously, which will cause problem. By calling `continueLoading`, the `Loader` is set with a `currentTask`, and when that long sync logic in `Loader.Callback.onLoadError` ends, the `Loader` will immediately retry, and then a non-null `currentTask` will cause the `IllegalStateException`.

Issue: androidx/media#1568

PiperOrigin-RevId: 662550622
(cherry picked from commit cd532c5fb2)
2024-08-21 11:35:51 +00:00
ibaker
07e9c659d7 Handle HEADSETHOOK as 'play' in MediaButtonReceiver.onReceive
Issue: androidx/media#1581

PiperOrigin-RevId: 662515428
(cherry picked from commit c48c051ce2)
2024-08-21 11:30:14 +00:00
ibaker
eebf081528 Pass missing length into SubtitleParser from SubtitleExtractor
If the length of the `ExtractorInput` is not known then the
`subtitleData` field is re-sized by 1kB each time
(`SubtitleExtractor.DEFAULT_BUFFER_SIZE`), so the end of the array is
often not populated. This change ensures that `length` is propagated to
`SubtitleParser`, so that implementations don't try and parse the
garbage/zero bytes at the end of the array.

Discovered while investigating Issue: androidx/media#1516

#cherrypick

PiperOrigin-RevId: 661195634
(cherry picked from commit f37f9690f4)
2024-08-21 11:23:53 +00:00
michaelkatz
c773789edb Skip invalid media description in SessionDescriptionParser
Some RTSP servers may provide media descriptions for custom streams that are not supported. ExoPlayer should skip the invalid media description and continues parsing the following media descriptions.

To start, ExoPlayer will still error on malformed SDP lines for media descriptions, but will now skip media descriptions with "non-parsable" formats as described by [RFC 8866 Section 5.14](https://datatracker.ietf.org/doc/html/rfc8866#section-5.14).

Issue: androidx/media#1472
PiperOrigin-RevId: 660826116
(cherry picked from commit 8b33ad5811)
2024-08-21 11:23:53 +00:00
ibaker
bf934495df Fix IndexOutOfBoundsException in LegacySubtitleUtil
This is caused when the requested "output start time" is equal to or
larger than the last event time in a `Subtitle` object.

This resolves the error in Issue: androidx/media#1516, but subtitles are still not
renderered (probably because the timestamps aren't what we expect
somewhere, but I need to investigate this part further).

#cherrypick

PiperOrigin-RevId: 660462720
(cherry picked from commit 3763e5bc1d)
2024-08-21 11:23:53 +00:00
claincly
cd2a36f705 Add a method to disallow VFP destroying shared eglContext
Previously in MultiInputVideoGraph, each VFP would destroy the shared
eglContext, such that the same eglContext object is destroyed multiple times.

Adding a flag to disallow this.

The alternative being we could add a flag on the VFP constructor, but I think
that is too subscriptive (meaning if we later might want to add another boolean
to control another GL behaviour, multiple booleans would make the class less
reason-able), and would incur a lot of code changes at places.

PiperOrigin-RevId: 660354367
(cherry picked from commit 8f8e48731e)
2024-08-21 11:23:49 +00:00
Googler
efb79472ff Fixes README instructions for depending on modules locally
#cherrypick

PiperOrigin-RevId: 659504142
(cherry picked from commit e7eef0ce34)
2024-08-21 11:22:24 +00:00
ibaker
eb19aefa57 Implement MP3 ConstantBitrateSeeker.getDataEndPosition()
This is needed to correctly handle files with trailing non-MP3 data
(which is indicated by the length in the `Info` frame being shorter than
the overall length of the file).

The test file was generated by appending 150kB of `DEADBEEF` onto the
end of `test-cbr-info-header.mp3`, and the test asserts that the
extracted samples are identical.

Issue: androidx/media#1480

PiperOrigin-RevId: 658727595
(cherry picked from commit b09cea9e3a)
2024-08-21 11:22:20 +00:00
Copybara-Service
3dfe43b498 Merge pull request #1548 from kikoso:chore/fixed_links
PiperOrigin-RevId: 657138513
(cherry picked from commit f1ed195c10)
2024-08-21 11:21:02 +00:00
Googler
692ab33640 Add support for Audio Vorbis codec in Mp4Muxer.
Update esdsBox to support muxing of files encoded with Vorbis audio codec .

PiperOrigin-RevId: 655159074
(cherry picked from commit b77f1d0f99)
2024-08-21 11:21:02 +00:00
dancho
c2d7417ec8 Destroy EGLSurface immediately by focusing a placeholder surface
eglDestroySurface only destroys the surface when it's made not current.
Pass the placeholder surface in FinalShaderProgramWrapper and use it
when destroying eglSurface.

PiperOrigin-RevId: 655139661
(cherry picked from commit 1797359950)
2024-08-21 11:21:02 +00:00
dancho
b6e78f0b2f Ensure EGLSurface is released on GL thread
Add VideoFrameProcessingTaskExecutor.invoke() method that blocks until
Task has executed on GL thread.
Use that for FinalShaderProgramWrapper.setOutputSurfaceInfo

PiperOrigin-RevId: 655119768
(cherry picked from commit 9c075b692e)
2024-08-21 11:21:01 +00:00
bachinger
d44500e0fb Add EXTRAS_KEY_DOWNLOAD_STATUS to MediaContants
This was used in media1 `MediaItemDescription` to indicate the download
status of a media item. When connected to a legacy
`MediaBrowserServiceCompat` the Media3 browsers converts the legacy
media item to a Media3 `MediaItem` and converts the extras of
`MediaDescriptionCompat.extras` to `MediaMetadata.extras`.

#cherrypick

PiperOrigin-RevId: 654625502
(cherry picked from commit 225ad482b1)
2024-08-21 11:21:01 +00:00
Googler
818e015e05 Add support for Opus audio codec.
Implement dOpsBox to provide support for Opus audio codec

PiperOrigin-RevId: 653288049
(cherry picked from commit 01dda6d3e5)
2024-08-21 11:21:01 +00:00
Googler
66e977a810 Add support for 3gpp h263 codec in Mp4Muxer.
Implement d263Box to provide support for muxing video encoded with the h263 codec.

PiperOrigin-RevId: 653188633
(cherry picked from commit 951f296851)
2024-08-21 11:21:01 +00:00
Googler
a153d26d8f Add support for 3gpp amr-nb audio codec.
To support AMR audio codec(audio/3gpp) add `0x81FF` mode to create damrBox.

Add unit test and an Android end to end test.

PiperOrigin-RevId: 652438693
(cherry picked from commit 11ca78761e)
2024-08-21 11:21:01 +00:00
ibaker
4070535ba9 Remove stray parenthesis from MediaSession.ControllerInfo.toString()
#cherrypick

PiperOrigin-RevId: 651760391
(cherry picked from commit 2c7f2686b7)
2024-08-21 11:21:01 +00:00
ibaker
09b6e8fd04 Transform double-tap of HEADSETHOOK to skip-to-next
As reported in Issue: androidx/media#1493 we already use `HEADSETHOOK` to start
waiting for a double-tap, but we don't consider it for the second tap.

Similarly, we previously considered `PLAY` for the second tap, but not the first.
Only `HEADSETHOOK` and `PLAY_PAUSE` are
[documented](https://developer.android.com/reference/androidx/media3/session/MediaSession#media-key-events-mapping)
to transform double-tap to `seekToNext`. So this change removes the
`PLAY` detection from the second tap.

PiperOrigin-RevId: 651017522
(cherry picked from commit c64dacf3df)
2024-08-21 11:20:56 +00:00
Googler
0e75a0a5e1 Add support to MPEG4 codec in Mp4Muxer.
Add support for MPEG4 codec to enable muxing video encoded with the mp4v-es codec. Use esdsBox method to generate esds box required for Mp4v box.

PiperOrigin-RevId: 651000744
(cherry picked from commit 34a802ef38)
2024-08-21 11:20:10 +00:00
Googler
70e8e1bf45 Support for Large CodecSpecificData in ESDS box
Some external media files have CodecSpecificData greater than 128 bytes. Currently, that size
isn't fitting in one byte. Hence, added support to store large CodecSpecificDataSize, as per
ISO standard, by extending to more than one byte as required.

PiperOrigin-RevId: 650972472
(cherry picked from commit cf90d2624d)
2024-08-21 11:20:10 +00:00
dancho
0b6249b8ae Destroy eglSurface as soon as Surface changes
eglDestroySurface now unbinds surface from the GL
thread to ensure quick release of resources.

PiperOrigin-RevId: 650938712
(cherry picked from commit 70a6b5d50d)
2024-08-21 11:20:10 +00:00
Googler
c4bb43517d Add support for amr-wb audio codec.
Implement damrBox to provide support for amr-wb audio codec.

Add unit test and an Android end to end test.

PiperOrigin-RevId: 650210732
(cherry picked from commit 6e18cb0053)
2024-08-21 11:20:10 +00:00
Googler
f2d3072d1a Refactor audioEsdsBox to esdsBox
Since the muxer supported only AAC audio codec, the esdsBox was unconditionally created within the audioSampleEntry. This CL refactors the box creation logic by moving it to the codecSpecificBox method. This is to make adding support for new audio codecs easier.

PiperOrigin-RevId: 650130935
(cherry picked from commit a269355369)
2024-08-21 11:20:10 +00:00
ibaker
ae5a7e54ae Fix TTML handling of inherited percentage tts:fontSize values
The percentage should be interpreted as relative to the size of a parent
node.

This change makes this inheritance work correctly for percentages in
both the parent and child. It does not fix the case of a non-percentage
parent size with a percentage child size.

PiperOrigin-RevId: 649631055
(cherry picked from commit bb2fd002ae)
2024-08-21 11:20:07 +00:00
bachinger
4dc21fd743 Count down three playback states to match the assertion
PiperOrigin-RevId: 648629427
(cherry picked from commit ec3a58f8db)
2024-08-21 11:18:57 +00:00
tianyifeng
351593a250 Allow playback regardless buffered duration when loading fails
It is possible for playback to be stuck when there is failure in loading further data, while the player is required to load more due to the buffered duration being under `DefaultLoadControl.bufferForPlayback`. Therefore, we check if there is any loading error in `isLoadingPossible`, so that the player will allow the playback of the existing data rather than waiting forever for the data that can never be loaded.

Issue: androidx/media#1571
#cherrypick
PiperOrigin-RevId: 665801674
2024-08-21 03:37:42 -07:00
sheenachhabra
875953f971 Add Mp4Extractor test for interleaved editable video tracks file
PiperOrigin-RevId: 665800463
2024-08-21 03:34:28 -07:00
Copybara-Service
1bb48b1c47 Merge pull request #1616 from colinkho:chmain
PiperOrigin-RevId: 665779059
2024-08-21 02:32:16 -07:00
kimvde
51622b6d80 Add BufferingVideoSink
PiperOrigin-RevId: 665733825
2024-08-21 00:15:25 -07:00
Copybara-Service
5304f227a7 Merge pull request #1624 from colinkho:comain
PiperOrigin-RevId: 665430514
2024-08-20 10:47:43 -07:00
Ian Baker
bed1dadcbf Add release note 2024-08-20 17:50:58 +01:00
Ian Baker
9c25845cd7 Restore a couple of blank lines 2024-08-20 17:47:48 +01:00
Ian Baker
a6f5d3daf5 Format with google-java-format 2024-08-20 17:47:48 +01:00
Colin Kho
0a0444b9a5 Use Suppliers.memoize for lazy instantiation of AudioManager 2024-08-20 17:47:47 +01:00
Colin Kho
6af92b0af3 Differ AudioManager retrieval to whenever AudioFocusManagement is required 2024-08-20 17:47:47 +01:00
sheenachhabra
4b7c5100f1 Move moov box generation to Boxes.java
This is a no-op change.
Like all other boxes, moov box creation can also be in
Boxes.java class.

PiperOrigin-RevId: 665359529
2024-08-20 07:47:58 -07:00
rohks
f52ca07446 Add option to enable index-based seeking in AmrExtractor
This allows seek operations in files that were previously unseekable, particularly those with variable bitrate (VBR) or constant bitrate (CBR) with silence frames.

New samples for tests were created by adding silence frames to existing narrowband and wideband versions.

PiperOrigin-RevId: 665349241
2024-08-20 07:17:26 -07:00
Copybara-Service
24f3856ea4 Merge pull request #1580 from colinkho:main
PiperOrigin-RevId: 665330328
2024-08-20 06:17:20 -07:00
Ian Baker
41430aaa0c Fix annotation position and clarify javadoc 2024-08-20 13:42:00 +01:00
sheenachhabra
bb3948aa98 Implement interleaving of editable video tracks
The CL adds another way of writing editable video
tracks where the samples will be interleaved with the
primary track samples in the "mdat" box.

PiperOrigin-RevId: 665313751
2024-08-20 05:28:29 -07:00
Copybara-Service
643ec73e58 Merge pull request #1607 from colinkho:atom
PiperOrigin-RevId: 665285219
2024-08-20 04:03:45 -07:00
ibaker
b04b270c2b Use SubtitleExtractor from MediaParserChunkExtractor
This uses a 'bundled' extractor (`SubtitleExtractor`) because
`MediaParser` doesn't support transcoding subtitles to
`application/x-media3-cues`. This transcoding is required to support
non-legacy subtitle handling where they are parsed during extraction,
instead of during rendering.

PiperOrigin-RevId: 665282298
2024-08-20 03:54:17 -07:00
Ian Baker
af5df6e700 Add retryCount parameter to make it clear onLoadStarted is called for retries too 2024-08-20 11:28:18 +01:00
Colin Kho
33d9b78e21 Fix javadoc of onLoadStarted & remove error information as fields 2024-08-20 11:13:41 +01:00
Colin Kho
1cc1bf02ef Added onLoadStarted callback to Loader's callback 2024-08-20 11:13:41 +01:00
Ian Baker
2e49e91c84 Rename to singular BoxParser for consistency with other types like ColorParser 2024-08-20 11:11:14 +01:00
Ian Baker
77f3ef9b25 Add @UnstableApi annotation 2024-08-20 11:09:50 +01:00
Ian Baker
2dd6794ba0 More atom -> box updates in public API surface 2024-08-20 11:09:50 +01:00
Colin Kho
3a95b24afc Rename BoxParsers tag from AtomParsers to BoxParsers 2024-08-20 11:09:50 +01:00
Colin Kho
6ba9c9ff9e Rename AtomParsers to BoxParsers 2024-08-20 11:09:50 +01:00
Colin Kho
0b5443c450 Make Extractor/Mp4 Atom Parsing code reusable by external custom mp4 extractors 2024-08-20 11:09:50 +01:00
kimvde
266f16823f Remove VideoSink.isFrameDropAllowedOnInput
This is an unnecessary layer

PiperOrigin-RevId: 665267029
2024-08-20 03:09:13 -07:00
kimvde
9b69690856 Move some tests from CompositionPlaybackTest out of performance
directory

PiperOrigin-RevId: 665202382
2024-08-20 00:13:21 -07:00
Colin Kho
f9f3e67ee2 Include initialization chunk wording in getChunkIndex method 2024-08-19 10:31:34 -07:00
Colin Kho
4a6c5c7598 Cache ChunkIndex once load is done 2024-08-19 10:28:14 -07:00
ktrajkovski
ab366e2626 Fix licensing link from http to https in IAMF related files.
PiperOrigin-RevId: 664845636
2024-08-19 09:38:49 -07:00
claincly
677f8ad9f4 Fix edge case: no frame between trim position and the next sync sample
PiperOrigin-RevId: 664841893
2024-08-19 09:32:32 -07:00
ktrajkovski
63b45b7503 Build IAMF libraries with gradle and ndk-build.
In order to support building with `gradle` a new `build.gradle` file was added together with `Android.mk`, `Application.mk`, and `libiamf.mk` necessary for local builds with NDK.

After this change, IAMF files may also be played in the ExoPlayer demo built locally (without blaze).

PiperOrigin-RevId: 664841684
2024-08-19 09:29:47 -07:00
tonihei
ba00798451 Make NalUnitTargetBuffer public
This class is a useful utility for custom TS parsers that operate
on NAL units.

PiperOrigin-RevId: 664795988
2024-08-19 07:23:05 -07:00
kimvde
cd0a7e1143 Document why playback tests are in the performance package
PiperOrigin-RevId: 664792272
2024-08-19 07:14:32 -07:00
kimvde
b95b534f68 Fix inverted colors in call to Color.rgb
PiperOrigin-RevId: 664716252
2024-08-19 03:00:45 -07:00
sheenachhabra
ed905a6498 Refactor pending sample writing logic in Mp4Writer
The refactored method can be reused when implementing depth/editing format
interleave mode.

PiperOrigin-RevId: 663774290
2024-08-16 10:29:32 -07:00
ibaker
3600d04719 Deprecate SingleSampleMediaChunk
This is only used as part of legacy subtitle decoding. If any apps are
using it directly (rather than via `DashMediaSource` or `SsMediaSource`)
they probably need to enable legacy decoding in `TextRenderer` to avoid
playback failures.

PiperOrigin-RevId: 663740343
2024-08-16 08:36:38 -07:00
ibaker
91a95e23c9 Remove CueDecoder.decode overload without length & offset params
This method is only used in tests, so let's remove it and just test the
one that takes `length` and `offset`.

PiperOrigin-RevId: 663731139
2024-08-16 07:59:12 -07:00
tianyifeng
1ffc962fde Update translations
#cherrypick

PiperOrigin-RevId: 663705597
2024-08-16 06:06:40 -07:00
Googler
afac17bef0 Mp4Muxer: Add support for Vp9 codec
Implement vpcCBox to provide support for muxing video encoded using the VP9 codec.

PiperOrigin-RevId: 663603654
2024-08-15 22:34:56 -07:00
jbibik
c3313c0049 Add jvmTarget and kotlin-android plugin to common_ktx module
According to https://kotlinlang.org/docs/gradle-configure-project.html#check-for-jvm-target-compatibility-of-related-compile-tasks and https://kotlinlang.org/docs/gradle-configure-project.html#what-can-go-wrong-if-targets-are-incompatible, we require explicit jvmTarget setting in order not to run into:

`'compileDebugJavaWithJavac' task (current target is 1.8) and 'compileDebugKotlin' task (current target is 17) jvm target compatibility should be set to the same Java version.`

Missing the plugin and the jvmTarget resulted in a failed `compileDebugKotlin` task for any application code, which was trying to import common_ktx functions (e.g. `Player.listen` with `Unresolved reference: listen` error)

PiperOrigin-RevId: 663358677
2024-08-15 10:36:10 -07:00
Colin Kho
1c1fd4d8b8 Add getter for ChunkIndex on InitializationChunk 2024-08-15 10:00:56 -07:00
rohks
50708f8c37 Add AmrExtractor tests with FLAG_ENABLE_CONSTANT_BITRATE_SEEKING_ALWAYS
PiperOrigin-RevId: 663320349
2024-08-15 08:53:28 -07:00
tonihei
b58a1d16f7 Split DefaultAudioSink.writeBuffer in two seperate steps
The method currently has two ways of operating with a complicated
contract:
 1. outputBuffer == null -> sets a new outputBuffer and starts
    draining it as far as possible.
 2. outputBuffer != null -> continues draining a previous buffer,
    requires that the input parameter is the same as outputBuffer.

This contract can be made cleaner by splitting the logic into
(1) setting a new output buffer and (2) draining the output buffer.

Only one parameter is needed for each method and there is no
requirement to pass in the same argument as before because we already
know what we are draining. This also means the caller of the method
doesn't have to keep track of the actual outputBuffer, allowing
further processing steps in the future that change the drained
instance.

PiperOrigin-RevId: 663316251
2024-08-15 08:33:31 -07:00
sheenachhabra
7a1f3629ff Extract method to find minimum presentation timestamp across tracks
This is a ground work of implementing depth/editing format interleave mode.

PiperOrigin-RevId: 663301670
2024-08-15 07:40:27 -07:00
ibaker
873ec1544e Remove nested import of Player.Events from PlayerExtensions.listen
This makes it clearer that the part inside and outside the parentheses
are clearly different, and not "just" a reference to `Player.Events`.
Specifically this syntax is showing that the function has a `Player`
"receiver", **and** is a function from `Player.Events` to `Unit`.

https://kotlinlang.org/docs/lambdas.html#function-types

PiperOrigin-RevId: 663293405
2024-08-15 07:07:48 -07:00
ibaker
ee27334f06 Rename Atom to Mp4Box, and move it to container module
This makes the class available to custom MP4-parsing implementations,
while also allowing it to be used by `muxer` in future.

'Box' is the term used throughout the ISO 14496-12 spec, while the
'Atom' nomenclature was used in an earlier form of the spec
(Quicktime).

This change moves it from `extractor.mp4.Atom` to `container.Mp4Box`,
to be consistent with existing MP4-specific types in the `container`
module like `Mp4TimestampData`.

PiperOrigin-RevId: 663274752
2024-08-15 05:44:32 -07:00
sheenachhabra
4df5ecb045 Rename flushPending() to writePendingTrackSamples()
The new name is more readable

PiperOrigin-RevId: 663264188
2024-08-15 04:54:19 -07:00
ktrajkovski
fc18ad3135 Add LibiamfAudioRenderer's constructor to proguard rules.
Making a change to the `proguard-rules.txt` also requires a test added as `IamfModuleProguard`.

PiperOrigin-RevId: 663239150
2024-08-15 02:55:38 -07:00
sheenachhabra
68eaa061e0 Add support for depth/editing file format in Mp4Extractor
PiperOrigin-RevId: 662956209
2024-08-14 09:55:01 -07:00
claincly
92635342fb Move the test of removeAudio to robolectric
The audio mixing is not deterministic on real device testing because of
threading, but runs deterministically on robolectric tests

PiperOrigin-RevId: 662925912
2024-08-14 08:23:22 -07:00
dancho
879771ded2 Add an experimental flag for renderer dynamic scheduling
Use ExoPlayer dynamic scheduling to reduce the render() interval for
older API devices where `DefaultCodec.getMaxPendingFrameCount()` is set
to 1 in order to prevent frame drops.

Controlled via API on DefaultDecoderFactory.

Add TransformerForegroundSpeedTest that mimics transcoding while the app
is in foreground.

PiperOrigin-RevId: 662925764
2024-08-14 08:20:21 -07:00
sheenachhabra
dbc9f5e0d1 Add EditablevideoParameter class
The parameter class will allow addition of more
parameters (link shouldInterleaveSamples), which are specific to
editable video file format.

PiperOrigin-RevId: 662923844
2024-08-14 08:13:05 -07:00
rohks
74cfd2ad79 Deduplicate AMR samples and use dump file prefix for unique names
AMR samples with identical data but different names, previously used to generate uniquely named dump files, have been deleted. Instead, `AssertionConfig` is now used to set the dump file prefix, ensuring files are generated with unique names.

PiperOrigin-RevId: 662883541
2024-08-14 05:36:26 -07:00
ibaker
9d62845c45 Pass explicit securityLevel into MediaDrm.requiresSecureDecoder
Previous to this change, `FrameworkMediaDrm.requiresSecureDecoder`
ignores its `sessionId` parameter on API 31+, and uses only the
`mimeType` parameter. This means the result [assumes the session is
opened at the 'default security
level'](https://developer.android.com/reference/android/media/MediaDrm#requiresSecureDecoder(java.lang.String)):
> The default security level is defined as the highest security level
> supported on the device.

This change is a no-op in all (?) cases, because the `ExoMediaDrm`
interface only exposes the zero-arg `openSession()` method, which in the
framework case **also** assumes the highest security level is preferred:
> By default, sessions are opened at the native security level of the
> device.

However, it seems more obviously correct to only make this
"highest/native security level" assumption in one place
(`openSession()`), and check the session's **actual** security level
everywhere else.

Issue: androidx/media#1603
PiperOrigin-RevId: 662872860
2024-08-14 04:52:33 -07:00
rohks
e9cfd72083 Enable CBR seeking for files with unknown length in AmrExtractor
Constant bit rate (CBR) seeking can be enabled even when the length of the file is not known.

Additionally, dump files for these files have been updated to accurately log the `position` when `timeUs` is set to `0`.

PiperOrigin-RevId: 662868607
2024-08-14 04:32:38 -07:00
ibaker
ca455ee858 Check WV version before relying on MediaDrm.requiresSecureDecoder
This method was added in API 31 (S) but it's non-functional
(incorrectly, silently, returns `false`) on the Widevine plugin version
(`16.0`) from R (API 30), which some devices up to at least API 34 are
still using.

This results in ExoPlayer incorrectly selecting an insecure decoder for
L1 secure content, and subsequently calling
`MediaCodec.queueInputBuffer` instead of `queueSecureInputBuffer`,
which is not supported and generates the following error:
> Operation not supported in this configuration: ERROR_DRM_CANNOT_HANDLE

Issue: androidx/media#1603

#cherrypick

PiperOrigin-RevId: 662852176
2024-08-14 03:27:50 -07:00
kak
e7f037bff5 Automated Code Change
PiperOrigin-RevId: 662793513
2024-08-13 23:32:49 -07:00
sheenachhabra
68393832b4 Use Track instead of TrackToken internally
The TrackToken is primarily for public API.
Using Track object internally will remove unnecessary
type casting at various places.

PiperOrigin-RevId: 662564224
2024-08-13 10:24:04 -07:00
tianyifeng
cd532c5fb2 Handle preload callbacks asynchronously in PreloadMediaSource
When there is an exception thrown from the `LoadTask`, the `Loader` will call `Loader.Callback.onLoadError`. Some implementations of `onLoadError` method may call `MediaPeriod.onContinueLoadingRequested`, and in the `PreloadMediaSource`, its `PreloadMediaPeriodCallback` will be triggered and then it can further call `continueLoading` if it finds needed. However the above process is currently done synchronously, which will cause problem. By calling `continueLoading`, the `Loader` is set with a `currentTask`, and when that long sync logic in `Loader.Callback.onLoadError` ends, the `Loader` will immediately retry, and then a non-null `currentTask` will cause the `IllegalStateException`.

Issue: androidx/media#1568

#cherrypick

PiperOrigin-RevId: 662550622
2024-08-13 09:45:35 -07:00
ktrajkovski
0b23285bae Add nativeDecoderPointer field to IamfDecoder.
Moving this field to `IamfDecoder` instead of `iamf_jni` allows multiple instances of the IAMF decoder with possibly different configurations at the same time.

PiperOrigin-RevId: 662548068
2024-08-13 09:38:44 -07:00
ktrajkovski
92cff64321 Add spatial effects to IAMF support in Exoplayer.
Check if the output device supports spatialization for the requested output format. If so, return a stream decoded for 6 channels in a 5.1 layout. Otherwise, return a stream decoded for 2 channels in a binaural layout.

PiperOrigin-RevId: 662546818
2024-08-13 09:34:50 -07:00
ibaker
c48c051ce2 Handle HEADSETHOOK as 'play' in MediaButtonReceiver.onReceive
Issue: androidx/media#1581

#cherrypick

PiperOrigin-RevId: 662515428
2024-08-13 07:53:04 -07:00
simakova
2d527b08c3 Toggle video effects in the composition demo.
Add an option to enable or disable video effects in preview or export.

PiperOrigin-RevId: 662488658
2024-08-13 06:14:22 -07:00
ibaker
9d008da356 Remove unused Atom.ContainerAtom.getChildAtomOfTypeCount(int) method
This is in preparation for making this class public.

PiperOrigin-RevId: 662466043
2024-08-13 04:41:05 -07:00
ibaker
9dfd72b6c6 Move atom parsing logic from Atom to AtomParsers
This is groundwork to moving `Atom` to the `container` library, which
we want to do before making it public (so it can be used by `muxer` in
future).

PiperOrigin-RevId: 662453520
2024-08-13 03:50:40 -07:00
sheenachhabra
96f2c7ece7 Refactor editable video track related logic
This is to reuse same logic in depth/edit file format `interleave` mode.

PiperOrigin-RevId: 662117528
2024-08-12 09:32:37 -07:00
claincly
62da288caf Support removing video in previewing
Video playback will be disabled if *any* `EditedMediaItem` removes video. This
is consistent with Transformer.

PiperOrigin-RevId: 662093484
2024-08-12 08:28:16 -07:00
claincly
46eeabb877 Support setRemoveAudio in CompositionPlayer
PiperOrigin-RevId: 662063725
2024-08-12 06:34:44 -07:00
ibaker
ef6cb5d913 Use runCatching instead of try/catch in PlayerExtensionsTest
PiperOrigin-RevId: 661992546
2024-08-12 01:44:53 -07:00
Googler
a76ff16179 Manage wakelock when playback suppression is being handled.
After this change, a WakeLock of PowerManager#PARTIAL_WAKE_LOCK level would be acquired when the media is paused due to playback attempt without suitable output.
This WakeLock will be release either when the suitable media output has been connected or the set timeout to do so has expired.

PiperOrigin-RevId: 661570346
2024-08-10 02:28:12 -07:00
Googler
65a471e3db Automated Code Change
PiperOrigin-RevId: 661516063
2024-08-09 21:18:31 -07:00
sheenachhabra
117ac2e3f4 Create a common constant for large box size header
PiperOrigin-RevId: 661323230
2024-08-09 10:48:46 -07:00
ibaker
0411e1937b Deprecate SingleSampleMediaSource
This is an additional signal that legacy subtitle support needs to be
explicitly enabled, and is going away at some point.

PiperOrigin-RevId: 661305694
2024-08-09 10:07:14 -07:00
sheenachhabra
94abb9515b Write same timestamp in edit data MP4 as in outer MP4
The exiting code ensured that the timestamp is same only when it is set by the app.

PiperOrigin-RevId: 661283124
2024-08-09 09:05:33 -07:00
dancho
931b0e25f1 Add a DefaultDecoderFactory option to configure operating rate
This has the largest impact during operations with no encoder, such as
frame extraction. Add a matching performance test.

PiperOrigin-RevId: 661220044
2024-08-09 05:03:02 -07:00
ibaker
f37f9690f4 Pass missing length into SubtitleParser from SubtitleExtractor
If the length of the `ExtractorInput` is not known then the
`subtitleData` field is re-sized by 1kB each time
(`SubtitleExtractor.DEFAULT_BUFFER_SIZE`), so the end of the array is
often not populated. This change ensures that `length` is propagated to
`SubtitleParser`, so that implementations don't try and parse the
garbage/zero bytes at the end of the array.

Discovered while investigating Issue: androidx/media#1516

#cherrypick

PiperOrigin-RevId: 661195634
2024-08-09 03:09:09 -07:00
michaelkatz
8b33ad5811 Skip invalid media description in SessionDescriptionParser
Some RTSP servers may provide media descriptions for custom streams that are not supported. ExoPlayer should skip the invalid media description and continues parsing the following media descriptions.

To start, ExoPlayer will still error on malformed SDP lines for media descriptions, but will now skip media descriptions with "non-parsable" formats as described by [RFC 8866 Section 5.14](https://datatracker.ietf.org/doc/html/rfc8866#section-5.14).

Issue: androidx/media#1472
PiperOrigin-RevId: 660826116
2024-08-08 07:22:22 -07:00
dancho
c1078e3cfa Do not checkState based on input data
App users can choose arbitrary data that might not be
anticipated by developers. Transformer shouldn't `checkState` based on
media data or file type -- report an error for unsupported data instead.

Public API change `ImageAssetLoader` needs to parse MIME type and now accepts
`Context` as parameter.

PiperOrigin-RevId: 660762459
2024-08-08 03:18:27 -07:00
kak
2202397758 Automated Code Change
PiperOrigin-RevId: 660491742
2024-08-07 12:28:25 -07:00
ibaker
3763e5bc1d Fix IndexOutOfBoundsException in LegacySubtitleUtil
This is caused when the requested "output start time" is equal to or
larger than the last event time in a `Subtitle` object.

This resolves the error in Issue: androidx/media#1516, but subtitles are still not
renderered (probably because the timestamps aren't what we expect
somewhere, but I need to investigate this part further).

#cherrypick

PiperOrigin-RevId: 660462720
2024-08-07 11:16:30 -07:00
sheenachhabra
0530d663bc Rename muxer/Mp4Utils.java to muxer/Mp4MuxerUtil.java
PiperOrigin-RevId: 660417092
2024-08-07 09:23:53 -07:00
rohks
bef134a093 Fix IndexSeekMap.getTimeUs() javadoc
PiperOrigin-RevId: 660376007
2024-08-07 07:11:43 -07:00
rohks
9bc199f107 Refactor IndexSeeker to utilize IndexSeekMap, removing redundant code
This is a no-op change.

PiperOrigin-RevId: 660370824
2024-08-07 06:51:42 -07:00
claincly
8f8e48731e Add a method to disallow VFP destroying shared eglContext
Previously in MultiInputVideoGraph, each VFP would destroy the shared
eglContext, such that the same eglContext object is destroyed multiple times.

Adding a flag to disallow this.

The alternative being we could add a flag on the VFP constructor, but I think
that is too subscriptive (meaning if we later might want to add another boolean
to control another GL behaviour, multiple booleans would make the class less
reason-able), and would incur a lot of code changes at places.

PiperOrigin-RevId: 660354367
2024-08-07 05:50:32 -07:00
rohks
a087f82fa8 Make IndexSeekMap dynamic, allowing seek points to be added later
PiperOrigin-RevId: 660324829
2024-08-07 03:57:51 -07:00
sheenachhabra
5dac58995a Make parsing editable track map method non static
The method is not supposed to work with any input byte[]
so its best to make it non static and add appropriate validations.

PiperOrigin-RevId: 659906543
2024-08-06 04:44:40 -07:00
samrobinson
a23f655cf4 Check AssetLoader supports output type required by TransformerInternal.
PiperOrigin-RevId: 659557063
2024-08-05 08:10:23 -07:00
claincly
5165d7df68 Rollback of ffc45820b9
PiperOrigin-RevId: 659520675
2024-08-05 05:31:46 -07:00
tonihei
b00e018697 Add ImageDecoder for external image loading libraries
The integration with external libraries like Glide or Coil is
currently extremely complicated. Providing the boilerplate code
to handle the ImageDecoder interface and a better hook for custom
image decoders in DefaultRenderersFactory allows apps to easily
inject their own logic for external image loading libraries.

PiperOrigin-RevId: 659508914
2024-08-05 04:36:16 -07:00
Googler
e7eef0ce34 Fixes README instructions for depending on modules locally
#cherrypick

PiperOrigin-RevId: 659504142
2024-08-05 04:14:22 -07:00
kak
399f48ab42 Automated Code Change
PiperOrigin-RevId: 658829974
2024-08-02 10:29:47 -07:00
sheenachhabra
6a7e9132fd Write sample location key when muxing editable tracks
There are two ways to write editable tracks samples.
1. In the embedded edit data MP4.
2. Interleaved with primary tracks samples.

Initial plan was to support only option 1 but then the
decision is to support both ways. To identify between these two
an additional key will be required.

Option 2 is yet to be implemented in Mp4Muxer.

PiperOrigin-RevId: 658791214
2024-08-02 08:03:35 -07:00
rohks
8aab324fb4 Add the getSampleSize() API to MediaExtractorCompat
This API allows users to retrieve the sample size, ensuring they can allocate sufficient buffer capacity before utilizing the `readSampleData(ByteBuffer buffer, int offset)` method to read data.

PiperOrigin-RevId: 658772408
2024-08-02 06:33:06 -07:00
ktrajkovski
20df8b282a Collect configuration values in IamfDecoder.
Instead of hard-coding values in multiple files, all default values are declared in `IamfDecoder`. Additionally, the max number of frames used for output buffer initialisation is fetched from `libiamf` native functions.

PiperOrigin-RevId: 658772175
2024-08-02 06:30:34 -07:00
jbibik
9ace81bf2f Move PlayerExtensions into common-ktx module
For now, the only extension function on the `Player` has been used in a Compose demo. It can be promoted to a proper module where in the future other extension functions will reside. Given that `Player` is in `androidx.media3.common`, the corresponding KTX library for it is `androidx.media3.common-ktx`

To start using the new `suspend fun listen`, one must add `androidx.media3:media3-common-ktx` as a Gradle dependency and `import androidx.media3.common.listen`

PiperOrigin-RevId: 658771029
2024-08-02 06:24:10 -07:00
sheenachhabra
86bd1df632 Move editable track type constants to container module
This is to share the constants with the extractor.

PiperOrigin-RevId: 658755661
2024-08-02 05:10:16 -07:00
dancho
a79b80fcee Support setting H.264 level
Try to follow recommendations in
https://developer.android.com/media/optimize/sharing
more closely

For maximum compatibility the H.264 level should be less than or equal to 4.1

PiperOrigin-RevId: 658755139
2024-08-02 05:06:53 -07:00
ibaker
b09cea9e3a Implement MP3 ConstantBitrateSeeker.getDataEndPosition()
This is needed to correctly handle files with trailing non-MP3 data
(which is indicated by the length in the `Info` frame being shorter than
the overall length of the file).

The test file was generated by appending 150kB of `DEADBEEF` onto the
end of `test-cbr-info-header.mp3`, and the test asserts that the
extracted samples are identical.

Issue: androidx/media#1480

#cherrypick

PiperOrigin-RevId: 658727595
2024-08-02 02:51:49 -07:00
jbibik
018d0488e1 Create a new media3-common-ktx module
It will be used for Kotlin-specific functionality like extension functions on the classes from the `media3-common` module. To import it, add the following to your build.gradle file:

`implementation("androidx.media3:media3-common-ktx:1.X.Y")`

PiperOrigin-RevId: 658492256
2024-08-01 12:14:16 -07:00
jbibik
61e68d3f24 Add Kotlin extension function on Player
Given that `Player` interface is written in Java and is has a callback-based Listener interface, we need an adapter for the Kotlin-native world.

This change introduces a suspending function `listen` that creates a coroutine, in order to capture `Player.Events`.

PiperOrigin-RevId: 658478608
2024-08-01 11:41:11 -07:00
tonihei
56c419c1b3 Run CronetDataSource contract test for all Cronet providers
The data source may behave differently, depending on the provider,
so we can extend the contract test to check all available providers.

PiperOrigin-RevId: 658457650
2024-08-01 10:49:37 -07:00
dancho
a98a37aa75 Initial Frame Extractor Transformer Factory
Package-private until API is more useable.

Similar to frame analyzer mode: uses ImageReader instead of an encoder,
and no muxer.

PiperOrigin-RevId: 658446675
2024-08-01 10:21:10 -07:00
dancho
ddc86686b7 Experimental flag to limit the number of frames in encoder
Transformer.experimentalSetMaxFramesInEncoder controls max number
of frames in encoder.

VideoFrameProcessor now allows delayed releasing of frames to Surface,
while still using the original presentation time.

VideoSampleExporter can now configure video graphs to not render frames
automatically to output surface.

VideoSampleExporter.VideoGraphWrapper tracks how many frames are ready
to be rendered to Surface, and how many frames are already in-use by encoder.

PiperOrigin-RevId: 658429969
2024-08-01 09:33:16 -07:00
tonihei
766902634e Define Glide version
PiperOrigin-RevId: 658378243
2024-08-01 06:18:28 -07:00
sheenachhabra
9d14b91d94 Dump auxiliaryTrackType in a string format
PiperOrigin-RevId: 658372776
2024-08-01 05:59:54 -07:00
sheenachhabra
bd399eb601 Refactor get editable track types from map logic
The new method will be reused when Mp4Extractor need to
parse this metadata.

PiperOrigin-RevId: 658372567
2024-08-01 05:56:24 -07:00
samrobinson
34d3dc926d Use getDecoderNames method, rather than duplicating logic.
PiperOrigin-RevId: 658368479
2024-08-01 05:38:30 -07:00
Googler
b951833aec Update list of supported video and audio mime type.
Add parameterized test for codecs supported by InAppMuxer.
Split TransformerWithInAppMuxerEndToEndParameterizedTest tests
between parameterized and non parameterized

This will be helpful for adding more tests which need not to
be parameterized.

PiperOrigin-RevId: 658353532
2024-08-01 04:31:04 -07:00
ktrajkovski
01593a9c1f Replace RuntimeException with IllegalStateException.
Refactor to replace instances of `RuntimeException` with `IllegalStateException`.
This change ensures exceptions can be handled more specifically without
unintended catches of unrelated exceptions.

PiperOrigin-RevId: 658337459
2024-08-01 03:20:54 -07:00
claincly
f3bf4ad5fe Disable frame dropping on sm-x200@API34
From debug trace when decoding a 30fps video, the decoder output

```
"0us",
"33366us",
"66733us",
"100100us",
"133466us",
"166833us",
"200200us",
```

But the frame processor only received, despite setting `ALLOW_FRAME_DROP`:

```
"0us",
"166833us",
"200200us",
```

PiperOrigin-RevId: 658079749
2024-07-31 11:30:18 -07:00
sheenachhabra
dc3a9cea3e Validate data before creating MdtaMetadataEntry object
For some predefined keys the type of value is already defined.
Early validation will help avoiding error when processing this data later.

PiperOrigin-RevId: 658060844
2024-07-31 10:42:11 -07:00
kimvde
ffc45820b9 Move playback tests outside of performance directory
PiperOrigin-RevId: 658055853
2024-07-31 10:29:39 -07:00
Copybara-Service
40de898b22 Merge pull request #1576 from colinkho:main
PiperOrigin-RevId: 657990422
2024-07-31 06:55:45 -07:00
dancho
6e678e511b Enable experimentalRepeatInputBitmapWithoutResampling
Speed up image to video export by default.

PiperOrigin-RevId: 657958037
2024-07-31 04:40:29 -07:00
Ian Baker
c637774cc2 Take Executor instead of ExecutorService
This also avoids shutting down the externally-provided ExecutorService,
which we shouldn't do (since we don't really own it, and didn't create
it).
2024-07-31 10:37:14 +01:00
Googler
4a99dc4c94 Reserve space for the skip buttons in the media3 demo
This is to avoid the shuffle custom action jumping around when skipping to the first or last item of a playlist.

PiperOrigin-RevId: 657925696
2024-07-31 02:31:03 -07:00
Ian Baker
ff22838c0d Add javadoc summary fragment 2024-07-31 10:00:01 +01:00
Colin Kho
68e65ec884 Allow custom ExecutorService to be supplied to the Loader 2024-07-30 13:20:30 -07:00
dancho
3f49f5c157 Check for EGL_NO_SURFACE and similar in GlUtil
`== null` does not check for equality with
EGL_NO_SURFACE, EGL_NO_CONTEXT, or EGL_NO_DISPLAY.

PiperOrigin-RevId: 657651835
2024-07-30 10:49:06 -07:00
ktrajkovski
04bfeec751 Add decoding functions to IamfDecoder and LibiamfAudioRender.
PiperOrigin-RevId: 657621223
2024-07-30 09:33:31 -07:00
Copybara-Service
e9787c4196 Merge pull request #1566 from colinkho:main
PiperOrigin-RevId: 657571792
2024-07-30 06:42:22 -07:00
rohks
8b7b1b51a9 Add MediaDataSourceAdapter
Added a new data source which acts an adapter to read media data from platform `MediaDataSource`. This enables adding the `setDataSource(MediaDataSource)` API to `MediaExtractorCompat`.

PiperOrigin-RevId: 657564901
2024-07-30 06:16:30 -07:00
rohks
867e9ea2da Add APIs to set data source using content URI, file path or HTTP URL
Added three `setDataSource` APIs in `MediaExtractorCompat`:
- `setDataSource(Context context, Uri uri, @Nullable Map<String, String> headers)` to set data source with a content URI and optional headers.
- `setDataSource(String path)` to set data source using a file path or HTTP URL.
- `setDataSource(String path, @Nullable Map<String, String> headers)` to set data source using a file path or HTTP URL with optional headers.

PiperOrigin-RevId: 657563973
2024-07-30 06:12:56 -07:00
kimvde
ca5a26a409 Add frame count tests for preview
This is to ensure prewarming doesn't introduce any regression

PiperOrigin-RevId: 657559693
2024-07-30 06:04:41 -07:00
rohks
004b9d69fd Handle case where length is unset in FileDescriptorDataSource
- Modified the logic of `open()` and `read()` methods to handle scenarios where length is unset for the `FileDescriptor` provided.
- Added unit test and contract test to handle this case.

Also used `getDeclaredLength()` instead of `getLength()` to set the length of `AssetFileDescriptor` in unit tests and contract tests.

PiperOrigin-RevId: 657551343
2024-07-30 05:29:05 -07:00
ibaker
8360e44e07 Remove multidex config from iamf_decoder library's
`AndroidManifest.xml`. This doesn't have Gradle wiring yet, so was
probably missed as part of https://github.com/androidx/media/pull/1549.

PiperOrigin-RevId: 657549817
2024-07-30 05:22:49 -07:00
Ian Baker
335d5e7a1d Add some tests to TrackSelectionUtilTest 2024-07-29 15:12:23 +01:00
Colin Kho
0ead7bb221 Refactor getMaxVideoSizeInViewport into TrackSelectionUtil so it can be reused in external code 2024-07-29 15:12:23 +01:00
tofunmi
7d784d4067 Use FEATURE_HlgEditing to determine HDR support
PiperOrigin-RevId: 657174992
2024-07-29 06:11:48 -07:00
Copybara-Service
f1ed195c10 Merge pull request #1548 from kikoso:chore/fixed_links
PiperOrigin-RevId: 657138513
2024-07-29 03:36:26 -07:00
Googler
f6dc02fa6a Unsuppress/suppress playback on suitable media output updates
PiperOrigin-RevId: 657111555
2024-07-29 01:43:46 -07:00
Enrique López Mañas
debea15bdf chore: fixed links 2024-07-26 12:21:31 +00:00
Enrique López Mañas
b93cc68a67 chore: updated docs and broken links 2024-07-26 12:21:31 +00:00
rohks
32c9d62d39 Add DataSource contract tests to verify offset and position
These tests addresses two identified gaps in the contract:
 - Ensures that the output buffer offset passed to the `DataSource.read` method is correctly applied.
 - Verifies that the position within the input stream is properly incremented when reading in two parts.

PiperOrigin-RevId: 656358935
2024-07-26 05:14:51 -07:00
Copybara-Service
ccf704b30b Merge pull request #1549 from MGaetan89:min_sdk_21
PiperOrigin-RevId: 656358426
2024-07-26 05:11:46 -07:00
dancho
940e28e4db Refactor threading in FinalShaderProgramWrapper
Public methods either assert they're running GL thread, or
submit a task to run on GL thread.

Move methods to keep interface implementations together.

Add javadoc to VideoFrameProcessingTaskExecutor to clarify which
thread can call each public method.

PiperOrigin-RevId: 655978796
2024-07-25 09:23:41 -07:00
Googler
300453820c Selectable builtin speaker support for Wear OS
The builtin speaker is to be supported as a suitable output when that is deliberately selected for the media playback by the user in Wear OS.

PiperOrigin-RevId: 655950824
2024-07-25 07:42:31 -07:00
Tianyi Feng
b01c6ffcb3 Merge branch 'release' into release-1.4.0 2024-07-25 14:42:08 +00:00
tofunmi
685ea1e616 create and use SpeedProviderMediaPeriod in CompositionPlayer
PiperOrigin-RevId: 655945332
2024-07-25 07:21:31 -07:00
Ian Baker
4af220a2ac Clarify javadoc in controller test app 2024-07-25 15:12:07 +01:00
tofunmi
043de45763 Store the speed provider in timestamp adjustment
PiperOrigin-RevId: 655928480
2024-07-25 06:09:02 -07:00
Ian Baker
8c79a8fed2 Remove tools:replace="android:name" from manifests where multidex config has been removed 2024-07-25 13:12:10 +01:00
Googler
aaa6561aa9 Rename tests in Boxestest
Replace the box name with Codec name in the test.

PiperOrigin-RevId: 655915063
2024-07-25 05:09:43 -07:00
kimvde
3211f38ebc Add tests for image seeking in CompositionPlayer
This is to make sure prewarming won't introduce any regression when it
will be implemented.

PiperOrigin-RevId: 655879558
2024-07-25 02:27:45 -07:00
rohks
80202bc9f2 Use getDeclaredLength() for setting length of AssetFileDescriptor
Should have been part of the change: 0ac90855b4.

PiperOrigin-RevId: 655873821
2024-07-25 02:05:14 -07:00
Googler
d160aa2520 Modify tests in BoxesTest
Replace the string with the field from MimeType class

PiperOrigin-RevId: 655783812
2024-07-24 19:37:43 -07:00
tianyifeng
edd3a3f349 Fix bug where BasePreloadManager.Listener invokes from incorrect thread
The DefaultPreloadManagerTest didn't to catch this because we use main looper as the preload looper in the tests. This CL also improves the tests by assigning the preload looper with one that corresponds to a different thread.

PiperOrigin-RevId: 655664189
2024-07-24 12:41:21 -07:00
Gaëtan Muller
ed15ab012f Revert changes to androidx.media3.session.legacy 2024-07-24 16:17:02 +01:00
Gaëtan Muller
b90f00c774 Revert erroneous changes 2024-07-24 16:17:02 +01:00
Gaëtan Muller
eefb37a0ba Simplify VolumeProviderCompat.getVolumeProvider() 2024-07-24 16:17:01 +01:00
Gaëtan Muller
0593b36dad Remove MediaSessionImplBase, MediaSessionImplApi18, and MediaSessionImplApi19 2024-07-24 16:17:01 +01:00
Gaëtan Muller
0c564004c4 Remove unnecessary @SdkSuppress annotation 2024-07-24 16:17:01 +01:00
Gaëtan Muller
b84a63d318 Fix deprecation message 2024-07-24 16:17:01 +01:00
Gaëtan Muller
7406b78fbc Update javadoc 2024-07-24 16:17:01 +01:00
Gaëtan Muller
28edfcbb69 Remove unnecessary SDK_INT checks 2024-07-24 16:17:01 +01:00
Gaëtan Muller
7289764a65 Remove unnecessary @RequiresApi 2024-07-24 16:17:00 +01:00
Gaëtan Muller
71b8c32a6f Remove Multidex 2024-07-24 16:17:00 +01:00
Gaëtan Muller
e1633ff03b Remove unnecessary targetApi 2024-07-24 16:17:00 +01:00
Gaëtan Muller
64eedceb8c Use project.ext.minSdkVersion everywhere 2024-07-24 16:17:00 +01:00
ibaker
4fc66f42d6 Move OpusDecoderTest from /test/ (Robolectric) to /androidTest/
The dependency on the native `opusV2JNI` library doesn't work from
Robolectric, so the `assumeTrue` statements in this test always fail,
and the tests are always skipped. Moving it to an instrumentation test
allows the native library to be successfully loaded, and the test to be
run.

PiperOrigin-RevId: 655570129
2024-07-24 08:11:13 -07:00
tianyifeng
9fb7316696 Fix the release notes for 1.4.0 stable release
#cherrypick

PiperOrigin-RevId: 655558346
(cherry picked from commit d70ff7e4d2)
2024-07-24 14:45:25 +00:00
tianyifeng
d70ff7e4d2 Fix the release notes for 1.4.0 stable release
#cherrypick

PiperOrigin-RevId: 655558346
2024-07-24 07:31:39 -07:00
kimvde
da4c962e09 Rename VideoSink methods
This is following a renaming of registerInputFrame to handleInputFrame.
- queueInputBitmap is renamed to handleInputBitmap for consistency with
  handleInputFrame.
- registerInputStream is renamed to onInputStreamChanged for consistency
  with media3 method names.

PiperOrigin-RevId: 655529699
2024-07-24 05:56:17 -07:00
ktrajkovski
a1f20de3a9 Import a library for a Java clarity fix.
PiperOrigin-RevId: 655488843
2024-07-24 02:38:00 -07:00
dancho
7103f21da9 Use WORKING_COLOR_SPACE_DEFAULT in multi-sequence compositions
Build upon Transformer.videoFrameProcessorFactory in MultipleInputVideoGraph
Check that Transformer.videoFrameProcessorFactory is DefaultVideoFrameProcessor
for multi-input video

Fixes https://github.com/androidx/media/issues/1509

PiperOrigin-RevId: 655232381
2024-07-23 11:14:12 -07:00
dancho
9a42d03466 Enable experimentalAdjustSurfaceTextureTransformationMatrix
PiperOrigin-RevId: 655231134
2024-07-23 11:11:14 -07:00
ktrajkovski
2793ba845e Implement IamfDecoder and LibiamfAudioRenderer configuration.
PiperOrigin-RevId: 655212678
2024-07-23 10:23:48 -07:00
Googler
b77f1d0f99 Add support for Audio Vorbis codec in Mp4Muxer.
Update esdsBox to support muxing of files encoded with Vorbis audio codec .

PiperOrigin-RevId: 655159074
2024-07-23 07:39:26 -07:00
rohks
0ac90855b4 Use getDeclaredLength() in setDataSource for AssetFileDescriptor
Aligns `MediaExtractorCompat` with platform behavior by using `getDeclaredLength()`
instead of `getLength()` when setting the data source. This ensures compatibility
with asset files where the length is not predefined, even though it may result
in reading across multiple logical files when backed by the same physical file.

PiperOrigin-RevId: 655153390
2024-07-23 07:17:52 -07:00
dancho
1797359950 Destroy EGLSurface immediately by focusing a placeholder surface
eglDestroySurface only destroys the surface when it's made not current.
Pass the placeholder surface in FinalShaderProgramWrapper and use it
when destroying eglSurface.

PiperOrigin-RevId: 655139661
2024-07-23 06:22:08 -07:00
dancho
9c075b692e Ensure EGLSurface is released on GL thread
Add VideoFrameProcessingTaskExecutor.invoke() method that blocks until
Task has executed on GL thread.
Use that for FinalShaderProgramWrapper.setOutputSurfaceInfo

PiperOrigin-RevId: 655119768
2024-07-23 04:59:59 -07:00
Googler
3c5c81fc3e BoxesTest: Add default format builders
Move the common initialization code for format builder into separate methods to reduce code duplication.

PiperOrigin-RevId: 655118764
2024-07-23 04:54:32 -07:00
kimvde
225d336713 Remove VideoSinkProvider parameter from renderers
PiperOrigin-RevId: 655073481
2024-07-23 01:41:30 -07:00
tonihei
6147050b90 Delay flush after AudioTrack pause to ramp down volume
AudioTrack automatically ramps down volume when pausing. However,
when this happens as part of a AudioSink.flush() operation, we
need to postpone the actual flush() until the ramp down finished
in the audio system. Otherwise audio is just cut off, creating pop
sounds.

Delaying the release is fine now, because DefaultAudioSink starts
creating a new track immediately without waiting for the previous
track to be released.

Also using the opportunity to add more comments about related quirks
of the AudioTrack flush/release handling for more context.

PiperOrigin-RevId: 654794818
2024-07-22 09:58:53 -07:00
bachinger
225ad482b1 Add EXTRAS_KEY_DOWNLOAD_STATUS to MediaContants
This was used in media1 `MediaItemDescription` to indicate the download
status of a media item. When connected to a legacy
`MediaBrowserServiceCompat` the Media3 browsers converts the legacy
media item to a Media3 `MediaItem` and converts the extras of
`MediaDescriptionCompat.extras` to `MediaMetadata.extras`.

#cherrypick

PiperOrigin-RevId: 654625502
2024-07-21 23:41:37 -07:00
tonihei
0a8ca18305 Create new AudioTrack without waiting for previous released tracks
We currently wait until a previous AudioTrack from the same
DefaultAudioSink is released on a background thread before attempting
to initialize a new AudioTrack. This is done to avoid issues where
the releasing track blocks some shared audio memory, preventing a new
track from being created.

The current solution has two main shortcomings:
 - In most cases, the system can easily handle multiple AudioTracks
   and waiting for the release just causes unnecessary delays (e.g.
   when seeking).
 - It only waits for a previous track from the same DefaultAudioSink,
   not accounting for any other tracks that may be in the process of
   being released from other players.

To improve on both shortcomings, we can
 (1) move the check for "is releasing tracks and thus may block shared
 memory" to the static release infrastructure to be shared across all
 player instances.
 (2) optimistically create a new AudioTrack immediately without waiting
 for the previous one to be fully released.
 (3) extend the existing retry logic that already retries failed
 attempts for 100ms to only start the timer when ongoing releases are
 done. This ensures we really waited until we have all shared resources
 we can get before giving up completely. This also acts as a replacement
 for change (2) to handle situations where creating a second track is
 genuinely not possible. Also increase threshold to 200ms as the new
 unit test is falky on a real device with just 100ms (highlighting that
 the device needed more than 100ms to clean up internal resources).

PiperOrigin-RevId: 654053123
2024-07-19 10:41:17 -07:00
bachinger
076bc451f2 Update Kotlin Gradle plugin to version 1.9.10.
According to b/292763081 the build failure
`unresolved reference: addLast` in the session-demo is caused
by a bug in the Kotlin compiler 1.9.0 to which we depend.

Bumping the Kotlin plugin version to 1.9.10 which is the next
above 1.9.0 as listed in [1], the build problem is resolved.

Further, the Kotlin extension compiler version is set to 1.5.3
to make compose work with Kotlin 1.9.10 (see [2] for the
Kotlin/Compose compatibility map).

[1] https://kotlinlang.org/docs/releases.html#release-details
[2] https://developer.android.com/jetpack/androidx/releases/compose-kotlin

PiperOrigin-RevId: 654030537
2024-07-19 09:33:41 -07:00
tianyifeng
4e6a643d88 Update media3 version for 1.4.0 stable release
PiperOrigin-RevId: 653654999
(cherry picked from commit 3c9332bb48)
2024-07-19 13:20:28 +00:00
tianyifeng
18a1582e8c Fix the release notes for 1.4.0 stable release
#cherrypick

PiperOrigin-RevId: 653640574
(cherry picked from commit 1cbcd20851)
2024-07-19 13:15:34 +00:00
tianyifeng
1dfab4f73a Merge release notes for media3 1.4.0 stable release
#cherrypick

PiperOrigin-RevId: 653261278
(cherry picked from commit 68e8d9cb68)
2024-07-19 13:15:34 +00:00
tonihei
50f9f35353 Guard timeline access in ImaSSAIMS against empty timelines
All methods check if the player is currently handling the ad source
by calling isCurrentAdPlaying(). This method was missing a check
for empty timelines that throws an exception when trying to access
a non-existent period.

Also add this check to two methods that assume the current item
is the ads source, but didn't check it yet.

PiperOrigin-RevId: 653963557
2024-07-19 04:27:36 -07:00
rohks
0def3b215c Add APIs to set data source using AssetFileDescriptor & FileDescriptor
Introduced three `setDataSource` APIs in `MediaExtractorCompat`, enabling the use of `AssetFileDescriptor` and `FileDescriptor` to set the data source.

PiperOrigin-RevId: 653957035
2024-07-19 04:00:44 -07:00
tofunmi
1e28755b4a CompositionPlayer: clip silence with media source
PiperOrigin-RevId: 653667116
2024-07-18 10:17:29 -07:00
tianyifeng
3c9332bb48 Update media3 version for 1.4.0 stable release
#cherrypick

PiperOrigin-RevId: 653654999
2024-07-18 09:43:16 -07:00
dancho
f8bdb7e59f Fix division by zero in MuxerWrapper
PiperOrigin-RevId: 653644998
2024-07-18 09:18:34 -07:00
tianyifeng
1cbcd20851 Fix the release notes for 1.4.0 stable release
#cherrypick

PiperOrigin-RevId: 653640574
2024-07-18 09:06:22 -07:00
jbibik
4ba7fd0ace Fix javadoc formatting from backticks to tags
PiperOrigin-RevId: 653629763
2024-07-18 08:34:56 -07:00
tonihei
f7a726bb11 Add MediaCodec loudness controller for API35+
This controller connects the audio output to the MediaCodec so
that it can automatically propagate CTA-2075 loudness metadata.

PiperOrigin-RevId: 653628503
2024-07-18 08:31:14 -07:00
sheenachhabra
a52df6d29e Make Mp4MoovStructure.moov() method static
Creating a moov box is same as creating any other box so
there is no particular need to have a separate class for this.
In a follow up CL the method will be moved into Boxes.java along with
other box creation methods.

Made nit changes in the final fields ordering to match with
constructor parameter ordering.

PiperOrigin-RevId: 653602558
2024-07-18 06:50:42 -07:00
samrobinson
570be3680c Reduce test flakes by adding effects to multi-sequence playback test.
This test is flaky at p4head, because CompositionPlayer has no logic to
ensure a specific input is used to configure the audio graph. Depending
on which sequence registers input first, it changes the output format
of the media.

By setting effects on the 2nd sequence, both inputs are the same format
and this flakiness is avoided in the test.

PiperOrigin-RevId: 653582441
2024-07-18 05:40:49 -07:00
samrobinson
e28270b4cb Add preview tests for duration wrt clipping and speed adjustment.
PiperOrigin-RevId: 653569415
2024-07-18 04:43:41 -07:00
tonihei
54f5e0729e Support detached surface mode from API 35
This replaces the existing PlaceholderSurface mode with a more
efficient solution that doesn't require a GL texture or a new
thread.

PiperOrigin-RevId: 653537596
2024-07-18 02:29:57 -07:00
sheenachhabra
51d27d7575 Merge Boxes.moov() into Mp4MoovStucture.moov()
Boxes.moov() simply wraps the subboxes and this logic can be
put into main method which has all the logic of creating moov box.
This is to eventually move Mp4MoovStucture.moov() into
Boxes.java where all other box creation methods are already present.

PiperOrigin-RevId: 653319292
2024-07-17 12:15:44 -07:00
Googler
01dda6d3e5 Add support for Opus audio codec.
Implement dOpsBox to provide support for Opus audio codec

PiperOrigin-RevId: 653288049
2024-07-17 10:51:43 -07:00
tianyifeng
68e8d9cb68 Merge release notes for media3 1.4.0 stable release
#cherrypick

PiperOrigin-RevId: 653261278
2024-07-17 09:38:23 -07:00
tonihei
a86b5f065f Move release note to right section
The change is purely video releated.

PiperOrigin-RevId: 653229546
2024-07-17 07:41:15 -07:00
samrobinson
d0afb96c40 Implement repeat mode for CompositionPlayer.
-----

Context:
* Each sequence is wrapped as a single MediaSource, each being played
by an underlying ExoPlayer.
* Repeat mode is typically implemented in Players as a seek to the next
item in the playlist.

-----

This CL:

Repeat mode is triggered by listening for when the main input player
sees a play when ready change due to the end of the media item.

There is a slight delay at the end of the playback, before it repeats.
Setting repeat mode on the underlying players addresses this, but means
that the players will seek without waiting for the CompositionPlayer,
and as such previewAudioPipeline does not get the correct signals
around blocking/flushing.

PreviewAudioPipeline - The seek position can validly be C.TIME_UNSET,
however preview pipeline did not handle this case.

CompositionPlayer getContentPosition is given (through a lambda) as a
supplier to the State object, which means any comparisons between
previous/new state for this value does not work. In SimpleBasePlayer,
there is logic to use the positionDiscontinuityPositionUs for the
position change (see getPositionInfo called from
updateStateAndInformListeners), however this logic is not considered in
getMediaItemTransitionReason, so a condition needed to be added for
this case.

-----

Tests:
* Dump files clearly show the position and data is repeated.
* Assertions on the reasons for transitions or position
discontinuities.
PiperOrigin-RevId: 653210278
2024-07-17 06:22:02 -07:00
tofunmi
29a2486ce3 implement getDurationAfterEffectApplied in TimestampAdjustment Effect
PiperOrigin-RevId: 653206245
2024-07-17 06:07:27 -07:00
dancho
c05a5c6237 Rollback of 9151dbf9e6
PiperOrigin-RevId: 653192624
2024-07-17 05:08:52 -07:00
Googler
951f296851 Add support for 3gpp h263 codec in Mp4Muxer.
Implement d263Box to provide support for muxing video encoded with the h263 codec.

PiperOrigin-RevId: 653188633
2024-07-17 04:53:28 -07:00
ibaker
76db936d68 Enable lint errors in session tests
Also resolve some failures.

Lint checks [aren't enabled in tests by default](http://groups.google.com/g/lint-dev/c/rtjVpqHmY0Y).

This change suppresses `NewApi` failures in Robolectric tests because
these tests only run at 'target SDK' by default (currently 30), but the
lint doesn't understand this and so flags spurious issues with API
usages below this.

PiperOrigin-RevId: 653172059
2024-07-17 03:50:05 -07:00
ibaker
3b8ea4a412 Allow negative presentation time in ReorderingSeiMessageQueue
PiperOrigin-RevId: 653170404
2024-07-17 03:43:34 -07:00
simakova
e78802d0d8 Update recommendation on setting frame rate for images
PiperOrigin-RevId: 653167049
2024-07-17 03:31:57 -07:00
dancho
e94ee03cd0 Add 1920 and 1088 as guesses for surface texture crop fix
Some devices always allocate 1920x1088 pixel buffers,
regardless of video resolution

PiperOrigin-RevId: 653148028
2024-07-17 02:16:46 -07:00
tofunmi
1e43404468 Correct typo
PiperOrigin-RevId: 653137432
2024-07-17 01:35:01 -07:00
rohks
ded66debc3 Retry alternative addresses on timeout in SNTP client
Changed the default timeout for SNTP requests to 1 second.

Issue: androidx/media#1540
PiperOrigin-RevId: 652897579
2024-07-16 10:38:10 -07:00
ibaker
7f304092ae Explicitly set the group ID
This avoids it being implicitly set from the `rootProject.name`

PiperOrigin-RevId: 652879619
2024-07-16 09:47:17 -07:00
tonihei
b4975a1b49 Remove unused field in MediaCodecAdapter
The field is always 0 as the only publicly accessible creator
methods set it to zero in all cases.

PiperOrigin-RevId: 652858810
2024-07-16 08:42:48 -07:00
dancho
f68cf30791 Change ExportTest assertion to allow mismatching level
Due to differences in MediaCodec behavior between minor Android
versions, this test was flaky.

PiperOrigin-RevId: 652841512
2024-07-16 07:55:34 -07:00
samrobinson
1c3fe20826 Handle no supported encoder & muxer mime types in the Encoder factory.
PiperOrigin-RevId: 652825117
2024-07-16 07:03:25 -07:00
ibaker
99679645fc Add a test for MediaCodecRenderer handling of IllegalStateException
This is a regression test for the bug introduced in bb9ff30c3a
which was manually spotted and fixed in 0d2bf49d6a.

Reverting the fix causes this test to fail.

This test is a bit hacky because we have to munge the stack trace of
the `IllegalStateException` to make it look like it was thrown from
inside `MediaCodec`. We deliberately do this 'badly' (e.g. using
`fakeMethod`) to avoid a future reader being confused by a
fake-but-plausible stack trace.

PiperOrigin-RevId: 652820878
2024-07-16 06:47:31 -07:00
tonihei
d4c6e39dfb Further unapplied rotation clean-up
Now the value is guaranteed to be zero (see bb9ff30c3a), we can
remove the rotation handling for it in the UI module. We can also
enforce the documentation more clearly by not even setting the
value to anything other than zero.

PiperOrigin-RevId: 652772091
2024-07-16 03:35:46 -07:00
ktrajkovski
104fcc1c76 Add skeleton of the IAMF JNI wrapper for the native decoder in libiamf.
PiperOrigin-RevId: 652761237
2024-07-16 02:54:21 -07:00
rohks
c60baabb1c Allow changing SNTP client timeout
Added a method to set the timeout for the SNTP request.

Also changed the default timeout to 5s instead of 10s as it seemed quite high.

Issue: androidx/media#1540
PiperOrigin-RevId: 652566008
2024-07-15 12:36:30 -07:00
tonihei
0d2bf49d6a Partially revert MediaCodecException detection
The change in bb9ff30c3a removed the detection util completely,
but even on API21+, the codec exceptions can be thrown as
IllegalStateException and we should reinstate this check to
correctly classify the exceptions.

PiperOrigin-RevId: 652557091
2024-07-15 12:06:22 -07:00
tianyifeng
ec1954c1d5 Release all ListenerHolders when clearing ListenerSet
When removing one listener from the `ListenerSet`, we release the corresponding `ListenerHolder`, which prevents the event queued or sent later than the removal from being invoked. We should also do this in the method `ListenerSet.clear()` where every listener is removed.

PiperOrigin-RevId: 652535216
2024-07-15 10:59:13 -07:00
sheenachhabra
d747f38f59 Skip TransformerPauseResumeTest on vivo 1901
The process crashes unexpectedly on vivo devices.
When test is run individually it completes successfully.

PiperOrigin-RevId: 652496852
2024-07-15 08:56:37 -07:00
ibaker
bb9ff30c3a Remove dead code related to MediaCodec now minSdk is 21
This removes several workarounds that are no longer needed, including
`codecNeedsMonoChannelCountWorkaround` which has been permanently
disabled since the (incomplete) minSdk 19 clean-up in fb7438378d.

PiperOrigin-RevId: 652495578
2024-07-15 08:51:35 -07:00
Googler
1bb8d5f956 Update internal reference.
PiperOrigin-RevId: 652448337
2024-07-15 05:34:32 -07:00
dancho
bfe4824bfd Rollback of 9151dbf9e6
PiperOrigin-RevId: 652443920
2024-07-15 05:14:58 -07:00
Googler
11ca78761e Add support for 3gpp amr-nb audio codec.
To support AMR audio codec(audio/3gpp) add `0x81FF` mode to create damrBox.

Add unit test and an Android end to end test.

PiperOrigin-RevId: 652438693
2024-07-15 04:48:28 -07:00
tofunmi
4da1e26206 Take effects in account when calculating presentationDurationUs
PiperOrigin-RevId: 652425099
2024-07-15 03:40:59 -07:00
andrewlewis
4b7cc80593 Handle muxing with timestamps offset from zero in wrapper
Sources (for example media projection) can populate the `Surface` from
`SurfaceAssetLoader` with timestamps that don't start from zero. But
`MuxerWrapper` assumes the latest sample timestamp can be used as the duration
when it calculates average bitrate and notifies its listener.

This can cause a crash because the calculated average bitrate can be zero if
the denominator duration is large enough.

Use the max minus first sample timestamp across tracks instead to get the
duration.

Side note: the large timestamps from the surface texture when using media
projection arrive unchanged (apart from conversion from ns to us) in effect
implementations and in the muxer wrapper (and are passed to the underlying
muxer). The outputs of media3 muxer and the framework muxer are similar.

PiperOrigin-RevId: 652422674
2024-07-15 03:30:26 -07:00
tonihei
c510ab81bb Update compileSdk to 35
This should have no influence on app behavior and other policies
and just allows code to depend on new API 35 platform symbols.

PiperOrigin-RevId: 652414026
2024-07-15 02:45:55 -07:00
ibaker
268c8cf6a2 Remove dead code from MediaStyleNotificationHelper now minSdk is 21
Tested using session demo app on API 21 emulator, and checked
notification layout looked correct.

PiperOrigin-RevId: 652403407
2024-07-15 01:56:37 -07:00
tonihei
e96ca5a242 Decouple displaySurface from placeholderSurface
We currently use displaySurface == placeholderSurface IF codec != null
as a signal that the codec is configured with a placeholder. In the
future, this placeholder might not be needed and we can decouple this
state a bit better by leaving displaySurface == null in this case and
only using placeholderSurface instead of null when setting a Surface
to the codec.

PiperOrigin-RevId: 652391729
2024-07-15 01:04:48 -07:00
ibaker
d035b745cd Remove dead code from ExoPlayerImpl now minSdk is 21
PiperOrigin-RevId: 651815091
2024-07-12 10:27:49 -07:00
ibaker
6a9ff95bf0 Bump minSdk to 21 and remove resulting simple dead code
All other AndroidX libraries have already increased their min SDK to
21.

This change renames private symbols to remove `V21` suffixes and
similar, but doesn't change public or protected symbols with similar
names, to avoid needless breakages/churn on users of the library.

Some of the dead code removal is more complex, so I've split it out
into follow-up changes to make it easier to review.

PiperOrigin-RevId: 651776556
2024-07-12 08:11:01 -07:00
ibaker
5fa9985ce6 Add H264_ prefix to NalUnitUtil.NAL_UNIT_TYPE_* constants
Also promote all H.265 constants to be public in `NalUnitUtil` with
`H265_` prefixes, for consistency.

A lot of these names are used in h.265 too (and `NalUnitUtil` handles
both), but with different values, so this rename aims to avoid
accidentally using an h.264 value in an h.265 context.

PiperOrigin-RevId: 651774188
2024-07-12 08:02:24 -07:00
ibaker
2c7f2686b7 Remove stray parenthesis from MediaSession.ControllerInfo.toString()
#cherrypick

PiperOrigin-RevId: 651760391
2024-07-12 06:58:33 -07:00
dancho
9151dbf9e6 Avoid decoder input skipping close to media end duration
MediaCodecRenderer might not be able to determine whether a sample
is last in time. Do not use decoder input skipping optimization
for buffers close to media end duration in order to ensure
last frame is rendered.

PiperOrigin-RevId: 651757814
2024-07-12 06:44:51 -07:00
dancho
09239a8a55 Add tests for releasing DefaultVideoFrameProcessor output surface
Add parametrized tests for DefaultVideoFrameProcessor that ensure
output EGL surface can be released, and deallocated.

PiperOrigin-RevId: 651712624
2024-07-12 03:07:20 -07:00
Googler
4c4e24db60 Recognize QC's MV-HEVC decoder.
PiperOrigin-RevId: 651539516
2024-07-11 14:40:39 -07:00
tianyifeng
7aa70a5f2f Add Listener to BasePreloadManager to propagate preload events to apps
PiperOrigin-RevId: 651421044
2024-07-11 08:36:41 -07:00
Googler
735e0cf8a1 Add an MV-HEVC test to Mp4ExtractorParameterizedTest.
PiperOrigin-RevId: 651392787
2024-07-11 06:52:15 -07:00
claincly
1ba2d98fce Remove extra comment line
PiperOrigin-RevId: 651367551
2024-07-11 05:06:17 -07:00
claincly
81f5a5f5f3 Set a longer muxer timeout on emulators
This is because the force EOS workaround for videos is longer than the original
muxer timeout. This way the apps depending on Transformer won't have to manually
set the muxer timeout on emulators.

PiperOrigin-RevId: 651355755
2024-07-11 04:12:59 -07:00
ktrajkovski
b7f141ad2a Replace sample mp4 files related to IAMF and update the dump files.
PiperOrigin-RevId: 651347968
2024-07-11 03:41:56 -07:00
ibaker
0ea555dae0 Stop using SubtitleTranscodingExtractor and deprecate it
The integration with `SubtitleTranscodingExtractorOutput` has been
moved inside the relevant `Extractor` implementations instead.

PiperOrigin-RevId: 651213564
2024-07-10 18:09:53 -07:00
ibaker
240b6fd606 Fix 'duplicate class' error caused by incomplete kt stdlib metadata
When testing locally it seemed that upgrading KGP to `1.9.20` resolved
this, but testing again confirms this was incorrect, so the problem
was reintroduced in 00d1e70a34.

This change reverts back to KGP `1.9.0` (since upgrading didn't help)
and instead implements the workaround suggested in
https://issuetracker.google.com/278545487. The workaround is now in
the `lib-common` `build.gradle` file, which is transitively depended
on by all modules (and therefore all apps that use this library), so
there's no need for any developer action, and so the release note is
removed.

Issue: androidx/media#1262
PiperOrigin-RevId: 651066418
2024-07-10 10:20:12 -07:00
kimvde
21992bff33 Call getFrameReleaseAction from VideoSink when enabled
VideoSink.registerInputFrame is now called for every input frame (not
only the ones that should be rendered to the input surface) because it's
the VideoSink that decides whether it wants the frame to be rendered.

PiperOrigin-RevId: 651049851
2024-07-10 09:33:11 -07:00
dancho
0ff9e0723d Expose fMP4 FLAG_READ_WITHIN_GOP_SAMPLE_DEPENDENCIES to DASH
In order for DASH playback to benefit from
FLAG_READ_WITHIN_GOP_SAMPLE_DEPENDENCIES, the fMP4 extractor flag
must be set. The smallest API change that allows this is to add an
experimental method to BundledChunkExtractor.

Add a dash end-to-end test to verify that video frames are skipped at
decoder input.

PiperOrigin-RevId: 651046676
2024-07-10 09:23:35 -07:00
ibaker
c64dacf3df Transform double-tap of HEADSETHOOK to skip-to-next
As reported in Issue: androidx/media#1493 we already use `HEADSETHOOK` to start
waiting for a double-tap, but we don't consider it for the second tap.

Similarly, we previously considered `PLAY` for the second tap, but not the first.
Only `HEADSETHOOK` and `PLAY_PAUSE` are
[documented](https://developer.android.com/reference/androidx/media3/session/MediaSession#media-key-events-mapping)
to transform double-tap to `seekToNext`. So this change removes the
`PLAY` detection from the second tap.

#cherrypick

PiperOrigin-RevId: 651017522
2024-07-10 07:52:18 -07:00
tonihei
e8778d77fa Document Renderer and BaseRenderer in more detail
PiperOrigin-RevId: 651008509
2024-07-10 07:24:02 -07:00
Googler
f673ef43b4 Add support for SEI and vexu box parsing.
Stereo view information is stored in the 3D reference displays information SEI and the optional vexu box.  Parsing of the SEI and vexu box is added, and based on the parsed info, proper mapping of primary/secondary view to left/right eye is determined.

PiperOrigin-RevId: 651002190
2024-07-10 07:00:29 -07:00
Googler
34a802ef38 Add support to MPEG4 codec in Mp4Muxer.
Add support for MPEG4 codec to enable muxing video encoded with the mp4v-es codec. Use esdsBox method to generate esds box required for Mp4v box.

PiperOrigin-RevId: 651000744
2024-07-10 06:55:00 -07:00
Googler
cf90d2624d Support for Large CodecSpecificData in ESDS box
Some external media files have CodecSpecificData greater than 128 bytes. Currently, that size
isn't fitting in one byte. Hence, added support to store large CodecSpecificDataSize, as per
ISO standard, by extending to more than one byte as required.

PiperOrigin-RevId: 650972472
2024-07-10 05:16:01 -07:00
tonihei
9d4e43cf55 Support multiple DataSource configurations in DataSourceContractTest
PiperOrigin-RevId: 650967939
2024-07-10 05:01:33 -07:00
ibaker
a202fd0c9c Add parameter comments in ReorderingSeiMessageQueueTest
PiperOrigin-RevId: 650959556
2024-07-10 04:34:24 -07:00
dancho
70a6b5d50d Destroy eglSurface as soon as Surface changes
eglDestroySurface now unbinds surface from the GL
thread to ensure quick release of resources.

PiperOrigin-RevId: 650938712
2024-07-10 03:21:48 -07:00
andrewlewis
dcc3e439e2 Handle AVI containers with no keyframes in index
If there is no keyframe in the index assume that the first chunk has a
keyframe.

PiperOrigin-RevId: 650915467
2024-07-10 01:51:06 -07:00
tonihei
b145a9b35e Limit maximum number of parallel metadata retrievals.
The operation almost always acquires resources straight-away,
for example a new thread or file access. This means starting
many metadata retrievals in parallel easily causes resource
contention. This problem can be alleviated by limiting the
maximum number of parallel retrievals.

Local testing showed a 20% speedup for local file retrievals
when limited to 5 in parallel. Any more parallel retrievals
did not show any improvement or started getting slower again
the more operations are allowed.

PiperOrigin-RevId: 650674685
2024-07-09 10:25:20 -07:00
tonihei
5777e30979 Reuse thread in MetadataRetriever
MetadataRetriever is often used in a loop to retrieve data about many
items in a directory for example. In such cases, it's wasteful to
start a new 'playback' thread for each retrieval, in particular since
this thread is doing almost nothing (just triggering loads and handling
events). This change re-uses an existing thread if one exists already.

PiperOrigin-RevId: 650633343
2024-07-09 08:15:45 -07:00
ibaker
00d1e70a34 Rollback of 91633e6ae3
PiperOrigin-RevId: 650620012
2024-07-09 07:29:57 -07:00
claincly
60359c16da Add a new debug trace log to log the device name / sdk
PiperOrigin-RevId: 650567544
2024-07-09 03:48:52 -07:00
dancho
6650270a4e MediaCodecVideoRenderer skips decoder inputs unused as reference
During a seek, or when playing a media with clipped start,
MCVR encounters preroll decode-only buffers that are not rendered.
Use C.BUFFER_FLAG_NO_OTHER_SAMPLE_DEPENDS_ON_THIS to determine
whether a decode-only buffer is unused as reference.
These buffers can be dropped before the decoder.
When this optimization is triggered, increment
decoderCounters.skippedInputBufferCount.

Tested in ExoPlayer demo app on "One hour frame counter (MP4)"
after enabling extractorsFactory.setMp4ExtractorFlags(
    FLAG_READ_WITHIN_GOP_SAMPLE_DEPENDENCIES);
Observe: "sib" increases on each seek.
PiperOrigin-RevId: 650566216
2024-07-09 03:43:06 -07:00
dancho
7d4f623b00 Fix RELEASENOTES merge conflict
PiperOrigin-RevId: 650551156
2024-07-09 02:43:03 -07:00
dancho
439536480b Parse the H264 bitstream of fMP4 files to identify sample dependencies
Changes to FragmentedMp4Extractor to parse additional sample dependency
information and mark output samples as "no other samples depend on this".
Only applies to H.264 tracks.
Controlled by new fMP4 flag: FLAG_READ_WITHIN_GOP_SAMPLE_DEPENDENCIES

PiperOrigin-RevId: 650538377
2024-07-09 01:53:51 -07:00
tonihei
2bb719fd54 Remove obsolete TODO
The idea was to not even write any samples to SampleQueues as
they are not needed during the metadata extraction process.
However, this is not easily possible as long as we use our
existing Extractors and MediaSource/Periods for loading given
how deeply ingrained the extraction of samples is in these
classes. For most common formats like MP4, no samples will be
extracted anyway as they can finish the prepare step without
reading any samples.

PiperOrigin-RevId: 650529371
2024-07-09 01:18:01 -07:00
andrewlewis
74c06dc2f4 Add SurfaceAssetLoader
This supports queueing input to Transformer via a `Surface`.

PiperOrigin-RevId: 650318396
2024-07-08 11:33:05 -07:00
ibaker
5dd377fb7b Rollback of 91633e6ae3
PiperOrigin-RevId: 650312000
2024-07-08 11:15:18 -07:00
claincly
ecd8a33f01 Check EOS is not signalled when queueing bitmap and texture
This is consistent with Surface input

PiperOrigin-RevId: 650298944
2024-07-08 10:39:39 -07:00
ktrajkovski
972007abef Add readLeb128 and readLeb128ToInt to ParsableByteArray.
Leb128 is a little-endian long of variable byte length. The format is used during the extraction of the size of the OBU configuration for the iacb configuration box.

PiperOrigin-RevId: 650295002
2024-07-08 10:29:42 -07:00
rohks
007c258ceb Fix maxInputSize for AMR-NB
The `maxInputSize` for AMR-NB should be 32, not 61. The `maxInputSize` for AMR-WB is 61.

PiperOrigin-RevId: 650282516
2024-07-08 09:52:54 -07:00
bachinger
06d61ffaaa Allow an app to decide to not start the service
Once a service is started as a foreground service, it must
be started into the foreground. This means an app can not
suppress a play command arriving from the `MediaButtonReceiver`
once the receiver has started the service.

This change adds a method to the `MediaButtonReceiver` that
allows app to suppress starting the service to not get into
this situation of wanting to suppress the play command after
the service is already started.

Issue: androidx/media#1528
PiperOrigin-RevId: 650280025
2024-07-08 09:44:30 -07:00
ibaker
2377d7556f Remove warning about depending on Kotlin std lib
We now depend on Kotlin from both `annotation` and
`annotation-experimental`, so it's not really possible to avoid
depending on it from any module now.

PiperOrigin-RevId: 650251094
2024-07-08 08:04:04 -07:00
okunhardt
91633e6ae3 Update HttpEngineDataSource to require at least S extension 7.
This earlier version supports [HttpEngine](https://developer.android.com/reference/android/net/http/HttpEngine) and thus this change allows more devices to use HttpEngine.

This fixes Issue: androidx/media#1262, which suggests to do this.

PiperOrigin-RevId: 650224711
2024-07-08 06:13:24 -07:00
Googler
6e18cb0053 Add support for amr-wb audio codec.
Implement damrBox to provide support for amr-wb audio codec.

Add unit test and an Android end to end test.

PiperOrigin-RevId: 650210732
2024-07-08 05:13:18 -07:00
claincly
d0a29400ea Fix test failuer on real-device
In the previous CL, muxer timeout is set to the surface timeout, which is
incorrect.

PiperOrigin-RevId: 650203505
2024-07-08 04:40:22 -07:00
tianyifeng
58ff8fa3c2 Add onPreloadError method to PreloadMediaSource.PreloadControl
Upon the call of `PreloadMediaSource.preload`, the source will periodically check the source refresh or period loading error, and trigger `PreloadMediaSource.PreloadControl.onPreloadError`. For now, the `DefaultPreloadManager` will skip the problematic source and continue to preload the next source. The checking of the error will be terminated when the source stops preloading or releases.

PiperOrigin-RevId: 650195817
2024-07-08 04:06:32 -07:00
claincly
b4722ef1ea Make timeout longer for emulators
Some test is flaky because frame processing is quite slow and triggered this
time out.

PiperOrigin-RevId: 650191068
2024-07-08 03:47:15 -07:00
tonihei
f55c09cfe2 Add ForwardingSimpleBasePlayer
This utility helps apps to forward to another Player while overriding
selected behavior or state values. The advantage to a ForwardingPlayer
is that the SimpleBasePlayer base class keeps ensuring correctness,
listener handling etc.

The default forwarding logic tries to stay as close as possible to the
original method calls, even if not strictly required by the Player
interface (e.g. calling single item addMediaItem instead of
addMediaItems if only one item is added).

Issue: androidx/media#1183
PiperOrigin-RevId: 650155924
2024-07-08 01:15:16 -07:00
Googler
a269355369 Refactor audioEsdsBox to esdsBox
Since the muxer supported only AAC audio codec, the esdsBox was unconditionally created within the audioSampleEntry. This CL refactors the box creation logic by moving it to the codecSpecificBox method. This is to make adding support for new audio codecs easier.

PiperOrigin-RevId: 650130935
2024-07-07 23:13:29 -07:00
tonihei
b2585aad0f Allow externally provided Timeline in SimpleBasePlayer.State
The Timeline, Tracks and MediaMetadata are currently provided
with a list of MediaItemData objects, that are a declarative
version of these classes. This works well for cases where
SimpleBasePlayer is used for external systems or custom players
that don't have a Timeline object available already. However,
this makes it really hard to provide the data if the app already
has a Timeline, currently requiring to convert it back and forth
to a list of MediaItemData.

This change adds an override for `State.Builder.setPlaylist`
that allows to set these 3 objects directly without going
through MediaItemData. The conversion only happens when needed
(e.g. when modifying the playlist).

PiperOrigin-RevId: 649667983
2024-07-05 09:39:49 -07:00
tonihei
fafd927702 Replace SimpleBasePlayer.State.playlist by getter
The value is basically a duplicate of the information stored
in the timeline field. Reducing the source of truth to the
single Timeline also allows acceptance of other Timelines in the
future that don't necessarily have the helper structure of
the playlist.

To allow apps to retrieve the current playlist as it is, we
add a getter instead.

PiperOrigin-RevId: 649667281
2024-07-05 09:35:44 -07:00
ktrajkovski
35a43d5c43 Add support for IAMF audio in MP4 Extractors.
A new IAMF type can now be recognized as an audio sample entry. A new mime type was created.

PiperOrigin-RevId: 649658865
2024-07-05 08:40:18 -07:00
dancho
40a5d31753 Parse the H264 bitstream of mp4 files to identify sample dependencies
Changes to Mp4Extractor to parse additional sample dependency information
and mark output samples as "no other sample depend on this".
Only applies to H.264 tracks.
Controlled by new mp4 flag: FLAG_READ_WITHIN_GOP_SAMPLE_DEPENDENCIES

PiperOrigin-RevId: 649640184
2024-07-05 06:45:40 -07:00
ibaker
bb2fd002ae Fix TTML handling of inherited percentage tts:fontSize values
The percentage should be interpreted as relative to the size of a parent
node.

This change makes this inheritance work correctly for percentages in
both the parent and child. It does not fix the case of a non-percentage
parent size with a percentage child size.

PiperOrigin-RevId: 649631055
2024-07-05 05:57:54 -07:00
andrewlewis
8f72054f2b Remove unused tag
PiperOrigin-RevId: 649448617
2024-07-04 10:55:15 -07:00
rohks
adf1c7915d Add FileDescriptorDataSource
This is a new `DataSource` that can be used to read from a `FileDescriptor`.

Limitations:
- The provided file descriptor must be seekable via lseek.
- There's no way to duplicate a file descriptor with an independent position (it
  would be necessary instead for the app to provide a new FD). Therefore this
  implementation will only work if there's one open data source for a given file
  descriptor at a time.
PiperOrigin-RevId: 649443584
2024-07-04 10:24:25 -07:00
ibaker
b7f317e650 Remove deprecation note from release notes
This was added in 0b96f4372f
but isn't needed. The deprecation annotation is self-documenting.

PiperOrigin-RevId: 649419778
2024-07-04 08:19:59 -07:00
Googler
0d4a785b61 Add support for parsing LHEVCConfigurationBox.
Parse LHEVCDecoderConfigurationRecord with the ‘lhvC’ type and set the corresponding sample mime type to video/mv-hevc.  With no MV-HEVC decoder available, fallback to single-layer HEVC decoding.

PiperOrigin-RevId: 649119173
2024-07-03 10:24:36 -07:00
claincly
8632c3add6 Fix not setting videoSinkNeedsRegisterInputStream when seeking
PiperOrigin-RevId: 649093092
2024-07-03 09:04:58 -07:00
andrewlewis
4c1807781f Mark flaky test as ignored
PiperOrigin-RevId: 649091256
2024-07-03 08:58:58 -07:00
claincly
ccdc0ffc27 Use us (microsecond) API.
PiperOrigin-RevId: 649058648
2024-07-03 07:00:18 -07:00
sheenachhabra
a1fc4e766f Reduce Exoplayer load control buffer durations for Transformer demo app
The default value is 50 seconds.
Changed it to 5 seconds.

This prevents the player from buffering too much data and causing the app to crash due to OOM.

This was reported in https://github.com/androidx/media/issues/1506

PiperOrigin-RevId: 649054885
2024-07-03 06:41:52 -07:00
kimvde
c832cf5a57 Clarify Javadoc of VideoSink
The VideoSink has an input and an output surface. Clarify which surface
the Javadoc is referring to. Also document that the VideoSink can be fed
with images, and that multiple renderers can feed the same sink.

PiperOrigin-RevId: 649052551
2024-07-03 06:31:40 -07:00
claincly
ed3a741601 Fix MCVR crash when seeking in HDR10 videos
MCVR crashed because MCVR registers a new input stream to VideoSink on every
`onOutputFormatChanged()`, assuming that `onOutputFormatChanged()` is only
invoked on media item transition. However, it can be called multiple times for
one media item.

PiperOrigin-RevId: 649050576
2024-07-03 06:22:44 -07:00
claincly
ce8ab84b7c Add test that covers clipping all videos in a sequence
PiperOrigin-RevId: 649048322
2024-07-03 06:13:08 -07:00
claincly
b9d101f090 Use a resolution that should be encode-able on all devices
The image in the test has a resolution of 1x1 which some device will reject.

PiperOrigin-RevId: 649039791
2024-07-03 05:32:56 -07:00
tianyifeng
567204e986 Version bump to 1.4.0-rc01
#cherrypick

PiperOrigin-RevId: 648982615
(cherry picked from commit b531d93b90)
2024-07-03 10:25:39 +00:00
andrewlewis
0b96f4372f Rollback of 95260e28a5
PiperOrigin-RevId: 649003095
2024-07-03 02:52:00 -07:00
tianyifeng
b531d93b90 Version bump to 1.4.0-rc01
#cherrypick

PiperOrigin-RevId: 648982615
2024-07-03 01:27:39 -07:00
claincly
73da1c09bd Call onProcessedStreamChange() for every media item change
Added `MCR.experimentalEnableProcessedStreamChangedAtStart()` to guard this new
feature.

PiperOrigin-RevId: 648886533
2024-07-02 17:04:08 -07:00
tianyifeng
75dadeaa9e Update release notes for 1.4.0-rc01
PiperOrigin-RevId: 648745388
(cherry picked from commit 9277a34253)
2024-07-02 16:57:58 +00:00
sheenachhabra
3793a06bdd Add support for file format for depth/editing in Mp4Muxer
PiperOrigin-RevId: 648747038
2024-07-02 09:42:36 -07:00
tianyifeng
9277a34253 Update release notes for 1.4.0-rc01
#cherrypick

PiperOrigin-RevId: 648745388
2024-07-02 09:37:05 -07:00
dancho
91bf3d1da1 Use software decoder in VideoDecodingWrapper
Hardware decoder on some devices fails to write 1920x1080 YUV_420_888 buffers into an ImageReader. This change allows us to remove skipCalculateSsim device workaround in ExportTest.java.

VideoDecodingWrapper now uses media3.MediaExtractorCompat: necessary for parsing of MediaFormat#KEY_CODECS_STRING and decoder capabilities check

PiperOrigin-RevId: 648726721
2024-07-02 08:29:36 -07:00
andrewlewis
3b7d59ef4f Rollback of 95260e28a5
PiperOrigin-RevId: 648708459
2024-07-02 07:16:27 -07:00
tianyifeng
d97ec132b9 Suppress the lint "WrongConstant" error
Lint somehow complains that the integer resulting from the bit-manipulation shouldn't be passed as an @IntDef parameter.

#cherrypick

PiperOrigin-RevId: 648687698
(cherry picked from commit afe3826d7c)
2024-07-02 14:12:52 +00:00
tianyifeng
6946f49997 Add OptIn annotation to method declaration in demo app file
#cherrypick

PiperOrigin-RevId: 648641357
(cherry picked from commit 0510370bd2)
2024-07-02 14:12:52 +00:00
ibaker
5b60f6c67d Fix index out of bounds exception when a Subtitle is empty
Issue: androidx/media#1516

#cherrypick

PiperOrigin-RevId: 648416119
(cherry picked from commit 711d18de03)
2024-07-02 14:12:52 +00:00
bachinger
035c943219 Improve automatic error replication for legacy browsers
This change extends the error replication to a given set of
error codes (not only authentication error), but only
replicates an error if the caller of the service `Callback`
is a legacy controller. It also makes error replication
configurable so that apps can opt-out and report errors
manually instead, or define the error codes for which
replication is enabled.

The change also removes the restriction of `sendError` only
being available for Media3 controllers. Instead, sending an
error to a legacy controller updates the platform playback
state in the same way as sending the error to the media
notification controller.

#cherrypick

PiperOrigin-RevId: 648399237
(cherry picked from commit 70c063905c)
2024-07-02 14:12:52 +00:00
tianyifeng
4a319f19e3 Update translations
#cherrypick

PiperOrigin-RevId: 648385733
(cherry picked from commit 6bf2461f80)
2024-07-02 14:12:52 +00:00
simakova
0df98407d3 Update the composition README file
PiperOrigin-RevId: 648282532
(cherry picked from commit 16ef63cdfc)
2024-07-02 14:12:52 +00:00
michaelkatz
bd1704904e Cache audio timestamp frame position across track transition reset
Upon track transition of offloaded playback of gapless tracks, the framework will reset the audiotrack frame position. The `AudioTrackPositionTracker`'s `AudioTimestampPoller` must be made to expect the reset and cache accumulated sum of `AudioTimestamp.framePosition`.

#cherrypick

PiperOrigin-RevId: 647294360
(cherry picked from commit a58e77a5a6)
2024-07-02 14:12:52 +00:00
tonihei
adeef60c14 Send pending updates before adding discontinuity for error
When handling a playback error that originates from a future item in
the playlist, we added support for jumping to that item first,
ensuring the errors 'happen' for the right 'current item'.
See 79b688ef30.

However, when we add this new position discontinuity to the
playback state, there may already be other position discontinuities
pending from other parts of the code that executed before the
error. As we can't control that in this case (because it's part
of a generic try/catch block), we need to send any pending
updates first before handling the new change.

Issue: androidx/media#1483
PiperOrigin-RevId: 646968309
(cherry picked from commit 727645179b)
2024-07-02 14:12:47 +00:00
Copybara-Service
708dc6cab9 Merge pull request #1487 from colinkho:main
PiperOrigin-RevId: 646917527
(cherry picked from commit 6244d8605f)
2024-07-02 14:11:38 +00:00
rohks
0b87e176fd Use removeKey method instead of setting null for KEY_CODECS_STRING
Setting a `null` value doesn't remove the key as expected per the `MediaFormat` API documentation, using the `removeKey` method instead which is only available starting API level 29.

PiperOrigin-RevId: 646462402
(cherry picked from commit 12c42585d2)
2024-07-02 14:11:38 +00:00
ibaker
0f0a20bc1c Use MediaCodec.stop() before release() for surface switching bug
ExoPlayer used to call `stop()` before `release()`. This was removed in
<unknown commit>.

A framework bug introduced in Android 11 (API 30) resulted in some
DRM -> clear transitions failing during `MediaCodec.configure()`. An
investigation in Issue: google/ExoPlayer#8696 and b/191966399 identified that this was
due to `release()` returning 'too early' and the subsequent
`configure()` call was then trying to re-use a `Surface` that hadn't
been fully detached from the previous codec. This was fixed in
Android 13 (API 33) with http://r.android.com/2094347.

ExoPlayer worked around the framework bug by adding an arbitrary 50ms
sleep after a failed codec initialization, followed by retrying. This
was enough to resolve the problem in the test scenario on a OnePlus
AC2003.

Issue: androidx/media#1497 points out that 50ms might not be the appropriate delay
for all devices, so it's an incomplete fix. They suggested re-adding the
`MediaCodec.stop()` call instead. This also reliably resolves the issue
on the OnePlus AC2003 (with neither workaround in place, the problem
repros almost immediately).
PiperOrigin-RevId: 646461943

(cherry picked from commit 5fcc7433a1)
2024-07-02 14:11:38 +00:00
tonihei
a73d32a795 Rename DummyTrackOutput and DummyExtractorOutput
#cherrypick

PiperOrigin-RevId: 646434450
(cherry picked from commit 867410fece)
2024-07-02 14:11:38 +00:00
tonihei
0f18fd87ac Add guard against additional tracks reported by Extractors
Extractors should not report additional tracks once they called
ExtractorOutput.endTracks. This causes thread safety issues in
ProgressiveMediaPeriod where the array of sample queues is
extended while the playback thread accesses the arrays.

Detecting this problem early is beneficial to avoid unexplained
exceptions later one. In most cases where this may happen (namely
TS extractors finding new tracks), it's better to ignore the new
tracks instead of failing completely. So this change adds a
warning log message and assigns a placeholder output.

Note: The same workaround already exists in HlsSampleStreamWrapper
and MediaExtractorCompat.

Issue: androidx/media#1476
#cherrypick
PiperOrigin-RevId: 646427213
(cherry picked from commit 18e631ff79)
2024-07-02 14:11:38 +00:00
Copybara-Service
aa508b1aaf Merge pull request #1479 from dryganets:sdryanets/fix-handler-usage
PiperOrigin-RevId: 646402268
(cherry picked from commit 0466728497)
2024-07-02 14:11:38 +00:00
Copybara-Service
53bb87b7d6 Merge pull request #1416 from khouzam:customFormat
PiperOrigin-RevId: 646121082
(cherry picked from commit b026271c84)
2024-07-02 14:11:38 +00:00
tonihei
f49fa99aab Add fail-early checks for TrackSelectorResult correctness
The two arrays need to have the same length and the selection
must match in their nullness (unless for TYPE_NONE
renderers). Clarify this more clearly in the docs and add
new asssertions for it. This avoids that the player is failing
in obscure ways much later.

Issue: androidx/media#1473
#cherrypick
PiperOrigin-RevId: 646086833
(cherry picked from commit 71ef848ec3)
2024-07-02 14:11:38 +00:00
okunhardt
ddf188552e In DemoUtil, don't set cookie handler when using HttpEngineDataSource.
HttpEngine does not support cookie storage.

#cherrypick

PiperOrigin-RevId: 646084702
(cherry picked from commit bb568b5150)
2024-07-02 14:11:38 +00:00
tonihei
3a5e367b93 Fix flakiness in MediaCodecVideoRendererTest
The test is flaky because the decoding process in the renderer
depends on some timing from MediaCodec beyond our control and
the new keyframe added in the test is sometimes 'dropped' when
it arrives too late.

We can fix this by controlling the test progress a bit more
tightly: first rendering with the same current time until the
key frame is processed and then start increasing the time
until we've reached the end.

#cherrypick

PiperOrigin-RevId: 646064352
(cherry picked from commit ada4dc982f)
2024-07-02 14:11:38 +00:00
okunhardt
b433bf928b Use HttpEngineDataSource when supported in demo app.
HttpEngineDataSource is the recommended HttpDataSource when it is available. It uses the [HttpEngine](https://developer.android.com/reference/android/net/http/HttpEngine).

#cherrypick

PiperOrigin-RevId: 646051562
(cherry picked from commit e591c37b1e)
2024-07-02 14:11:37 +00:00
ibaker
9b713907ce Add null-check to PlayerView to avoid NPE in edit mode
Previously we assumed that `surfaceSyncGroupV34` was always non-null on
API 34, but this isn't true in edit mode. Instead we add an explicit
null-check before accessing it. We don't need to null-check it at the
other usage site because we are already null-checking `surfaceView` (via
`instanceof` check).

Issue: androidx/media#1237

#cherrypick

PiperOrigin-RevId: 645008049
(cherry picked from commit 99803066ea)
2024-07-02 14:11:37 +00:00
ibaker
f645e9ccdc Remove direct AspectRatioFrameLayout usage from session demo
This class is a lower-level UI component that isn't directly needed if
apps are using `PlayerView` to handle their video output (it is used as
an implementation detail of `PlayerView`).

Removing its unecessary usages from this demo avoids developers copying
this as an example when building their own apps.

#cherrypick

PiperOrigin-RevId: 644972454
(cherry picked from commit cb8f87e05e)
2024-07-02 14:11:37 +00:00
tonihei
c14110cdbf Fix audio focus handling in ExoPlayerImpl
Some cases are not handled correctly at the moment:
 - Pausing during suppressed playback should not clear the
   suppression state.
 - Transient focus loss while paused should be reported as
   a playback suppression.

Issue: androidx/media#1436
#cherrypick
PiperOrigin-RevId: 644971218
(cherry picked from commit e84bb0d21c)
2024-07-02 14:11:37 +00:00
tonihei
05571b3e0d Clarify that onPlayWhenReadyChanged can be called again with new reason
Sometimes the reason for the current state may change. If we don't
report this again, users have no way of knowing that the reason
changed.

Also adjust ExoPlayerImpl and MediaControllerImplBase accordingly.
SimpleBasePlayer already adheres to this logic.

#cherrypick

PiperOrigin-RevId: 644970236
(cherry picked from commit 1d26d1891e)
2024-07-02 14:11:37 +00:00
tonihei
2fd6b60daa Move playWhenReadyChangeReason inside PlaybackInfo
This helps to keep the reason always together with the state it
is referring to, avoiding any side channels and making sure there
are no accidental inconsistencies.

#cherrypick

PiperOrigin-RevId: 644969317
(cherry picked from commit c0abd6f91e)
2024-07-02 14:11:37 +00:00
ibaker
30cb76269a Use SurfaceSyncGroup to ensure resize transaction isn't dropped
This workaround is only applied on API 34, because the problem isn't
present on API 33 and it is fixed in the platform for API 35 onwards.

Issue: androidx/media#1237

#cherrypick

PiperOrigin-RevId: 644729909
(cherry picked from commit 968f72fec6)
2024-07-02 14:11:37 +00:00
bachinger
4330d6a952 Use a localized fallback message for known error codes
In the case of a legacy session app providing an error
code different to `ERROR_UNKNOWN` without an error
message, a localized fallback message is provided
instead of ignoring the error.

#cherrypick

PiperOrigin-RevId: 644704680
(cherry picked from commit 6cc6444dd9)
2024-07-02 14:11:37 +00:00
bachinger
56ae85fa3c Allow session activity to be set per controller
PiperOrigin-RevId: 644693533
(cherry picked from commit 856d394c28)
2024-07-02 14:11:31 +00:00
tonihei
bd5f99cb09 Audio focus player command clean up
The 'player commands' returned to ExoPlayerImpl instruct the
player on how to treat the current audio focus state.

The current return value when playWhenReady==false is misleading
because it implies we are definitely not allowed to play as if
we've lost focus. Instead, we should return the actual player
command corresponding to the focus state we are in.

This has no practical effect in ExoPlayerImpl as we already
ignore the 'player command' completely  when playWhenReady=false.

To facilitate this change, we also introduce a new internal
state for FOCUS_NOT_REQUESTED to distinguish it from the state
in which we lost focus.

#cherrypick

PiperOrigin-RevId: 644416586
(cherry picked from commit 66c19390e2)
2024-07-02 14:10:12 +00:00
tonihei
d76316a1f7 Improve audio focus handling tests with ExoPlayer
There are a lot of tests for AudioFocusManager in isolation,
but almost none for the handling in ExoPlayer.

Add test coverage for all the common cases, including some
currently broken behavior that is indicated by TODOs.

PiperOrigin-RevId: 644319251
(cherry picked from commit e20e94fde2)
2024-07-02 14:10:12 +00:00
tianyifeng
afe3826d7c Suppress the lint "WrongConstant" error
Lint somehow complains that the integer resulting from the bit-manipulation shouldn't be passed as an @IntDef parameter.

#cherrypick

PiperOrigin-RevId: 648687698
2024-07-02 05:49:23 -07:00
andrewlewis
95260e28a5 Add input type for automatic frame registration
Deprecate `setInputDefaultBufferSize` and `setRequireRegisteringAllInputFrames`
as the new input stream type replaces these (as far as we know they are always
used together).

This is in preparation for supporting asset loaders signaling that they require
these features, specifically for recording from a surface.

PiperOrigin-RevId: 648686087
2024-07-02 05:41:23 -07:00
kimvde
a2087ba5bb Improve Javadoc of VideoSink.registerInputFrame/queueBitmap
Document that the stream must be registered before

PiperOrigin-RevId: 648648650
2024-07-02 02:50:02 -07:00
ibaker
03a205f220 Re-order CEA-6/708 samples during extraction instead of rendering
This is required before we can move CEA-6/708 parsing from the rendering
side of the sample queue to the extraction side.

This re-ordering is needed for video encodings with different decoder
and presentation orders, because the CEA-6/708 data is attached to each
frame and needs to be processed in presentation order instead of decode
order. This change re-orders frames within a group-of-pictures, but also
takes advantage of `maxNumReorderFrames/Pics` values to cap the size of
the re-ordering queue, allowing caption data to be released 'earlier'
than the end of a GoP.

Annex D of the CEA-708 spec (which also applies for CEA-608 embedded in
SEI messages), makes the need to re-order from decode to presentation
order clear.

PiperOrigin-RevId: 648648002
2024-07-02 02:47:45 -07:00
tianyifeng
0510370bd2 Add OptIn annotation to method declaration in demo app file
#cherrypick

PiperOrigin-RevId: 648641357
2024-07-02 02:19:18 -07:00
bachinger
ec3a58f8db Count down three playback states to match the assertion
PiperOrigin-RevId: 648629427
2024-07-02 01:30:38 -07:00
tianyifeng
7fb6eee920 Add PreloadException with initial subset of error codes
As the first version, the error codes only include the miscellaneous and IO errors, but are likely to be extended.

PiperOrigin-RevId: 648466385
2024-07-01 13:24:34 -07:00
ibaker
711d18de03 Fix index out of bounds exception when a Subtitle is empty
Issue: androidx/media#1516

#cherrypick

PiperOrigin-RevId: 648416119
2024-07-01 10:40:15 -07:00
bachinger
70c063905c Improve automatic error replication for legacy browsers
This change extends the error replication to a given set of
error codes (not only authentication error), but only
replicates an error if the caller of the service `Callback`
is a legacy controller. It also makes error replication
configurable so that apps can opt-out and report errors
manually instead, or define the error codes for which
replication is enabled.

The change also removes the restriction of `sendError` only
being available for Media3 controllers. Instead, sending an
error to a legacy controller updates the platform playback
state in the same way as sending the error to the media
notification controller.

#cherrypick

PiperOrigin-RevId: 648399237
2024-07-01 09:47:25 -07:00
tianyifeng
6bf2461f80 Update translations
#cherrypick

PiperOrigin-RevId: 648385733
2024-07-01 09:02:21 -07:00
simakova
16ef63cdfc Update the composition README file
PiperOrigin-RevId: 648282532
2024-07-01 01:34:17 -07:00
dancho
9939d77d14 Change test to output 16x width and height
PiperOrigin-RevId: 647716870
2024-06-28 10:03:48 -07:00
claincly
174d5ea530 Update test golden images
Now VFP receives actual (un-offsetted) frame presentation time, updates the
test goldens to match.

PiperOrigin-RevId: 647665323
2024-06-28 07:04:47 -07:00
ktrajkovski
e4d4a776c3 Remove deprecated hasPreviousWindow() and hasPrevious() methods.
Use Player.hasPreviousMediaItem() and Player.seekToPreviousMediaItem() instead.

PiperOrigin-RevId: 647664991
2024-06-28 07:02:33 -07:00
dancho
18b28cd625 Skip seahawk device for 8K encoding
PiperOrigin-RevId: 647647264
2024-06-28 05:40:50 -07:00
ktrajkovski
e392084c4d Remove deprecated DrmSessionEventListener.onDrmSessionAcquired method.
#cherrypick

PiperOrigin-RevId: 647620751
2024-06-28 03:36:51 -07:00
ktrajkovski
47b1ca18ed Remove deprecated Player#hasPrevious() method.
Use Player#hasPreviousMediaItem() instead.

#cherrypick

PiperOrigin-RevId: 647336042
2024-06-27 09:04:21 -07:00
Googler
3da63eeaa7 Add NAL unit parsing needed for stereo MV-HEVC playback.
Add the following NAL unit parsing utility functions that will be needed for the MV-HEVC support as proposed in Apple's HEVC stereo video interoperability profile:
- NAL unit header parsing to get the layer information needed for MV-HEVC support.
- VPS parsing, including vps_extension() needed for MV-HEVC support.
- SPS parsing modifications to support MV-HEVC.

PiperOrigin-RevId: 647329211
2024-06-27 08:39:12 -07:00
michaelkatz
304bcfc852 Fix spelling typo in 1.4.0-beta01 release notes
PiperOrigin-RevId: 647327810
2024-06-27 08:35:06 -07:00
michaelkatz
a58e77a5a6 Cache audio timestamp frame position across track transition reset
Upon track transition of offloaded playback of gapless tracks, the framework will reset the audiotrack frame position. The `AudioTrackPositionTracker`'s `AudioTimestampPoller` must be made to expect the reset and cache accumulated sum of `AudioTimestamp.framePosition`.

#cherrypick

PiperOrigin-RevId: 647294360
2024-06-27 06:27:32 -07:00
andrewlewis
dcbded0fa9 Rename cancel to pause in Transformer demo
The user might expect this button to back out to the configuration activity,
but actually it toggles pause/resume (though `cancel` is the method called).

PiperOrigin-RevId: 647273416
2024-06-27 04:59:13 -07:00
michaelkatz
023e9d1479 Version bump to media3:1.4.0-beta01
PiperOrigin-RevId: 644352776
(cherry picked from commit c07bbd333c)
2024-06-27 09:34:04 +00:00
tonihei
727645179b Send pending updates before adding discontinuity for error
When handling a playback error that originates from a future item in
the playlist, we added support for jumping to that item first,
ensuring the errors 'happen' for the right 'current item'.
See 79b688ef30.

However, when we add this new position discontinuity to the
playback state, there may already be other position discontinuities
pending from other parts of the code that executed before the
error. As we can't control that in this case (because it's part
of a generic try/catch block), we need to send any pending
updates first before handling the new change.

Issue: androidx/media#1483
#cherrypick
PiperOrigin-RevId: 646968309
2024-06-26 09:09:01 -07:00
kimvde
25b8385cff Fix Javadoc of VideoSink.setStreamOffsetAndAdjustmentUs
PiperOrigin-RevId: 646942034
2024-06-26 07:40:26 -07:00
Copybara-Service
6244d8605f Merge pull request #1487 from colinkho:main
PiperOrigin-RevId: 646917527
2024-06-26 06:05:07 -07:00
sheenachhabra
6fc0243106 Use Set instead of a List for metadata collection
All metadata entries are supposed to be unique, so Set is more appropriate.

PiperOrigin-RevId: 646907916
2024-06-26 05:29:47 -07:00
claincly
efbd522df9 Fix test with TimestampWrapper
The renderer offset is not needed as the pipeline now takes un-offset time,
from 73bf852405

PiperOrigin-RevId: 646808594
2024-06-26 03:48:43 -07:00
kimvde
3694487285 Correct documented Transformer HDR limitation
PiperOrigin-RevId: 646798618
2024-06-26 03:08:08 -07:00
claincly
9e7318e3b4 Clarify the HDR10 video in the demos is actually HDR10+
It's captured on a Samsung and has dynamic metadata.

PiperOrigin-RevId: 646796836
2024-06-26 03:02:00 -07:00
Ian Baker
a15710ba44 Reformat and add/remove some final keywords 2024-06-25 15:51:03 +01:00
Colin Kho
2ee69cb1f9 Avoid unnecessary getSystemService call on WifiLockManager and WakeLockManager if not enabled 2024-06-25 15:51:02 +01:00
sheenachhabra
be2d68c2b3 Improve method names in Mp4Writer
PiperOrigin-RevId: 646465516
2024-06-25 07:09:12 -07:00
rohks
12c42585d2 Use removeKey method instead of setting null for KEY_CODECS_STRING
Setting a `null` value doesn't remove the key as expected per the `MediaFormat` API documentation, using the `removeKey` method instead which is only available starting API level 29.

PiperOrigin-RevId: 646462402
2024-06-25 06:57:19 -07:00
ibaker
5fcc7433a1 Use MediaCodec.stop() before release() for surface switching bug
ExoPlayer used to call `stop()` before `release()`. This was removed in
<unknown commit>.

A framework bug introduced in Android 11 (API 30) resulted in some
DRM -> clear transitions failing during `MediaCodec.configure()`. An
investigation in Issue: google/ExoPlayer#8696 and b/191966399 identified that this was
due to `release()` returning 'too early' and the subsequent
`configure()` call was then trying to re-use a `Surface` that hadn't
been fully detached from the previous codec. This was fixed in
Android 13 (API 33) with http://r.android.com/2094347.

ExoPlayer worked around the framework bug by adding an arbitrary 50ms
sleep after a failed codec initialization, followed by retrying. This
was enough to resolve the problem in the test scenario on a OnePlus
AC2003.

Issue: androidx/media#1497 points out that 50ms might not be the appropriate delay
for all devices, so it's an incomplete fix. They suggested re-adding the
`MediaCodec.stop()` call instead. This also reliably resolves the issue
on the OnePlus AC2003 (with neither workaround in place, the problem
repros almost immediately).
PiperOrigin-RevId: 646461943
2024-06-25 06:54:45 -07:00
claincly
73bf852405 Make ExoPlayer.setVideoEffects() timestamp start from 0
This is consistent with `Transformer` and `CompositionPlayer`

Issue: androidx/media#1098
PiperOrigin-RevId: 646446824
2024-06-25 05:59:15 -07:00
tonihei
867410fece Rename DummyTrackOutput and DummyExtractorOutput
#cherrypick

PiperOrigin-RevId: 646434450
2024-06-25 05:07:56 -07:00
tonihei
18e631ff79 Add guard against additional tracks reported by Extractors
Extractors should not report additional tracks once they called
ExtractorOutput.endTracks. This causes thread safety issues in
ProgressiveMediaPeriod where the array of sample queues is
extended while the playback thread accesses the arrays.

Detecting this problem early is beneficial to avoid unexplained
exceptions later one. In most cases where this may happen (namely
TS extractors finding new tracks), it's better to ignore the new
tracks instead of failing completely. So this change adds a
warning log message and assigns a placeholder output.

Note: The same workaround already exists in HlsSampleStreamWrapper
and MediaExtractorCompat.

Issue: androidx/media#1476
#cherrypick
PiperOrigin-RevId: 646427213
2024-06-25 04:38:22 -07:00
Copybara-Service
0466728497 Merge pull request #1479 from dryganets:sdryanets/fix-handler-usage
PiperOrigin-RevId: 646402268
2024-06-25 02:56:09 -07:00
kimvde
304c4e41f8 Call VideoFrameReleaseControl.isReady from VideoSink when enabled
PiperOrigin-RevId: 646385384
2024-06-25 01:51:14 -07:00
sheenachhabra
babc9c69c6 Remove unnecessary FileChannel from Mp4Muxer
As per the documentation, closing a `FileOutputStream`
automatically closes the associated `FileChannel`.

PiperOrigin-RevId: 646152280
2024-06-24 10:58:30 -07:00
sheenachhabra
327f728010 Move muxer closing logic from Mp4Writer to Mp4Muxer
PiperOrigin-RevId: 646134522
2024-06-24 10:11:52 -07:00
Copybara-Service
b026271c84 Merge pull request #1416 from khouzam:customFormat
PiperOrigin-RevId: 646121082
2024-06-24 09:30:28 -07:00
tonihei
58864a4bb9 Additional variable changes + argument checks in HandlerWrapper 2024-06-24 16:42:02 +01:00
Sergei Dryganets
457deec4eb Stop using what == 0 for messages. 2024-06-24 16:26:27 +01:00
tonihei
b6070a5299 Formatting fixes 2024-06-24 16:10:13 +01:00
tonihei
71ef848ec3 Add fail-early checks for TrackSelectorResult correctness
The two arrays need to have the same length and the selection
must match in their nullness (unless for TYPE_NONE
renderers). Clarify this more clearly in the docs and add
new asssertions for it. This avoids that the player is failing
in obscure ways much later.

Issue: androidx/media#1473
#cherrypick
PiperOrigin-RevId: 646086833
2024-06-24 07:30:25 -07:00
okunhardt
bb568b5150 In DemoUtil, don't set cookie handler when using HttpEngineDataSource.
HttpEngine does not support cookie storage.

#cherrypick

PiperOrigin-RevId: 646084702
2024-06-24 07:21:08 -07:00
samrobinson
938fac4161 Update CompositionPlayer state for volume.
PiperOrigin-RevId: 646071591
2024-06-24 06:25:28 -07:00
tonihei
ada4dc982f Fix flakiness in MediaCodecVideoRendererTest
The test is flaky because the decoding process in the renderer
depends on some timing from MediaCodec beyond our control and
the new keyframe added in the test is sometimes 'dropped' when
it arrives too late.

We can fix this by controlling the test progress a bit more
tightly: first rendering with the same current time until the
key frame is processed and then start increasing the time
until we've reached the end.

#cherrypick

PiperOrigin-RevId: 646064352
2024-06-24 05:53:48 -07:00
okunhardt
e591c37b1e Use HttpEngineDataSource when supported in demo app.
HttpEngineDataSource is the recommended HttpDataSource when it is available. It uses the [HttpEngine](https://developer.android.com/reference/android/net/http/HttpEngine).

#cherrypick

PiperOrigin-RevId: 646051562
2024-06-24 04:52:15 -07:00
Gilles Khouzam
d717a0c5d5 Add a CustomData field to the Format class
Summary:
    This change aims to add a generic `CustomData` field to the `Format` class.

    The intent is to allow ExoPlayer customers to add extra data to the Format class without forcing
    specific data to be included, impacting customers that do not need it and would allow for the data
    to be changed without requiring changes to the `Media3` codebase.
2024-06-24 09:43:00 +01:00
dancho
476ec607f2 Implement isNoOp for LanczosResample
This allows for transmuxing whenever resolutions match,
and LanczosResample is in the video effects chain.

PiperOrigin-RevId: 645433104
2024-06-21 10:37:19 -07:00
simakova
d16004781e Remove AspectRatioFrameLayout usage from transformer demo
Removing unnecessary usage from transformer demo

PiperOrigin-RevId: 645426871
2024-06-21 10:18:30 -07:00
samrobinson
f1fadccef5 Add software decoder workaround for redmi 7a.
PiperOrigin-RevId: 645383707
2024-06-21 07:31:18 -07:00
claincly
89fbd0d27a Add Accept header to DESCRIBE request
The Accept header is required by some servers, and we only support SDP.

Issue: google/ExoPlayer#10919
PiperOrigin-RevId: 645361576
2024-06-21 05:47:52 -07:00
simakova
52bd9a2815 Add an option to include background audio sequence in Composition.
PiperOrigin-RevId: 645100835
2024-06-20 11:29:28 -07:00
ibaker
99803066ea Add null-check to PlayerView to avoid NPE in edit mode
Previously we assumed that `surfaceSyncGroupV34` was always non-null on
API 34, but this isn't true in edit mode. Instead we add an explicit
null-check before accessing it. We don't need to null-check it at the
other usage site because we are already null-checking `surfaceView` (via
`instanceof` check).

Issue: androidx/media#1237

#cherrypick

PiperOrigin-RevId: 645008049
2024-06-20 06:30:42 -07:00
sheenachhabra
307655f6d5 Move component initialization from Mp4Muxer.Builder to Mp4Muxer
PiperOrigin-RevId: 645004885
2024-06-20 06:18:13 -07:00
ibaker
cb8f87e05e Remove direct AspectRatioFrameLayout usage from session demo
This class is a lower-level UI component that isn't directly needed if
apps are using `PlayerView` to handle their video output (it is used as
an implementation detail of `PlayerView`).

Removing its unecessary usages from this demo avoids developers copying
this as an example when building their own apps.

#cherrypick

PiperOrigin-RevId: 644972454
2024-06-20 04:06:23 -07:00
tonihei
e84bb0d21c Fix audio focus handling in ExoPlayerImpl
Some cases are not handled correctly at the moment:
 - Pausing during suppressed playback should not clear the
   suppression state.
 - Transient focus loss while paused should be reported as
   a playback suppression.

Issue: androidx/media#1436
#cherrypick
PiperOrigin-RevId: 644971218
2024-06-20 04:00:57 -07:00
tonihei
1d26d1891e Clarify that onPlayWhenReadyChanged can be called again with new reason
Sometimes the reason for the current state may change. If we don't
report this again, users have no way of knowing that the reason
changed.

Also adjust ExoPlayerImpl and MediaControllerImplBase accordingly.
SimpleBasePlayer already adheres to this logic.

#cherrypick

PiperOrigin-RevId: 644970236
2024-06-20 03:58:05 -07:00
tonihei
c0abd6f91e Move playWhenReadyChangeReason inside PlaybackInfo
This helps to keep the reason always together with the state it
is referring to, avoiding any side channels and making sure there
are no accidental inconsistencies.

#cherrypick

PiperOrigin-RevId: 644969317
2024-06-20 03:54:04 -07:00
samrobinson
f2305cc05c Add a parameterized android test for single asset exports.
PiperOrigin-RevId: 644740900
2024-06-19 07:23:01 -07:00
kimvde
4751b80703 Call VideoFrameReleaseControl.join from VideoSink when enabled
PiperOrigin-RevId: 644738200
2024-06-19 07:09:38 -07:00
samrobinson
ff4feed0eb Add case to parameterized sequence test for no composition effects.
PiperOrigin-RevId: 644734136
2024-06-19 06:48:39 -07:00
ibaker
968f72fec6 Use SurfaceSyncGroup to ensure resize transaction isn't dropped
This workaround is only applied on API 34, because the problem isn't
present on API 33 and it is fixed in the platform for API 35 onwards.

Issue: androidx/media#1237

#cherrypick

PiperOrigin-RevId: 644729909
2024-06-19 06:27:13 -07:00
bachinger
6cc6444dd9 Use a localized fallback message for known error codes
In the case of a legacy session app providing an error
code different to `ERROR_UNKNOWN` without an error
message, a localized fallback message is provided
instead of ignoring the error.

#cherrypick

PiperOrigin-RevId: 644704680
2024-06-19 04:28:20 -07:00
bachinger
856d394c28 Allow session activity to be set per controller
#cherrypick

PiperOrigin-RevId: 644693533
2024-06-19 03:37:02 -07:00
kimvde
30b9c976ea Fix Javadoc of EditedMediaItem.Builder.setDurationUs
The Javadoc was indicating that the duration should always be set,
but it doesn't need to be set in most cases for export.

PiperOrigin-RevId: 644685827
2024-06-19 03:03:15 -07:00
samrobinson
afa7935553 Split parameterized android test utils into utility class.
Includes adjusting how effects are defined, to make it clearer in a
test that a given ItemConfig has effects associated with it.

PiperOrigin-RevId: 644684308
2024-06-19 02:56:34 -07:00
kimvde
d27549d29a Skip 4K export test on Pixel 3a
PiperOrigin-RevId: 644659699
2024-06-19 01:18:05 -07:00
tonihei
66c19390e2 Audio focus player command clean up
The 'player commands' returned to ExoPlayerImpl instruct the
player on how to treat the current audio focus state.

The current return value when playWhenReady==false is misleading
because it implies we are definitely not allowed to play as if
we've lost focus. Instead, we should return the actual player
command corresponding to the focus state we are in.

This has no practical effect in ExoPlayerImpl as we already
ignore the 'player command' completely  when playWhenReady=false.

To facilitate this change, we also introduce a new internal
state for FOCUS_NOT_REQUESTED to distinguish it from the state
in which we lost focus.

#cherrypick

PiperOrigin-RevId: 644416586
2024-06-18 09:42:26 -07:00
kimvde
048d71e392 Change muxer video duration unit to microseconds
PiperOrigin-RevId: 644402109
2024-06-18 08:56:26 -07:00
kimvde
ada7271974 Add a method to change the frame rate strategy from the VideoSink
PiperOrigin-RevId: 644373231
2024-06-18 07:11:58 -07:00
michaelkatz
cfeee5b34e Update release notes for 1.4.0-beta01
#cherrypick

PiperOrigin-RevId: 644351958
(cherry picked from commit 794731607d)
2024-06-18 13:43:30 +00:00
samrobinson
1d8b2e3f43 Migrate ParameterizedInputSequenceExportTest to AssetInfo for images.
PiperOrigin-RevId: 644363298
2024-06-18 06:31:56 -07:00
michaelkatz
c07bbd333c Version bump to media3:1.4.0-beta01
#cherrypick

PiperOrigin-RevId: 644352776
2024-06-18 05:52:03 -07:00
michaelkatz
794731607d Update release notes for 1.4.0-beta01
#cherrypick

PiperOrigin-RevId: 644351958
2024-06-18 05:48:00 -07:00
tonihei
e20e94fde2 Improve audio focus handling tests with ExoPlayer
There are a lot of tests for AudioFocusManager in isolation,
but almost none for the handling in ExoPlayer.

Add test coverage for all the common cases, including some
currently broken behavior that is indicated by TODOs.

PiperOrigin-RevId: 644319251
2024-06-18 03:24:21 -07:00
samrobinson
21ad768628 Add AndroidTestUtil missing asset Format info.
Also adds basic support for canDecode receiving an image Format.

PiperOrigin-RevId: 644300521
2024-06-18 02:06:59 -07:00
kimvde
f0aa30555a Remove calls to VideoFrameReleaseControl.join in CompositionPlayer
These calls have no effect because the VideoFrameReleaseControl of
CompositionPlayer is created with allowedJoiningTimeMs set to 0.

PiperOrigin-RevId: 644274524
2024-06-18 00:22:25 -07:00
samrobinson
2698f3ffc2 Migrate performance tests to use AndroidTestUtil constants.
PiperOrigin-RevId: 644058273
2024-06-17 10:38:23 -07:00
samrobinson
2b55a5bc2d Create an AssetInfo class for AndroidTestUtil test asset information.
This is an internal refactor with no logic changed.

There is a duplication in information and a lack of consistency around
the use of test assets in transformer androidTest. This change
refactors each asset to be defined as its own AssetInfo, with the other
relevant parts stored alongside the uri.

Once this is in place, we can consider other useful functionality, such
as having boolean flags for what tracks an asset has, helper methods
for whether an asset is local or remote, and more. This will reduce the
manual overhead necessary to use more assets in tests, and in
particular leads towards easily using new & existing assets in
parameterized tests.

PiperOrigin-RevId: 644040595
2024-06-17 09:47:56 -07:00
ibaker
d0815d3f7b Deprecate Util.areEqual in favour of Objects.equals
`Objects.equals` has been available since API 19.

PiperOrigin-RevId: 644026884
2024-06-17 09:04:48 -07:00
michaelkatz
32bedfa93e Fix linter errors in DemoMediaLibrarySessionCallback.kt
PiperOrigin-RevId: 644002147
(cherry picked from commit ed07ac5d7d)
2024-06-17 14:57:01 +00:00
Copybara-Service
f36395ae66 Merge pull request #1437 from MGaetan89:add_exoplayer_setMaxSeekToPreviousPosition
PiperOrigin-RevId: 643987403
(cherry picked from commit 67a7b41fa7)
2024-06-17 14:57:01 +00:00
michaelkatz
ed07ac5d7d Fix linter errors in DemoMediaLibrarySessionCallback.kt
PiperOrigin-RevId: 644002147
2024-06-17 07:37:00 -07:00
Copybara-Service
67a7b41fa7 Merge pull request #1437 from MGaetan89:add_exoplayer_setMaxSeekToPreviousPosition
PiperOrigin-RevId: 643987403
2024-06-17 06:38:02 -07:00
samrobinson
6dcbafad21 Use AndroidTestUtil constants so test asset information is consistent.
PiperOrigin-RevId: 643984158
2024-06-17 06:23:22 -07:00
sheenachhabra
ded1adc092 Change sample duration type from Long to Integer
In muxer only 32-bit sample duration is supported. Earlier the duration was type
casted at different places.

PiperOrigin-RevId: 643954226
2024-06-17 04:13:00 -07:00
kimvde
eedfb9960e Reset release control from video sink when enabled
PiperOrigin-RevId: 643950097
2024-06-17 03:58:13 -07:00
sheenachhabra
aeb8fd134b Write moov box at the start of the file if possible
This is done by reserving some space for moov box at the start of the file and writing it there if it fits. If it doesn't fit, then it is written at the end of the file.

PiperOrigin-RevId: 643944698
2024-06-17 03:38:11 -07:00
tonihei
cd2250b5fa Formatting fixes and additional plumbin in legacy controller 2024-06-14 17:47:03 +01:00
Gaëtan Muller
63103978be Make MediaControllerImplLegacy.getMaxSeekToPreviousPosition() return the correct value 2024-06-14 16:21:31 +01:00
Gaëtan Muller
424d2a52fe Support setting the max seek to previous position on CastPlayer 2024-06-14 16:21:30 +01:00
Gaëtan Muller
6153b6d740 Add the ExoPlayer.Builder.setMaxSeekToPreviousPosition(long) method
This method allows customizing the maximum position when using `Player.seekToPrevious()`.

This commit also adds two new methods to `TestExoPlayerBuilder`:
- `setMaxSeekToPreviousPosition(long)`
- `getMaxSeekToPreviousPosition()`
2024-06-14 16:21:30 +01:00
samrobinson
4109e2edd9 Add more cases for parameterized video android tests.
PiperOrigin-RevId: 643346610
2024-06-14 08:04:13 -07:00
ibaker
7fbaae66ec Add demo-composition to settings.gradle
This was missed as part of 0e5a5e0294

#cherrypick

PiperOrigin-RevId: 643331307
2024-06-14 07:01:57 -07:00
bachinger
872d8f078b Rollback of cd9b914c42
PiperOrigin-RevId: 643329324
2024-06-14 06:42:31 -07:00
tonihei
4cd8d64446 Image support in PlayerView
Images are rendered into an ImageView (on top of the video shutter).
The image view is set to the images emitted by ExoPlayer's ImageOutput
and cleared when there is no longer a selected image track.

In order to keep the existing behavior of video tracks to only clear
the old output once the new first frame is rendered (avoiding short
periods of black between playlist items), we have to reorder this code
slightly to make it work for video and images. Both are treated in the
same way. If both are enabled, video takes precedence.

As the UI module only depends on the common module, we can't direcly
add the ImageOutput to ExoPlayer. This is done via reflection if
the provided Player is an ExoPlayer.

#cherrypick

PiperOrigin-RevId: 643320666
2024-06-14 05:33:23 -07:00
bachinger
cd9b914c42 Remove PreloadConfiguration from public API
This feature isn't completed, so we should remove
the public facing API to avoid confusion.

#minor-release

PiperOrigin-RevId: 643318692
2024-06-14 05:23:53 -07:00
ibaker
93af537af7 Parse 'max num reorder samples' values from h.264 and h.265 videos
This value is used in a follow-up change to re-order SEI messages
containing CEA-6/708 data from decode order to presentation order.

PiperOrigin-RevId: 643296338
2024-06-14 03:31:38 -07:00
tofunmi
174c49313c support hdr text overlays
adds luminance multiplier to allow the luminance (i.e. brightness) over a text overlay to be scaled

PiperOrigin-RevId: 643047928
2024-06-13 10:41:09 -07:00
tofunmi
81f15dbd37 SpeedChangingAP: synchronize fields accessed from multiple threads
PiperOrigin-RevId: 643046385
2024-06-13 10:36:49 -07:00
rohks
df5352752f Add a drop-in replacement for MediaExtractor in Media3
This change introduces a new class in Media3 `MediaExtractorCompat`, designed to be a drop-in replacement for platform `MediaExtractor`. While not all APIs are currently supported, the core functionality for the most common use cases of `MediaExtractor` is now available. Full API compatibility will be achieved in the future.

PiperOrigin-RevId: 643045429
2024-06-13 10:33:38 -07:00
samrobinson
e985603e0a Refactor mixedInput E2E test to use parameterized logic.
This CL is a pure refactor of the existing tests, iterative changes
will be done in follow-ups.

The only logic change is having all MP4 assets have the presentaton of
height=360. The old code had some with height 480.
PiperOrigin-RevId: 643020773
2024-06-13 09:17:58 -07:00
sheenachhabra
a39a7f06cf Remove the code to restore current output position
Muxer never uses latest output position but always writes to
a specific location, so restoring its position does not add any
value.

PiperOrigin-RevId: 642996941
2024-06-13 08:07:16 -07:00
claincly
206d2ce8b8 Effect: Delay end of stream until all frames are rendered.
Previously, if renderFramesAutomatically = false, DefaultVideoFrameProcessor
may call onInputStreamProcessedListener after all frames have been
onOutputFrameAvailableForRendering, but before they had all been rendered and
freed.

Delay onInputStreamProcessedListener being called and subsequent DVFP
reconfiguration of effects, until all frames are rendered.

Tested using exoplayer setVideoEffects demo with playlist

PiperOrigin-RevId: 642963100
2024-06-13 06:22:03 -07:00
andrewlewis
a0312615f2 Fix AVI extractor WAVE format extraction
Allow `WAVEFORMAT` (in addition to `WAVEFORMATEX`), which omits initialization
data.

Fix reading of bits per sample to use little endian byte order like the other
reads. See also the wave format docs linked from
https://learn.microsoft.com/en-us/windows/win32/directshow/avi-riff-file-reference#avi-stream-headers.

PiperOrigin-RevId: 642962893
2024-06-13 06:19:10 -07:00
rohks
d4802a429b Fix bug where enabling CMCD for HLS live streams causes error
Determine `nextMediaSequence` and `nextPartIndex` based on the last `SegmentBaseHolder` instance, as it can update `mediaSequence` and `partIndex` depending on whether the HLS playlist has trailing parts or not.

Issue: androidx/media#1395
PiperOrigin-RevId: 642961141
2024-06-13 06:12:08 -07:00
sheenachhabra
4f691a7c02 Add a checkbox to use Media3 muxer in Transformer demo app
PiperOrigin-RevId: 642941439
2024-06-13 04:49:17 -07:00
tianyifeng
86a60e6ec2 Schedule refresh for all the playing playlists for HLS live stream
Issue: androidx/media#1240
PiperOrigin-RevId: 642927082
2024-06-13 03:52:16 -07:00
tonihei
ca51ed649b Fix single sample handling ProgressiveMediaPeriod when disabling tracks
When deselecting the single sample track and later re-selecting this
track, the current shortcuts in ProgressiveMediaPeriod don't handle
this case correctly and cause assertion failures.

In particular, this change fixes 3 issues:
 1. When re-selecting the single sample track, we have cleared the
    SampleQueue and need to reload the sample. The existing shortcut
    should only be applied to avoid the reload when starting from a
    non-zero position.
 2. When de-selecting the track, ProgressiveMediaPeriod is left in
    an inconsistent state where the sample queues are empty but
    loadingFinished is still true. Fix this by resetting
    loadingFinished to false.
 3. When seeking, we avoid reloading the stream if we can keep
    inside the existing samples. This logic assumes that all
    remaining samples will continue to be loaded in the queue.
    This condition isn't true though for single sample tracks
    that have been de-selected. They appear to support the seek
    inside the queue (=no seek necessary, always supported), but
    still require a new load if there is no ongoing one to load
    the sample. Fix this by checking this implicit assumption
    (still loading, or loading finished).

PiperOrigin-RevId: 642650248
2024-06-12 10:08:10 -07:00
sheenachhabra
94dff1f349 Split muxer android tests between parameterized and non parameterized
This will be helpful for adding more tests which need not to
be parameterized.

PiperOrigin-RevId: 642638702
2024-06-12 09:29:22 -07:00
tonihei
54f58cafed Clarify semantics of MSG_SET_IMAGE_OUTPUT
The value can be null, which isn't mentioned in the docs yet

PiperOrigin-RevId: 642622583
2024-06-12 08:30:31 -07:00
tonihei
ebe74daaec Add image samples and track selection to demo app
Also move the track selection header strings to the demo app
as they are only used there (except for audio, which stays in UI)

PiperOrigin-RevId: 642616037
2024-06-12 08:02:52 -07:00
kimvde
6234a8bede Move usages of allowReleaseFirstFrameBeforeStarted inside sink
PiperOrigin-RevId: 642611061
2024-06-12 07:39:53 -07:00
sheenachhabra
0b2bca02ca Make nit improvements in muxer code
PiperOrigin-RevId: 642599475
2024-06-12 06:46:28 -07:00
claincly
0da892d935 Refactors the seek test and add more test cases
PiperOrigin-RevId: 642597298
2024-06-12 06:34:43 -07:00
bachinger
011ed909c0 Sync and map fatal and non-fatal errors from and to the legacy session
A fatal `PlaybackException` is mapped to a legacy playback state
in state `STATE_ERROR` with error code, message and extras. A
non-fatal error sent to controllers with `MediaSession.sendError`
is synced to the legacy session by setting error code and message
and merging the extras while preserving the rest of the state in
sync with the session player.

Vice versa, a `MediaController` connected to a legacy session receives
fatal errors through `Player.onPlayerErrorChanged()` and non-fatal errors
through `MediaController.Listener.onError()`.

Error codes are mapped in `LegacyConversions`. Values of error codes
in `@SessionError.ErrorCode` come from `@PlaybackExceptino.ErrorCode`
with the exception of `@SessionError.ERROR_IO` and
`@SessionError.ERROR_UNKNOWN`. These already exist in
`@PlaybackException.ErrorCode` and are mapped accordingly to avoid
semantic duplicates.

PiperOrigin-RevId: 642595517
2024-06-12 06:26:00 -07:00
claincly
f2bdc08b24 Fix minor timestamp handling issue
- Video release should check for buffer timestamp (which is renderer-offsetted), rather than the frame timestamp
- ImageRenderer should report ended after all of it's outputs are released, rather than when finished consuming its input.

Add tests for timestamp handling

PiperOrigin-RevId: 642587290
2024-06-12 05:43:22 -07:00
tonihei
8bd6e5d10a Suppress warning about unused return value
The return value is intentionally unused because the check
is only done to see if the reflection operation succeeds.

PiperOrigin-RevId: 642579373
2024-06-12 05:01:23 -07:00
tonihei
27e6395dbc Make ImageOutput clearable
It's currently not possible to remove a previously set image output
on ExoPlayer, although the underlying renderer already supports
receiving null to clear the output. Marking the parameter as
nullable allows apps to clear it as well.

PiperOrigin-RevId: 642569081
2024-06-12 04:03:32 -07:00
tofunmi
20d56341fc Remove useHdr from overlaySettings
useHdr is unused option and doesn't make sense is the dynamic range of the overlay and video must match

Also reorders and adds javadoc in line with coding conventions

PiperOrigin-RevId: 642555396
2024-06-12 02:52:36 -07:00
kimvde
5a24f40a66 Pass clock to release control from sink provider
In order to do that, make the VideoSink nullable in MCVR.

We want to avoid calling VideoFrameReleaseControl.setClock directly
from MCVR when the sink is enabled. The goal is to handle all the
communication with the release control from the sink/sink provider.

PiperOrigin-RevId: 642542063
2024-06-12 01:51:27 -07:00
sheenachhabra
859ef082d4 Make ExportResult.processedInputs package private
Rational for keeping field package private:
Since the overall export already very complex, by looking at the output file
its hard to know if the desired processing happened or not. Since we now
support sequences with "n" media items, its even more important to know if all
the media items were processed or not.
Although the field exposes implementation details, it seems ok as we get benefit of detailed testing.

PiperOrigin-RevId: 642337888
2024-06-11 11:40:36 -07:00
ibaker
2416ec1cb5 Update @UnstableApi docs with a link to DAC
The code snippets in javadoc don't render correctly due to
https://issuetracker.google.com/342557694

PiperOrigin-RevId: 642309632
2024-06-11 10:18:13 -07:00
ibaker
2456669398 Propagate media3 session extras to media1 PlaybackStateCompat
PiperOrigin-RevId: 642299178
2024-06-11 09:44:22 -07:00
ibaker
b145a96c79 Clean up unecessary zero-arg toBundle() methods
These are no longer needed now that the `Bundleable` interface has been
removed. Public methods are deprecated, package-private ones are
removed. Callers are migrated in both cases (except where tests
explicitly exist for the deprecated method).

PiperOrigin-RevId: 642294451
2024-06-11 09:28:23 -07:00
ibaker
347da7e6a1 Add @CallSuper to TrackSelectionParameters.toBundle
PiperOrigin-RevId: 642292328
2024-06-11 09:19:59 -07:00
ibaker
f54991eea1 Publish the media3 session controller test app
Issue: androidx/media#78
PiperOrigin-RevId: 642277900
2024-06-11 08:27:08 -07:00
kimvde
b763673903 Increase sleep duration when video encoder ends with no output frames
This duration was not sufficient on a Pixel 3a

PiperOrigin-RevId: 642276212
2024-06-11 08:21:09 -07:00
ibaker
f554c12099 Remove Bundleable type & Bundleable.Creator<Foo> CREATOR fields
This interface is not used in the library. Callers can use the
`Bundle toBundle()` and `static Foo fromBundle(Bundle)` methods
defined directly on each type instead.

PiperOrigin-RevId: 642271609
2024-06-11 08:05:32 -07:00
bachinger
efff1ee2f1 Add SessionError and use it in service results
This change adds `SessionError` and uses it in `SessionResult`
and `LibraryResult` to report errors to callers.

Constructors and factory method that used a simple `errorCode` to
construct error variants of `SessionResult` and `LibraryResult`
have been overloaded with a variant that uses a `SessionError`
instead. While these methods and constructors are supposed to be
deprecated, they aren't yet deprecated until the newly added
alternative is stabilized.

PiperOrigin-RevId: 642254336
2024-06-11 06:53:42 -07:00
samrobinson
06e95ad2fb Reduce flakiness of getProgress tests around percentage values.
There is no requirement for the first progress value to be 0, if
progress is made instantly.

PiperOrigin-RevId: 642245457
2024-06-11 06:14:31 -07:00
claincly
fd376bea07 Add stress test for image transform
PiperOrigin-RevId: 642213253
2024-06-11 03:59:32 -07:00
tonihei
acb6a89ff6 Add MediaSession.Callback.onPlayerInteractionFinished
This callback is useful for advanced use cases that care about
which Player calls are batched together. It can be implemented
by triggering this new callback every time a batch of Player
interactions from a controller finished executing.

PiperOrigin-RevId: 642189491
2024-06-11 02:15:20 -07:00
Googler
32d7516237 Add helper function in Track.java to copy track without edit lists.
PiperOrigin-RevId: 642038117
2024-06-10 15:19:29 -07:00
ibaker
24462dd77b Create explicit key for testing 'notification controller'
Previously these tests were setting the test-only `KEY_CONTROLLER`
bundle value to the prod value of
`MediaController.KEY_MEDIA_NOTIFICATION_CONTROLLER_FLAG`, which is a bit
confusing because this is intended to be used as a `Bundle` **key**
(for a boolean value), and not a value itself.

Instead this CL creates a test-only value that can be used by
`RemoteMediaSession` and related test-only friends to indicate that
something (e.g. error or extras) should only be set on the notification
controller.

This CL also changes the logic in `MediaSessionProviderService` to
avoid needing to special-case checking for this controller key.

PiperOrigin-RevId: 641939283
2024-06-10 10:07:52 -07:00
cushon
04ca79182a Fix an invalid javadoc link
PiperOrigin-RevId: 641895590
2024-06-10 07:34:29 -07:00
andrewlewis
a1f21d976c Rename "preset file" to just "preset" in transformer demo
The new name means we can add streams and other sources that aren't files in
future, for example, screen recording input.

PiperOrigin-RevId: 641894319
2024-06-10 07:31:43 -07:00
andrewlewis
34966f5d86 Tidy passing views in transformer demos
PiperOrigin-RevId: 641891515
2024-06-10 07:18:12 -07:00
andrewlewis
cc046d5ce7 Remove most nullness marking from Transformer demos
The nullness checking is very verbose and redundant in some places, for
example, the ensures-non-null marking in the transformer activity, and it makes
changing features in the demo app more time consuming. The cost/benefit balance
seems to be in favor of removing this for demo code.

Note: the ExoPlayer main demo has nullness checks turned off.
PiperOrigin-RevId: 641890618
2024-06-10 07:14:10 -07:00
ibaker
253fcb1fd1 Clarify docs on ExoPlayer.setVideoEffects() re calling prepare()
The previous wording suggested that `setVideoEffects()` may **only** be
called before `prepare()`, i.e. the effect cannot be changed during
playback. The intent is instead that `setVideoEffects()` must be called
once before playback in order to configure the effects pipeline, but
the effect can then be changed during playback by further calls to
`setVideoEffects()`.

Issue: androidx/media#1393
PiperOrigin-RevId: 641853629
2024-06-10 04:12:50 -07:00
kimvde
ec49d19384 Call VideoFrameReleaseControl.setPlaybackSpeed from sink when enabled
Do not call VideoFrameReleaseControl.setPlaybackSpeed directly from
MCVR when the video sink is enabled.

PiperOrigin-RevId: 641840894
2024-06-10 03:15:05 -07:00
dancho
abf601feaa Support upscaling with LanczosResample
Avoid scaling the lanczos windown function when scaling up.
When scaling up (output > input), we shouldn't scale the window
function or we risk not sampling any of the input pixels.

PiperOrigin-RevId: 641838149
2024-06-10 03:01:11 -07:00
tofunmi
228d63848e HDR-only assets sequence effect test: rename golden files
rename to match test name

PiperOrigin-RevId: 641836522
2024-06-10 02:53:34 -07:00
simakova
5e1bc6aa4f Rename "preset file" to "preset" in composition demo.
This change is made for consistency with transformer demo.

PiperOrigin-RevId: 641835714
2024-06-10 02:48:27 -07:00
tofunmi
0d2fdcd025 Add Transformer HDR-only assets sequence effect tests.
PiperOrigin-RevId: 641828107
2024-06-10 02:11:09 -07:00
kimvde
2c71150f2b Set VideoSink listener when enabling MCVR
Before, the listener was set in onReadyToInitializeCodec, which means
that it was reset every time a new codec was used.

We need to set the listener every time MCVR is enabled (not only the
first time), because it might have been set by another renderer.

PiperOrigin-RevId: 641825717
2024-06-10 02:01:00 -07:00
ibaker
82970a6861 Remove incorrect 'bundleable' reference from stringMapToBundle param
This was accidentally copy-pasted in 5008417c8c

PiperOrigin-RevId: 641823991
2024-06-10 01:54:09 -07:00
jbibik
009f7360c5 Remember Player instance on recompositions
PiperOrigin-RevId: 641823733
2024-06-10 01:51:18 -07:00
samrobinson
6bb3af527a Add support for setting and getting volume for composition preview.
PiperOrigin-RevId: 641822822
2024-06-10 01:46:10 -07:00
jbibik
7b1a0376ad Add PlayerSurface Compose component
Underneath, it delegates to either
* `AndroidExternalSurface` (equivalent of SurfaceView), which is generally better for power and latency
* `AndroidEmbeddedExternalSurface` (equivalent of TextureView) which is better for interactions with other widgets or applying visual effects through the graphicsLayer

Note: the resulting surface is stretched across the whole screen. Aspect ratio handling will be addressed in the follow-up changes.
PiperOrigin-RevId: 641285482
2024-06-07 10:15:13 -07:00
claincly
b42b63f3a3 Change externalShaderProgramInputCapacity to int
The field is only accessed on the GL thread.

PiperOrigin-RevId: 641273595
2024-06-07 09:34:45 -07:00
ibaker
b1c6d9ff04 Mark PlayerWrapper as final
This package-private class isn't currently extended, so this change
makes it not possible to be extended in future.

PiperOrigin-RevId: 641270464
2024-06-07 09:23:56 -07:00
andrewlewis
3b6175daa7 Fix test names
PiperOrigin-RevId: 641249128
2024-06-07 07:56:30 -07:00
claincly
ea7cfeccb8 Fix timestamps in tests
38a7229d96 changed only some of the timestamps, in fact all
of the timestamps should have the offset removed.

PiperOrigin-RevId: 641226102
2024-06-07 06:04:31 -07:00
claincly
39e572ad6d Fix a concurrency issue that shader capacity is set off GL thread
Also add test to cover transitions between BT709 and 601.

PiperOrigin-RevId: 641224971
2024-06-07 05:59:20 -07:00
claincly
38a7229d96 Unify timestamp handling
Before this change, the timestamps output from composition playback is offset
with the renderer offset. After this change, the offset is removed and the
timestamp behaviour converges with Transformer, that is, the timestamps of
video/images frames will follow that of the composition. For example, with a
composition of two 10-s items, clipping the first with 2s at the start, the
timestamp of the first frame in the second item, will be 8s.

PiperOrigin-RevId: 641121358
2024-06-06 21:36:15 -07:00
sheenachhabra
ec0af5a7e0 Add CodecDetails to ExportException
This will replace the existing free-form string in the error message

PiperOrigin-RevId: 640954158
2024-06-06 11:01:29 -07:00
tonihei
977fe6aef3 Stabilize offload related error codes
PiperOrigin-RevId: 640839273
2024-06-06 03:34:58 -07:00
tofunmi
cd5a638e43 MuxerWrapper: Fix spelling mistake in method name
PiperOrigin-RevId: 640838741
2024-06-06 03:32:19 -07:00
tonihei
f238db8208 Exit early if buffer becomes invalid
When the frame release control invalidates a buffer and returns that
the buffer must be ignored, we need to exit early before performing
additional checks that may result in method calls using the invalid
buffer.

PiperOrigin-RevId: 640555688
2024-06-05 09:48:30 -07:00
tonihei
9547828468 Add missing null check
PiperOrigin-RevId: 640555113
2024-06-05 09:45:28 -07:00
rohks
438279a3a0 Remove unnecessary throws Exception from HlsChunkSourceTest
PiperOrigin-RevId: 640552488
2024-06-05 09:35:53 -07:00
samrobinson
8a02b44c96 Refactor trim optimization getProgress for improved readability.
This change is a no-op refactor to improve the readability of the
states returned in this method.

PiperOrigin-RevId: 640538374
2024-06-05 08:45:02 -07:00
samrobinson
01b860fdc4 Fix invalid state transitions for trim optimization getProgress.
Ensures valid progress state is returned. Should not return NOT_STARTED
once transformer.start has been called, until export ends.

PiperOrigin-RevId: 640533805
2024-06-05 08:30:42 -07:00
kimvde
f54380f9d8 Remove direct usages of release control when video sink is used
Usages removed in this CL are:
- onProcessedStreamChange, which was already called from the VideoSink
  (via VideoFrameRenderControl)
- setOutputSurface, which was also already called from the VideoSink
- setFrameRate, which this CL now sets in the VideoSink

PiperOrigin-RevId: 640530903
2024-06-05 08:19:17 -07:00
kimvde
9716985272 Move renderer state methods from release control to sink
PiperOrigin-RevId: 640515298
2024-06-05 07:16:36 -07:00
sheenachhabra
f3a9c74de2 Remove @UnknownInitialization DefaultCodec parameter
Using an uninitialised object seems unusual.

PiperOrigin-RevId: 640514501
2024-06-05 07:12:20 -07:00
samrobinson
67c19f87a7 Update FILE_UNKNOWN_DURATION to a longer fmp4 (~15s),
Removes the flakiness of
MediaItemExportTest.getProgress_unknownDuration_returnsConsistentStates
by using a longer input asset, such that ExoPlayer does not determine
the duration of the media.

PiperOrigin-RevId: 640502470
2024-06-05 06:19:11 -07:00
kimvde
d5e9f3b224 MCVR: use shouldUseVideoSink where possible
Before this CL, we were checking whether the video sink was initialized
to determine whether it should be used. In the meantime,
shouldUseVideoSink has been introduced. Use this boolean to check
whether to use the video sink as it's a clearer signal.

PiperOrigin-RevId: 640499147
2024-06-05 06:05:03 -07:00
dancho
9c4a532d5c Add LanczosResample effect to scale videos in Transformer
Add SeparableConvolution.configure(inputSize) to allow effect configuration
depending on input dimensions.
Add LanczosResample.scaleToFit method to scale input images to fit inside
given dimensions.

PiperOrigin-RevId: 640498008
2024-06-05 06:00:25 -07:00
kimvde
3334f0afee Decide whether to use the VideoSink when enabling renderer
This will simplify moving the release control inside the video sink

PiperOrigin-RevId: 640416128
2024-06-04 23:59:10 -07:00
jbibik
f3444aee5f Add icons for fastforward and rewind buttons
PiperOrigin-RevId: 640206040
2024-06-04 10:46:36 -07:00
tianyifeng
6dbf548253 Version bump to media3:1.4.0-alpha02
#minor-release

PiperOrigin-RevId: 640196724
2024-06-04 10:21:36 -07:00
tianyifeng
deb3c96f00 Update release notes for 1.4.0-alpha02
PiperOrigin-RevId: 640138307
2024-06-04 06:56:34 -07:00
dancho
5371ad406b Skip AV1 test on devices that don't support AV1 HDR encoding
Skip AV1 HDR test on some devices.

PiperOrigin-RevId: 640135455
2024-06-04 06:44:23 -07:00
jbibik
35b8ab411d Add isReleased() to the Exoplayer
This avoids having to add AnalyticsListener and catching the `onPlayerReleased` callback.

The `Exoplayer.release()` method is blocking and one can be sure that the player is released if the call returned. However, the method is useful for UI testing and asserting that the player is released after a certain UI action, e.g. closing the activity or detaching a window.

PiperOrigin-RevId: 640114416
2024-06-04 05:11:15 -07:00
dancho
73dd743929 Support Separable Convolutions with negative coefficients
fragment_shader_separable_convolution_es2.glsl had optimizations that assumed
all convolution coefficients are positive. Support negative coefficients,
and add tests.

PiperOrigin-RevId: 640104741
2024-06-04 04:26:26 -07:00
jbibik
d35bc176ff Allow customisation of various icons in PlayerControlView
Before this change:
The only way to customize the icons was to override the drawables, e.g.
* `exo_styled_controls_play`
* `exo_styled_controls_pause`

However, that would set the drawables globally and prevent users from customizing the icons **per** PlayerView.

After the change, it is possible to provide drawable icons in the xml layout directly via `<androidx.media3.ui.PlayerView>` and
* `app:play_icon="@drawable/...`
* `app:pause_icon="@drawable/...`
* `app:vr_icon="@drawable/...`
* `app:fullscreen_exit_icon="@drawable/...`
* `app:next_icon="@drawable/...`

Note:
Two buttons that are left out of this change are fast-forward and rewind. They are more complicated due to layout insertion and customization with seek back/forward increments in the TextView.

Issue: androidx/media#1200
PiperOrigin-RevId: 639832741
2024-06-03 10:32:39 -07:00
ibaker
64890a95da Move CEA-708 release note from 1.3.0 to 'unreleased' (1.4.0)
This was added in the wrong place as part of 0a58832d85

PiperOrigin-RevId: 639783174
2024-06-03 07:59:14 -07:00
tianyifeng
33c689a93d Fix the RELEASENOTES.md
This [commit](d175223cc6) was introduced not long ago (after 1.4.0-alpha01), but has the release note added to the alpha01 release. Moving this piece of note to "unreleased changes" so that it will be included in the 1.4.0-alpha02 release note as a new change.

PiperOrigin-RevId: 639768495
2024-06-03 07:06:49 -07:00
samrobinson
304b784314 Add an analyzer mode option to Transformer demo.
PiperOrigin-RevId: 639746452
2024-06-03 05:33:28 -07:00
tonihei
9ed86441e3 Remove module registration from HttpEngineDataSource
It used to be its own module in the first revision, but then moved
into the DataSource module as of 250fc80419.

PiperOrigin-RevId: 639745498
2024-06-03 05:31:01 -07:00
samrobinson
2c916dc306 Make progress tests stricter.
These changes are possible because getProgress is no longer a blocking
operation on transformer.

* Tests call getProgress after every looper message executed.
* Use longer media assets for getProgress tests to give more progress
  intervals.
* Remove conditional assertions.

PiperOrigin-RevId: 639734368
2024-06-03 04:42:36 -07:00
dancho
2bb12de00d Drop API requirement from SeparableConvolution
Switch from 4-channel RGBA_16F lookup texture to 1-channel R_16F.
Do not use a bitmap when creating the lookup table texture.
Instead, fill the texture directly.
Do not manually convert 32-bit float to 16-bit. Instead, let OpenGL
libraries do this for us.

PiperOrigin-RevId: 639717235
2024-06-03 03:31:41 -07:00
rohks
387153fcf2 Fix CMCD data assignment for init segment
The CMCD data was incorrectly added to the `dataSpec` of the media segment instead of the init segment.

Also relaxed the condition for playbackRate to be C.RATE_UNSET when creating an instance of CmcdData.Factory as there was nothing enforcing this check.

#minor-release

PiperOrigin-RevId: 639046080
2024-05-31 08:42:53 -07:00
simakova
dbeb412355 Move effect final values and preset names and paths to arrays file.
PiperOrigin-RevId: 639034630
2024-05-31 07:59:03 -07:00
tianyifeng
9916428728 Add FOREGROUND_SERVICE_MEDIA_PLAYBACK permission for test session app
Foreground service type `mediaPlayback` requires permission `android.permission.FOREGROUND_SERVICE_MEDIA_PLAYBACK`. The `MockMediaSessionService`, `LocalMockMediaSessionService`, `MockMediaLibraryService`
 and `LocalMockMediaLibraryService` declared in the manifest are in the `mediaPlayback` type.

PiperOrigin-RevId: 639013810
2024-05-31 06:23:17 -07:00
dancho
d3fa33250b Fix a race condition in AudioGraphInput
AudioGraphInput.onMediaItemChanged is called on input thread. Pending
media item changes are processed on processing thread, inside calls to
getOutput().
This change allows multiple pending media item changes to be enqueued,
and processed in sequence.

PiperOrigin-RevId: 638995291
2024-05-31 04:53:13 -07:00
ibaker
4dd8360693 Allow ByteArrayDataSource to resolve the byte array when opened
This is a relatively small change, and massively simplifies the work
needed for an app to consume Kotlin Multiplatform resources (without a
full `KmpResourceDataSource` implementation, which poses some
dependency challenges for now).

Issue: androidx/media#1405
PiperOrigin-RevId: 638991375
2024-05-31 04:33:14 -07:00
michaelkatz
ac34798344 Schedule doSomeWork when MediaCodec signals available buffers
When running in asynchronous mode, MediaCodec will be running the CPU to signal input and output buffers being made available for use by the player. With ExoPlayer.experimentalSetDynamicSchedulingEnabled set to true, ExoPlayer will wakeup to make rendering progress when MediaCodec raises these signals. In this way, ExoPlayer work will align more closely with CPU wake-cycles.

PiperOrigin-RevId: 638962108
2024-05-31 02:22:16 -07:00
ibaker
1329821a35 Use kotlinx-coroutines-guava in session demo app
I originally tried switching to `Futures.addCallback` (as a follow-up
to Issue: androidx/media#890), but it seemed like a good chance to go further into
Kotlin-ification.

Before this change, if the connection to the session failed, the app
would hang at the 'waiting' screen with nothing logged (and the music
keeps playing). This behaviour is maintained with the `try/catch` around
the `.await()` call (with additional logging). Without this, the failed
connection causes the `PlayerActivity` to crash and the music in the
background stops. The `try/catch` is used to flag to developers who
might be using this app as an example that connecting to the session
may fail, and they may want to handle that.

This change also switches `this.controller` to be `lateinit` instead of
nullable.

Issue: androidx/media#890
PiperOrigin-RevId: 638948568
2024-05-31 01:28:47 -07:00
jbibik
a652c5b3f5 Add references in javadocs to relevant listeners for Player fields
PiperOrigin-RevId: 638688864
2024-05-30 10:02:01 -07:00
michaelkatz
43f719fbb2 Schedule exoplayer work to when MediaCodecAudioRenderer can progress
Currently ExoPlayer schedules its main work loop on a 10 ms interval. When renderers cannot make any more progress (ex: hardware buffers are fully written with audio data), ExoPlayer should be able to schedule the next work task further than 10ms out into the future.

Through `experimentalSetDynamicSchedulingEnabled` and these changes to `MediaCodecAudioRenderer`, ExoPlayer can use the data provided by the audio renderer to dynamically schedule its work tasks based on when it is expected that progress can be made.

PiperOrigin-RevId: 638677454
2024-05-30 09:25:11 -07:00
tianyifeng
e879c4ac43 Call PreloadControl.onSourcePrepared only once for each preload request
PiperOrigin-RevId: 638677090
2024-05-30 09:21:59 -07:00
michaelkatz
9e0f533a11 Schedule exoplayer work task to when renderers can make progress
Currently ExoPlayer schedules its main work loop on a 10 ms interval. When renderers cannot make any more progress(ex: hardware buffers are fully written with audio data), ExoPlayer should be able to schedule the next work task further than 10Ms out.

Through `experimentalSetDynamicSchedulingEnabled`, ExoPlayer will dynamically schedule its work tasks based on when renderers are expected to be able to make progress.

PiperOrigin-RevId: 638676318
2024-05-30 09:19:28 -07:00
rohks
8c8bf1334e Use INDEX_UNSET instead of LENGTH_UNSET for next media sequence/part
Both constants have the same value, but the method returning initial values for the media sequence/part uses `INDEX_UNSET`, so it makes sense to use it.

PiperOrigin-RevId: 638673282
2024-05-30 09:10:09 -07:00
sheenachhabra
d598eb064d Remove unnecessary sortKey from Mp4Muxer.addTrack()
PiperOrigin-RevId: 638647112
2024-05-30 07:37:26 -07:00
kimvde
151a2be141 Regenerate TransformerHdrTest goldens after removing degammaing
Degammaing has been removed in cb4b2ea55c. The goldens for
TransformerHdrTest (previously TransformerSequenceEffectTestWithHdr)
were not regenerated because the test wasn't running due to its name
(fixed in e41a966237).

PiperOrigin-RevId: 638645635
2024-05-30 07:32:22 -07:00
michaelkatz
96fae82436 Suppress incorrect linter error in DebugRenderersFactory method
Method should use @RequiresApi annotation instead of @SdkSuppress

PiperOrigin-RevId: 638639225
2024-05-30 07:05:27 -07:00
tianyifeng
1f1897709f Rename PreloadMediaSource.PreloadControl methods
The IntDefs in `DefaultPreloadManager.Stage` are also renamed accordingly.

PiperOrigin-RevId: 638631357
2024-05-30 06:32:33 -07:00
ibaker
4db9bf92af Increase h.264 buffer size in ShadowMediaCodecConfig
Some test media has samples larger than 100kB

PiperOrigin-RevId: 638598553
2024-05-30 03:57:35 -07:00
tofunmi
1640becddd Use file inserts and string replacements in overlay shaders
PiperOrigin-RevId: 638251955
2024-05-29 05:39:35 -07:00
kimvde
e41a966237 Rename test so that it runs on MH
PiperOrigin-RevId: 638237657
2024-05-29 04:35:21 -07:00
michaelkatz
0ed08a5204 Import string translations for session module
#minor-release

PiperOrigin-RevId: 638224207
2024-05-29 03:39:07 -07:00
samrobinson
21eb482baf Add an experimental analyzer mode to Transformer.
PiperOrigin-RevId: 637926059
2024-05-28 09:31:40 -07:00
dancho
3c998ac408 Add a flag to control whether input bitmap resampling can be skipped
Add DefaultVideosFrameProcessor experimental flag that controls
whether input Bitmaps are sampled once for a repeating sequence of
output frames with the same contents, or once for each output frame.

PiperOrigin-RevId: 637921350
2024-05-28 09:15:23 -07:00
dancho
02df88e5d9 Speed up image to video Export
Only sample from input bitmap when the input image has changed.
Introduce GainmapShaderProgram.newImmutableBitmap API that signals
input bitmap changes to GainmapShaderProgram (DefaultShaderProgram).

PiperOrigin-RevId: 637920207
2024-05-28 09:12:24 -07:00
ibaker
3d8b5811b4 Remove deprecated RendererSupport.FormatSupport IntDef & constants
Use `C.FormatSupport` and associated constants instead.

PiperOrigin-RevId: 637890304
2024-05-28 07:21:48 -07:00
ibaker
496bc2b058 Tighten exception handling in TestPlayerRunHelper
This removes `throws Exception` from public methods in favour of more
specific exception types (`TimeoutException` and `PlaybackException`).

PiperOrigin-RevId: 637880546
2024-05-28 06:38:29 -07:00
kimvde
0baa4ff621 Reset input capacity when setting external shader program
Before this CL, externalShaderProgramInputCapacity was not reset when
the external shader program was reset (which occurs when  the
InputSwitcher switches to an input with a different ColorInfo). This is
due to a regression introduced in bef3d518d2.

PiperOrigin-RevId: 637869215
2024-05-28 05:55:00 -07:00
tofunmi
9622411b50 Add support for ultra HDR overlays
PiperOrigin-RevId: 637863706
2024-05-28 05:28:03 -07:00
ibaker
3bb6cf2129 Remove unused Util.getCommaDelimitedSimpleClassNames method
PiperOrigin-RevId: 637854422
2024-05-28 04:43:56 -07:00
ibaker
c87b7d86cc Remove deprecated format changed methods
Use the overloads with an additional `@Nullable DecoderReuseEvaluation`
parameter instead.

PiperOrigin-RevId: 637851937
2024-05-28 04:31:14 -07:00
dancho
aadcbe332b Ensure single-frame videos are correctly exported
Add a wait in DefaultCodec.signalEndOfInputStream when no
video encoder output has been seen. This avoids a thread synchronization problem
between writing frames to video surface, and signaling end of stream,
which was hit for video input of only one frame on some devices.

PiperOrigin-RevId: 637844690
2024-05-28 04:00:01 -07:00
Copybara-Service
67b799c714 Merge pull request #1389 from DolbyLaboratories:dlb/dovi-profile10/dev
PiperOrigin-RevId: 637827802
2024-05-28 02:39:42 -07:00
tofunmi
8feaf82768 UltraHdr: Fix calculations to apply gainmap
PiperOrigin-RevId: 636964921
2024-05-24 10:39:36 -07:00
ibaker
763a5f0272 Remove deprecated DrmSessionManager.DUMMY and getter method
Use `DRM_UNSUPPORTED` constant instead.

PiperOrigin-RevId: 636937592
2024-05-24 09:07:35 -07:00
ibaker
7fd8a06e08 Remove deprecated MediaCodecInfo.isSeamlessAdaptationSupported(...)
Use `MediaCodecInfo.canReuseCodec(...)` instead.

PiperOrigin-RevId: 636918479
2024-05-24 07:59:45 -07:00
ibaker
2ab1c75ca7 Remove deprecated DashMediaSource.DEFAULT_LIVE_PRESENTATION_DELAY_MS
Use `DashMediaSource.DEFAULT_FALLBACK_TARGET_LIVE_OFFSET_MS` instead.

PiperOrigin-RevId: 636906922
2024-05-24 07:11:39 -07:00
ibaker
0f1f6bfa41 Remove deprecated DefaultHttpDataSource constructors
Use `DefaultHttpDataSource.Factory` instead.

PiperOrigin-RevId: 636875524
2024-05-24 05:03:05 -07:00
ibaker
4a16212fb3 Remove deprecated Timeline.Window.isLive field
PiperOrigin-RevId: 636870982
2024-05-24 04:37:04 -07:00
ibaker
08d1eb4376 Remove ShadowLog references from tests
These were accidentally submitted after being added for local debugging.

PiperOrigin-RevId: 636865825
2024-05-24 04:10:27 -07:00
tofunmi
db6144e7dd Maintain a consistent luminance range across HDR content in effects
PQ and HLG have different luminance ranges (max 10k nits and max 1k nits resp). In GL, colors work in a normalised 0 to 1 scale, so for PQ content, 1=10k nits and and for HLG content, 1=1k nits.

This cl scales and normalises PQ content appropriately so that all HDR content works in the HLG luminance range. This fixes two things

1. Conversions between HLG and PQ are "fixed" (before the output colors looked too bright or too dark depending on which way you are converting)
2. color-altering effects will be able to work consistently across HLG and PQ content

1 is tested in this cl. 2 will be tested when ultra HDR overlays are implemented, both cases have been manually tested to ensure the output looks correct on a screen.

PiperOrigin-RevId: 636851701
2024-05-24 03:05:34 -07:00
ibaker
cfd29e04f3 Remove PlayerMessage.setHandler(Handler)
Use `setLooper(Looper)` instead.

PiperOrigin-RevId: 636840566
2024-05-24 02:13:43 -07:00
ibaker
4fb2255eb9 Print underlying extractor name in UnrecognizedInputFormatException
If subtitle-parsing-during-extraction is enabled (now defaults to on),
the 'outer' extractor class name is often
`SubtitleTranscodingExtractor`, leading to some slightly useless error
messages like:

`None of the available extractors (FragmentedMp4Extractor, Mp4Extractor, SubtitleTranscodingExtractor, SubtitleTranscodingExtractor, SubtitleTranscodingExtractor, SubtitleTranscodingExtractor, SubtitleTranscodingExtractor, SubtitleTranscodingExtractor, TsExtractor, MatroskaExtractor, SubtitleTranscodingExtractor, SubtitleTranscodingExtractor, SubtitleTranscodingExtractor, SubtitleTranscodingExtractor, AviExtractor, SubtitleTranscodingExtractor, SubtitleTranscodingExtractor, SubtitleTranscodingExtractor, SubtitleTranscodingExtractor, SubtitleTranscodingExtractor, SubtitleTranscodingExtractor)`

PiperOrigin-RevId: 636834354
2024-05-24 01:44:12 -07:00
Copybara-Service
0a58832d85 Merge pull request #1315 from datdoantelus:ClosedCaption_708Decoder_bugfix
PiperOrigin-RevId: 636591170
2024-05-23 10:18:02 -07:00
ibaker
e150e0d39f Remove OkHttpDataSource constructors & OkHttDataSourceFactory
Use `OkHttpDataSource.Factory` instead.

PiperOrigin-RevId: 636585523
2024-05-23 10:03:12 -07:00
ibaker
4986fdd1a6 Remove deprecated setContentTypePredicate() methods
Use the suggested alternative on the respective
`XXXDataSource.Factory` instead.

PiperOrigin-RevId: 636560182
2024-05-23 08:32:26 -07:00
ibaker
68c16782d7 Migrate buildConfig from properties.gradle to build.gradle
This is generated in response to a deprecation warning in AS:

```
The option setting 'android.defaults.buildfeatures.buildconfig=true' is deprecated.
The current default is 'false'.
It will be removed in version 9.0 of the Android Gradle plugin.
You can resolve this warning in Android Studio via `Refactor` > `Migrate BuildConfig to Gradle Build Files`
```

PiperOrigin-RevId: 636546985
2024-05-23 07:40:46 -07:00
tonihei
7b352e1903 Add more details to thread assertion in onAudioCapabilitiesChanged
This helps to debug issues reported in https://github.com/androidx/media/issues/1191

PiperOrigin-RevId: 636545970
2024-05-23 07:37:04 -07:00
ibaker
f5438c9d55 Remove jetifier config from gradle config
None of the AndroidX libs we depend on require jetification any more.

Issue: androidx/media#1362
PiperOrigin-RevId: 636544337
2024-05-23 07:32:27 -07:00
Ian Baker
e87b820626 Add release note 2024-05-23 15:27:25 +01:00
Ian Baker
3aebb38cd3 Rename and reshuffle tests 2024-05-23 15:27:19 +01:00
datdoantelus
ed5d47e856 Add cea708Decoder test for setPenLocation command and newline handling 2024-05-23 15:22:13 +01:00
datdoantelus
327d26cb32 remove test comment 2024-05-23 15:21:45 +01:00
datdoantelus
ec3065e981 revert rowLock and colomnLock changes since it will be done separately 2024-05-23 15:21:32 +01:00
datdoantelus
3b7ec52ca8 Ignore rowLock and numLock as define in CTA-708 spec.
Update current row value when new line is added.
2024-05-23 15:21:11 +01:00
andrewlewis
174d452bf7 Add missing module registrations
PiperOrigin-RevId: 636506860
2024-05-23 04:50:01 -07:00
samrobinson
414dbebc2b Assert file size in E2E android tests that claim to complete.
Remove redundant test logic to add file size to ExportResult because
the file size is already added to export result as part of an export
finishing.

PiperOrigin-RevId: 636499236
2024-05-23 04:17:19 -07:00
tonihei
08006651fa Update session module registration
PiperOrigin-RevId: 636482934
2024-05-23 03:11:51 -07:00
Googler
37c2d9957e Fragmented Mp4Muxer: add support to B-frame Muxing
Add composition time offset parameter to TRUN box to
support muxing of videos containing B-frames by FragmentedMp4Muxer.
Update TRUN box version from 0 to 1 in order to manage signed
composition time offset.

PiperOrigin-RevId: 636426397
2024-05-22 23:07:35 -07:00
ybai001
205bbef9d6 Add DV profile 10 handling in getAlternativeCodecMimeType() method 2024-05-23 09:42:43 +08:00
ybai001
e060c92068
Merge pull request #9 from androidx/main
Merge latest androidx/media main branch
2024-05-23 09:37:35 +08:00
Copybara-Service
1ffeafecc3 Merge pull request #1384 from trussellswitch:parse-dashif-laurl
PiperOrigin-RevId: 636205459
2024-05-22 10:06:52 -07:00
ibaker
8d515c8cdc MP3: Make a defensive copy of the header in XingFrame constructor
This is currently set from `Mp3Extractor.synchronizedHeader` which
gets overwritten every time we read a new frame. It seems safer to make
this defensive copy (and there will be at most one `XingFrame` instance
per-playback, so this is not prohibitively expensive).

PiperOrigin-RevId: 636181038
2024-05-22 08:48:35 -07:00
dancho
a74076f691 Trigger silence generation when end of stream is encountered
This change avoids a muxer deadlock when:
1. Sequence of items
2. First item has audio track that is shorter than video
3. Audio finishes, and muxer refuses to write more than 500ms of video
   consecutively.

SequenceAssetLoader fails to progress to the second item. A muxer
deadlock is possible when the audio of the first item finishes,
audio end-of-stream is not propagated through AudioGraph, and muxer blocks
video, preventing SequenceAssetLoader to move to the next item in sequence.

By triggering silence generation early as soon as audio EOS is
encountered, we ensure SequenceAssetLoader can progress to the next item.

PiperOrigin-RevId: 636179966
2024-05-22 08:44:28 -07:00
tonihei
9ccc4b27ef Add test and formatting changes 2024-05-22 15:08:52 +01:00
Trevor Russell
521c52fdb9 Parse dashif:Laurl license url in mpd 2024-05-22 15:08:52 +01:00
ibaker
5b3066f380 MP3: Derive duration and bitrate from frame count in Info header
`Info` header is used for CBR files, but in some cases not **every**
frame in these files is the same size. This change stops using the
single frame after the `Info` frame as the 'template' (and assuming all
subsequent frames are the same size/bitrate), and instead derives the
bitrate from fields in the `Info` header. This works for files which are
'almost' constant bitrate, like the one in Issue: androidx/media#1376 where every
frame is either 1044 or 1045 bytes except the one immediately after the
`Info` frame which is 104 bytes (32kbps), resulting in a wildly
incorrect duration calculation.

PiperOrigin-RevId: 636151605
2024-05-22 06:59:10 -07:00
dancho
c2fb2f1520 Work around 1080p export failures on certain devices
Fall back to using software decoder for 1920x1080 for certain
devices.

PiperOrigin-RevId: 636132298
2024-05-22 05:38:50 -07:00
tonihei
fb7cf154de Make getIconResIdForIconConstant public
This allows controller apps to map these constants to suitable
icons without creating a CommandButton instance first.

PiperOrigin-RevId: 636096841
2024-05-22 03:03:03 -07:00
Copybara-Service
d175223cc6 Merge pull request #1339 from colinkho:set-play-when-ready-load-control-branch
PiperOrigin-RevId: 636095759
2024-05-22 02:57:15 -07:00
kimvde
72ba3554a9 Set image duration on all media types
This was previously only set on images because it was not ignored on
other media types. This parameter was made no-op for non-images in
7b2a1b4443.

PiperOrigin-RevId: 636078142
2024-05-22 01:41:50 -07:00
kimvde
9506445148 Remove VideoFrameReleaseControl setter from SinkProvider
Move the parameter to the constructor instead.

PiperOrigin-RevId: 636077477
2024-05-22 01:38:56 -07:00
samrobinson
b6ce35d741 Migrate debug trace logs to track generic events for Muxer.
Track information is added to the details string where relevant.

PiperOrigin-RevId: 635815866
2024-05-21 08:33:12 -07:00
tofunmi
44f2f5056f Add new line between printing glsl source code in error
PiperOrigin-RevId: 635812838
2024-05-21 08:21:56 -07:00
ibaker
8fdf105ab4 Re-apply CEA-608 validDataChannelTimeoutMs assertion
This change was originally made in 379cb3ba54.

It was then accidentally lost in when `Cea608Parser` was merged back
into `Cea608Decoder` in 25498b151b.

This was spotted when re-doing a similar lost change to `Cea708Decoder`,
reported in https://github.com/androidx/media/pull/1315.

See reasoning on e2847b3b80
about why this is the only 'lost' CEA-608 change.

PiperOrigin-RevId: 635803536
2024-05-21 07:45:35 -07:00
ibaker
e2847b3b80 Re-apply CEA-708 rowLock/columnLock fix
This change was originally made in 6f8249184b

It was then accidentally lost in when `Cea708Parser` was merged back
into `Cea708Decoder` in 51b4fa2cc8.

This is the only change made to the actual 'decoding' logic in
`Cea708Parser` between it being split from `Cea708Decoder` and merged
back in again, all the other changes in this period relate to the
implementation of the `SubtitleParser` interface, so don't need to be
preserved in `Cea708Decoder`:
51b4fa2cc8/libraries/extractor/src/main/java/androidx/media3/extractor/text/cea/Cea708Parser.java

`Cea608Parser` was also merged back into `Cea608Decoder` in
25498b151b
and so is vulnerable to the same risk of accidental loss of changes. To
be sure, I also checked the history of this file:
25498b151b/libraries/extractor/src/main/java/androidx/media3/extractor/text/cea/Cea608Parser.java

The only 'decoding logic' change there is 379cb3ba54,
which was also lost in 25498b151b.
I will send a separate change to resolve this.

PiperOrigin-RevId: 635796696
2024-05-21 07:16:04 -07:00
ibaker
17bf47ed24 MP3: Add test CBR sample with 'too small' PCUT frame
This shows ExoPlayer currently wrongly reports the duration of this
sample, because it assumes every frame is 32kbps (104 bytes) due to the
`PCUT` frame immediately after the `Info` frame.

A follow-up change will modify `Info` frame handling to resolve this
issue.

This sample was crafted using a hex editor to insert the additional
`PCUT` frame (the pattern of `null` and `x` is taken from the sample
file in Issue: androidx/media#1376, the header is modified to set the channel count
to 1 to match the rest of the file), and then update the frame count
and data size of the `Info` header to match.

Issue: androidx/media#1376
PiperOrigin-RevId: 635772837
2024-05-21 05:31:44 -07:00
samrobinson
8e4d82b012 Assert file exists before trying to re-decode for test assertions.
PiperOrigin-RevId: 635748820
2024-05-21 03:41:48 -07:00
andrewlewis
2585051294 Move license to top for consistency
PiperOrigin-RevId: 635742699
2024-05-21 03:16:30 -07:00
claincly
e637ccd4aa Fix javadoc formatting
PiperOrigin-RevId: 635737466
2024-05-21 02:53:43 -07:00
dancho
ae240606db Move bitmap coordinate flip out of fragment shader
Fragment shaders in OpenGL ES shader language aren't guaranteed
to support highp, required to correctly represent pixel coordinates
inside large images (e.g. 1920x1080).
This change moves coordinate mirroring for images out of fragment shader.

Fixes http://Issue: androidx/media#1331

PiperOrigin-RevId: 635732208
2024-05-21 02:31:43 -07:00
dancho
b047e81e02 Work around SurfaceTexture implicit scale
If MediaCodec allocates passes an image buffer with a cropped region,
SurfaceTexture.getTransformMatrix will cut off 2 pixels from each dimensions.
The resulting videos will appear a little stretched.

This patch inspects the SurfaceTexture transform matrix, and guesses what the
unscaled transform matrix should be.
Behind experimentalAdjustSurfaceTextureTransformationMatrix flag

PiperOrigin-RevId: 635721267
2024-05-21 01:46:21 -07:00
tofunmi
c409623ca0 Create equals method for gainmaps
Gainmaps don't currently have an equals override, only reference equality is checked by Objects.equals(gainmap1, gainmap2). Create an equals method for gainmaps with the fields we care about to ensure we don't incur false positives in our equality checks.

PiperOrigin-RevId: 635510451
2024-05-20 11:06:03 -07:00
michaelkatz
cefc4dcd77 Add OptIn annotations to declarations in demo app files
#minor-release

PiperOrigin-RevId: 635469477
2024-05-20 08:56:30 -07:00
ibaker
c26042d7ca Fix issue links from google/ExoPlayer to androidx/media
PiperOrigin-RevId: 635469173
2024-05-20 08:53:42 -07:00
samrobinson
c9854cd695 Make flag for debug traces in logcat private and final.
PiperOrigin-RevId: 635465538
2024-05-20 08:38:33 -07:00
samrobinson
07ddc0fca5 Add debug trace for Muxer completely ending.
PiperOrigin-RevId: 635459757
2024-05-20 08:12:57 -07:00
tonihei
c46bb24264 Move parameters inside LoadControl and use it for shouldStartPlayback
+additional formatting and Javadoc changes
2024-05-20 15:53:07 +01:00
Colin Kho
be5cf6b5fd Allow LoadControl.shouldContinueLoading accept playWhenReady as a parameter 2024-05-20 15:48:14 +01:00
claincly
dc4f20ed84 Fix image seeking
Queue image again after position reset, and reset timestamp iterator.

PiperOrigin-RevId: 635049953
2024-05-18 07:41:14 -07:00
tonihei
b645004902 Keep manifest in DashMediaSource after release
This is a fix for the fix in 319854d624. The original fix did
not reset the firstPeriodId to avoid any id clashes with future
updates. This however only works under the assumption that the
next manifest load at the next call to prepare() is exactly the
same as the current manifest. This is not true unless the call
happens very quickly (and may fail even then). Instead we should
keep the existing manifest directly as a reference so we can use
it to find the number of removed periods when we get a new manifest
at the next call to prepare().

Issue: androidx/media#1329
PiperOrigin-RevId: 634853524
2024-05-17 12:24:52 -07:00
tonihei
6abb2db1c6 Refactor pending clock sync logic in DashMediaSource
This should be no-op overall and helps to disentangle the clock sync
update from the state of the manifest.

We currently check oldPeriodCount==0 to trigger the clock sync load,
which only works because the manifest happens to be null whenever
we need a new clock sync. We can decouple these concepts by directly
checking whether we have an existing elapsedRealtimeOffsetMs.

This also requires to set this value explicitly at the point where we
consider it set to the local device clock fallback when the timing
element load fails.

PiperOrigin-RevId: 634844921
2024-05-17 11:55:41 -07:00
tonihei
dd7fb8178a Handle timeline updates where all periods in window have been replaced
This case is most likely to happen when re-preparing a multi-period
live stream after an error. The live timeline can easily move on to
new periods in the meantime, creating this type of update.

The behavior before this change has two bugs:
 - The player resolves the new start position to a subsequent period
   that existed in the old timeline, or ends playback if that cannot
   be found. The more useful behavior is to restart playback in the
   same live item if it still exists.
-  MaskingMediaSource creates a pending MaskingMediaPeriod using the
   old timeline and then attempts to create the real period from the
   updated source. This fails because MediaSource.createPeriod is
   called with a periodUid that does no longer exist at this point.
   We already have logic to not override the start position and need
   to extend this to also not prepare the real source.

Issue: androidx/media#1329
PiperOrigin-RevId: 634833030
2024-05-17 11:16:12 -07:00
ibaker
eca6cb23d8 Clean up unused members in XingFrame
PiperOrigin-RevId: 634817614
2024-05-17 10:26:49 -07:00
dancho
b9ec24a269 Fix AV sync for sequences with audio track shorter than video
For each item, AudioGraphInput now pads the input audio track with silence
to the duration given in onMediaItemChanged.

Possibly resolves Issue: androidx/media#921 .

PiperOrigin-RevId: 634753721
2024-05-17 06:54:39 -07:00
tonihei
34792f7b11 Fix flakiness in ExoPlayerTest
The two affected tests where playing until a specific
position to enable the player to read ahead. The method
pauses at exactly the target position, but then has
temporarily undetermined behavior because the playback
thread uses player.getClock().onThreadBlocked() that lets
the playback thread make progress in parallel to the test
thread. The tests were flaky because they sometimes made
so much progress that they ended playback before we could
query the updated renderer state.

This can be fixed by using
run(player).untilBackgroundThreadCondition instead, which
is guaranteed to be fully deterministic, but may not be able
to stop at exactly the desired position (which we don't
really need anyway for this test).

PiperOrigin-RevId: 634699752
2024-05-17 03:34:04 -07:00
tonihei
2b5bb945e1 Add missing check before calling discardBuffer
The method is only allowed to be called on prepared items.
This check was currently missing and also causing the
corresponding test to be flaky in ExoPlayerTest.

PiperOrigin-RevId: 634694077
2024-05-17 03:09:52 -07:00
ibaker
282a944eb4 Throw errors from WebvttPlaybackTest.stallUntilPlayerCondition
Before this change, if a playback error is thrown the test fails with a
timeout and no additional info:

```
java.util.concurrent.TimeoutException
	at androidx.media3.exoplayer.e2etest.WebvttPlaybackTest.stallPlayerUntilCondition(WebvttPlaybackTest.java:361)
```

After this change, the test failure includes a much more useful stack
trace, e.g. from 0352db9a37:

```
Caused by: java.lang.IllegalStateException: Legacy decoding is disabled, can't handle text/vtt samples (expected application/x-media3-cues).
	at androidx.media3.common.util.Assertions.checkState(Assertions.java:100)
	at androidx.media3.exoplayer.text.TextRenderer.assertLegacyDecodingEnabledIfRequired(TextRenderer.java:587)
	at androidx.media3.exoplayer.text.TextRenderer.onStreamChanged(TextRenderer.java:210)
```

PiperOrigin-RevId: 634672138
2024-05-17 01:33:34 -07:00
samrobinson
d83e81f374 Add toggle for DebugTraceUtil to Transformer demo.
PiperOrigin-RevId: 634495944
2024-05-16 12:41:18 -07:00
samrobinson
1abcf5c22c Add debug trace log for AssetLoader Renderer format events.
PiperOrigin-RevId: 634474584
2024-05-16 11:32:13 -07:00
ibaker
2ac8247cf4 Fix and/or bug in XingSeeker
This was accidentally introduced in 4fde35c9cc

PiperOrigin-RevId: 634465380
2024-05-16 11:06:05 -07:00
tofunmi
25e56474bc Check for .heif extension in File types inference
PiperOrigin-RevId: 634409758
2024-05-16 08:42:14 -07:00
claincly
f0e420e101 Use List in createRenderers for better readability
Also Use `Iterables.toArray()` to void the confusing `List.toArray()` method call

PiperOrigin-RevId: 634351844
2024-05-16 06:04:58 -07:00
kimvde
7b2a1b4443 Fix image not ignored for non-images in setImageDurationMs
PiperOrigin-RevId: 634345071
2024-05-16 05:48:41 -07:00
kimvde
e23cc756e2 Handle playToEndOfStream called before configuring the audio sink
ExoPlayer sometimes calls AudioSink.playToEndOfStream before configuring
the sink. Before this CL, the composition player was failing if this
happened.

PiperOrigin-RevId: 634306592
2024-05-16 04:19:36 -07:00
Copybara-Service
a4faf4db6f Merge pull request #1367 from TheBeastLT:main
PiperOrigin-RevId: 634289663
2024-05-16 03:26:32 -07:00
Ian Baker
743e7942b6 Format with google-java-format and add release note 2024-05-16 10:04:49 +01:00
Simon Hung
d2f677bc4c Update PgsParser.java
Fix "subtitles rendered with border and no fill color" problem:
https://github.com/moneytoo/Player/issues/413

because '0' means it's an index to the palette table, not an RGBA value of 0
2024-05-16 10:02:46 +01:00
ibaker
0352db9a37 Default to parse subtitles while extracting, instead of while rendering
To override this change, and go back to parsing during rendering,
apps must make two method calls:

1. `MediaSource.Factory.experimentalParseSubtitlesDuringExtraction(false)`
2. `TextRenderer.experimentalSetLegacyDecodingEnabled(true)`

PiperOrigin-RevId: 634262798
2024-05-16 01:42:56 -07:00
samrobinson
5c6f48ecaf Add debug trace logs for AudioMixer & AudioGraph events.
PiperOrigin-RevId: 633973723
2024-05-15 09:06:34 -07:00
tofunmi
7b357337d2 Support AVIF in exoplayer
https://developer.android.com/media/platform/supported-formats#image-formats was updated to include AVIF support in API 34+, so <unknown commit> updated our associated Util's to reflect this. After that change, ExoPlayer's BitmapFactoryImageDecoder will be able to decode AVIF, but the player won't be able to detect or extract it. Add this support for completeness, so that ExoPlayer can continue to say it supports all formats in https://developer.android.com/media/platform/supported-formats#image-formats.

PiperOrigin-RevId: 633956245
2024-05-15 08:04:41 -07:00
ibaker
0e5a5e0294 Publish CompositionPlayer for playing compositions
This class is not ready for production app usage yet, so it is still
marked `@RestrictTo(LIBRARY_GROUP)` for now. Apps can experiment with it
in a non-prod context by suppressing the associated lint error.

* Issue: androidx/media#1014
* Issue: androidx/media#1185
* Issue: androidx/media#816

PiperOrigin-RevId: 633921353
2024-05-15 05:55:08 -07:00
tonihei
67554395cb Fix test flakiness
The test currently resets the time too far in the past and then has
to run through ~30000 additional iterations of doSomeWork to reach
the end, sometimes triggering the test timeout.

Fix it by resetting the time to the intended start position when
transitioning items.

PiperOrigin-RevId: 633918706
2024-05-15 05:45:45 -07:00
tianyifeng
e4f0ff8177 Clear the PreloadMediaSource when deprioritized by the preload manager
PiperOrigin-RevId: 633917110
2024-05-15 05:40:58 -07:00
kimvde
a5c94245f8 Add unit test for seeking in clipped MediaItem
PiperOrigin-RevId: 633912487
2024-05-15 05:25:43 -07:00
ibaker
c6f4ed0b66 Remove /* package */ comment from public classes
Also make one class truly package-private and keep the comment instead.

This comment should only appear on elements with default (package-private) visibility.

PiperOrigin-RevId: 633911914
2024-05-15 05:23:30 -07:00
ibaker
ed4820cb61 Remove @UnstableApi from package-private files
This annotation is only needed on public classes.

This change also removes the `/* package */` comment from some `public`
classes.

PiperOrigin-RevId: 633864544
2024-05-15 02:26:55 -07:00
ibaker
8dfcf025d9 Remove @UnstableApi from demo apps
This annotation is only needed on public classes that are part of a
distributed library.

Switch to `@OptIn` for the one file where `@UnstableApi` was
suppressing lint errors.

PiperOrigin-RevId: 633858516
2024-05-15 02:00:13 -07:00
tonihei
d27c36ac9e Use MaskingMediaSource for AdsMediaSource content source
This means the content source is 'prepared' instantly with a
placeholder, enabling all further preparation steps (e.g. loading
preroll ads) while the actual content is still preparing. This
improvement can speed up the start time for prerolls in  manifest-based
content that doesn't have a zero-time preparation step like progressive
media.

Issue: androidx/media#1358
PiperOrigin-RevId: 633640746
2024-05-14 11:02:00 -07:00
bachinger
bf7b4e0d8c Reset platform playback state immediately after sending custom error
This change resets the error in the platform error state immediately
to make sure that the custom error is reflected only very briefly
and then gets back to the playback state that actually reflects the
player state.

Issue: androidx/media#543
PiperOrigin-RevId: 633626180
2024-05-14 10:18:59 -07:00
tofunmi
f7390faeb0 Update supported image formats in line with platform standards
This treats heic as a separate mimetype to heif (even though heic files are a subset of heif files). This is in line with other platform classes like android.content.ContentResolver

https://developer.android.com/media/platform/supported-formats#image-formats was updated to include avif support or API level 34, so added this MimeType as well and updated our associated util.

solves Issue: androidx/media#1373

PiperOrigin-RevId: 633616214
2024-05-14 09:50:38 -07:00
bachinger
84c0b6bcb1 Add MediaSession.sendError to send non-fatal error data to controllers
This allows to set custom error message for instance on Android
Auto/Automotive OS.

Issue: androidx/media#543
PiperOrigin-RevId: 633610089
2024-05-14 09:30:18 -07:00
tonihei
2175c432d7 Add error code for codec reclaim
This allows apps to better detect when the platform
reclaims a codec. This requires adding the error code
to MediaCodecDecoderException.

PiperOrigin-RevId: 633588914
2024-05-14 08:12:51 -07:00
ibaker
4cbe963b86 Tweak session demo UI strings
* Consistently use 'playlist' instead of 'play list'
* Remove wording about 'playlist loading' since when this message is
  shown the music is already playing in the background, we're just
  waiting for the in-app controller to connect to the background
  service.

PiperOrigin-RevId: 633550729
2024-05-14 05:34:00 -07:00
samrobinson
e17b3d7f83 Omit "last: []" from debug trace json if less than 10 event logged.
Reduces the boilerplate from the json produced without any information
loss.

PiperOrigin-RevId: 633540269
2024-05-14 04:45:42 -07:00
Googler
55b9c391e8 Box: Implement ctts box
Add ctts box implementation to handle muxing B-frame videos.
Add method convertPresentationTimestampsToCompositionOffset to
provide sample offsets. Return empty ctts box in case of video
does not contain B-frame. Add ctts box to MoovStructure to handle
muxing the video containing B-frames.

PiperOrigin-RevId: 633537106
2024-05-14 04:32:04 -07:00
ibaker
f73c24a10d Bump Truth dep to 1.4.0 so we can assert directly on Java 8 types
https://truth.dev/faq#java8

Also use this change to remove most test usages of
`Lists.transform(...)` and replace them with `.stream().map(...)`.

PiperOrigin-RevId: 633523904
2024-05-14 03:38:31 -07:00
samrobinson
95c13819af Log DebugTraceUtil events to logcat as they occur.
PiperOrigin-RevId: 633512813
2024-05-14 03:08:43 -07:00
ibaker
b182e469f6 Standardise leak canary version in constants.gradle
PiperOrigin-RevId: 633505366
2024-05-14 02:51:23 -07:00
tonihei
cf1f9b04cf Add more predefined priority values
Also add documentation that suggests to use them in
PriorityTaskManager and adjust codec priorities in
Transformer's DefaultDe/EncoderFactory accordingly.

PiperOrigin-RevId: 633272667
2024-05-13 11:18:41 -07:00
samrobinson
acf1ede644 Add debug trace logs for input/output events for codecs.
PiperOrigin-RevId: 633244952
2024-05-13 10:01:47 -07:00
tonihei
1a5cf6718b Use BaseAudioProcessor format tracking in SilenceSkippingAudioProcessor
The class currently tracks the input format itself, updating it too
early in onConfigure() instead of onFlush(). This causes issues when
the format changes and the new values are applied to the silence
skipping logic of the old format. The fix is to use the base class
input format handling instead.

Issue: androidx/media#1352
PiperOrigin-RevId: 633232368
2024-05-13 09:17:28 -07:00
samrobinson
04ab71a1d4 Remove component names from event strings.
PiperOrigin-RevId: 633212723
2024-05-13 08:06:44 -07:00
tonihei
d52a32aadc Add method to obtain media duration from playout duration
This is the inverse operation of the already existing method.

PiperOrigin-RevId: 633207017
2024-05-13 07:47:14 -07:00
sheenachhabra
3a3145521b Replace Transformer.Muxer interface with Muxer.Muxer
PiperOrigin-RevId: 633193701
2024-05-13 06:54:19 -07:00
sheenachhabra
5950e884f6 Skip TransformerPauseResumeTest on vivo 1820 and vivo 1906
The process crashes unexpectedly on these devices.

The new changes skips running these tests instead of marking them pass, when
the device needs to be skipped.

PiperOrigin-RevId: 633183638
2024-05-13 06:07:20 -07:00
samrobinson
30624aae6e Pass component of event to debug trace logEvent as parameter.
PiperOrigin-RevId: 633176557
2024-05-13 05:33:31 -07:00
tianyifeng
0db23ae904 Add PreloadMediaSource.clear to discard the preloading period
PiperOrigin-RevId: 633167081
2024-05-13 04:47:58 -07:00
sheenachhabra
71e36ac6d2 Remove missing frame workaround from TransformerPauseResumeTest
Two devices were producing B-frames earlier and were causing
frame mismatch. So we had added a workaround for them.
Those devices does not produce B-frames now
after disabling high profile on them, so we don't need workaround now.

PiperOrigin-RevId: 633127755
2024-05-13 01:35:34 -07:00
jbibik
8fa72714db Fail MediaSourceFactory creation if the right module is not added
Due to loading a MediaSourceFactory via reflection:

Before this change
* the content type was logged as an integer, rather than a human-readable string
* `ClassNotFoundException` was swallowed silently by `maybeLoadSupplier` without telling the user what module they were missing

After:
* ClassNotFoundException is swallowed silently ONLY when determining supported types
* ClassNotFoundException is bubbled up when we are trying to play media without the corresponding module properly loaded
PiperOrigin-RevId: 632568989
2024-05-10 12:18:53 -07:00
tonihei
e1d8044ccc Fix flushing logic of SpeedChangingAudioProcessor
When the processor is flushed, it needs to reset its internal state
in preparation for receiving fresh input data.

Flushing the internal SonicAudioProcessor on the other hand should
not go through the parent flush() method and instead flush the
internal processor only when needed.

PiperOrigin-RevId: 632530395
2024-05-10 10:12:03 -07:00
tonihei
daa8750382 Ensure silence skipping doesn't interfere with other discontinuities
The same doSomeWork iteration that triggers the silence skipping
discontinuity may already have another discontinuities (like
AUTO_TRANSITION), which should take precedence over the silence
skipping.

PiperOrigin-RevId: 632432851
2024-05-10 02:51:58 -07:00
tofunmi
1749726bc9 Texture input tests: use separate textures to queue to transformer
Use different textures in calls to queueInputTexture(). Allows the texture to be deleted one it is used in transformer and effect.

PiperOrigin-RevId: 632430866
2024-05-10 02:41:51 -07:00
samrobinson
325f4ec502 Add debug trace JSON nesting per component.
PiperOrigin-RevId: 632424814
2024-05-10 02:13:56 -07:00
samrobinson
fff68f1932 Order DebugTraceUtil JSON output by each component.
PiperOrigin-RevId: 632193924
2024-05-09 10:28:49 -07:00
tofunmi
753f607a81 Test: Remove the invalid dataspace device list when asserting sdr
PiperOrigin-RevId: 632137474
2024-05-09 07:07:51 -07:00
ibaker
861e8218c0 Bump IMA dependency to 3.33.0 to fix NPE with data:// URIs
Issue: androidx/media#700
PiperOrigin-RevId: 632135478
2024-05-09 06:59:53 -07:00
tonihei
971486f5f9 Round bytesToNextSpeedChange up instead of down
Rounding down means that very small diferrences (e.g. 1 us) result
in bytesToNextSpeedChange==0, which stalls progress forever as no
new bytes are read. Rounding up instead ensures that we always read
at least one audio frame if nextSpeedChangeTimeUs is in the future.

PiperOrigin-RevId: 632116560
2024-05-09 05:36:49 -07:00
samrobinson
49fa343127 Remove unused DebugTraceUtil VFP event.
PiperOrigin-RevId: 632109159
2024-05-09 05:00:39 -07:00
tofunmi
e432005653 make TransformerUtil public
help apps statically calculate what transformer will do with certain inputs without running transformer.

PiperOrigin-RevId: 632087821
2024-05-09 03:06:30 -07:00
claincly
145e0faf3d Make DefaultVideoCompositor use the first registered input as primary
PiperOrigin-RevId: 632079022
2024-05-09 02:21:31 -07:00
Googler
524181d7f2 DefaultHttpDS: Allow forcing cross protocol redirects to original
One can set crossProtocolRedirectsForceOriginal to force cross protocol redirects to use the original protocol. This might cause the connection to fail so it can only used when allowCrossProtocolRedirects is set to false or unset (default false).

PiperOrigin-RevId: 631937956
2024-05-08 15:11:04 -07:00
claincly
d977eab5f1 Minor code move for readability
PiperOrigin-RevId: 631922318
2024-05-08 14:19:04 -07:00
samrobinson
8b14d71ff0 Handle null extraFormat on entry in DebugTraceUtil.
PiperOrigin-RevId: 631821753
2024-05-08 09:14:06 -07:00
tofunmi
ad2fc4fbb1 move Output Mime Type And Hdr Mode Fallback logic to TransformerUtil
allows apps to use the logic statically before running transformer.

Also ensure the mime type reported is the mime type outputted

PiperOrigin-RevId: 631811763
2024-05-08 08:40:01 -07:00
tianyifeng
1a5f57e9eb Complete preloading when the period has loaded to the end of the source
When the period has loaded to the end of the source, the `period.getBufferedPositionUs` will be set to `C.TIME_END_OF_SOURCE`, which is a negative value. Thus, the original `continueLoadingPredicate` will never turn to `false`, as the `bufferedPositionUs` is definitely less than the target preload position that is expected to be positive.

In this change, we added `PreloadMediaSource.PreloadControl.onLoadedToTheEndOfSource(PreloadMediaSource)` to indicate that the source has loaded to the end. This allows the `DefaultPreloadManager` and the custom `PreloadMediaSource.PreloadControl` implementations to preload the next source or take other actions.

This bug was not revealed by the the `DefaultPreloadManagerTest` because the related tests were all using the `FakeMediaSource` and only setting the preload target to `STAGE_TIMELINE_REFRESHED`. Thus, the tests for testing the `invalidate()` behaviors were modified to use the real progressive media whenever possible, unless we have to use `FakeMediaSource` to squeeze a chance to do more operations between the preloading of sources to test some special scenarios.

PiperOrigin-RevId: 631776442
2024-05-08 06:16:44 -07:00
tonihei
9ece3932e8 Add time unit to variable names and methods
This helps with readability of the code

PiperOrigin-RevId: 631771454
2024-05-08 05:54:16 -07:00
samrobinson
8b78e04ba3 Add time units to DebugTraceUtil logging.
PiperOrigin-RevId: 631764751
2024-05-08 05:29:04 -07:00
michaelkatz
ab64ca809a Reset tracker for offload track completion prior to stopping AudioTrack
For offloaded playback, reset the tracking field for stream completion in `DefaultAudioSink` prior to calling `AudioTrack.stop()` so that `AudioTrack.StreamEventCallback#onPresentationEnded` correctly identifies when all pending data has been played.

#minor-release

PiperOrigin-RevId: 631744805
2024-05-08 04:02:26 -07:00
kimvde
9adb532b6c Only set image duration on images in demo app
The Javadoc is stating that the image duration is ignored for non-image
input but this is incorrect (for example, it affects seeking
performance). The Javadoc will be updated in another CL.

PiperOrigin-RevId: 631730980
2024-05-08 03:25:04 -07:00
tonihei
38b9a5d441 Always check audio processor chain for media playout duration
When the PlaybackParameters are set to their DEFAULT value, we
currently bypass the audio processor chain when determining the
output media position, under the assumption that no timestamp
change happens in the audio processors. This assumption may not
be true as the audio processors can change playout durations on
their own accord independent of the provided PlaybackParameters.

To correctly reflect any updated playout duration, we can just
always check the audio processor chain. The default implementation
will continue to assume that only the SonicAudioProcessor changes
the playout duration.

PiperOrigin-RevId: 631726112
2024-05-08 03:12:40 -07:00
kimvde
49c75fdd37 Add unit tests for seeking
Other tests will follow

PiperOrigin-RevId: 631711913
2024-05-08 02:39:45 -07:00
Copybara-Service
c5964d197c Merge pull request #1055 from AradiPatrik:z-order-fix
PiperOrigin-RevId: 631616905
2024-05-07 18:45:09 -07:00
Luyuan Chen
766ff44a2c Fix review comment 2024-05-08 00:11:21 +00:00
Luyuan Chen
0403e5881d Format with google-java-format 2024-05-08 00:07:38 +00:00
Patrik Aradi
51a9bcca61 Refactor according to reviews. 2024-05-08 00:07:38 +00:00
Patrik Aradi
52adaf8d26 implement top down approach for passing input source id 2024-05-08 00:07:38 +00:00
Luyuan Chen
3cccecf368 Format with google-java-format 2024-05-08 00:07:38 +00:00
Patrik Aradi
84df55c6e8 fix naming and formatting 2024-05-08 00:07:38 +00:00
Patrik Aradi
b909162daa Use sparse array in MultipleInputVideoGraph, fix formatting 2024-05-08 00:07:37 +00:00
Patrik Aradi
177f1f33d0 Fix indeterminate z-order of EditedMediaItemSequences by passing sequenceIndex when registeringInput 2024-05-08 00:07:37 +00:00
claincly
bef3d518d2 Revise seeking in ExternalTextureManager (ETM)
After this CL, DVFP waits for flushing until all frames registered previously
arrives.

Previously, ETM records the difference between the number of registered frames,
and the number of frames arrivd on the SurfaceTexture, when flushing. (Note
that ETM is flushed the last in the chain, as flushing is done backwards from
FinalShaderProgramWrapper). ETM then waits until the number of frames arrive
after flush.

The normal flow is, MediaCodecVideoRenderer (MCVR) registers a new decoded
frame, in `processOutputBuffer()` to DVFP, MCVR call `codec.releaseOutputBuffer()`
to have MediaCodec render the frame, and then the frame arrives in DVFP's ETM.

However there might be a discrepancy. When registering the frame, ETM records
the frame on the calling thread, ~instantly. Later when the rendered frame
arrive, ETM records a frame is available on the task executor thread (or
commonly known as the GL thread). More specifically, when a frame arrives
in `onFrameAvailableListener`, ETM posts all subsequent processing to
the task executor. When seeking, the task executor is flushed as the first
step. It might be a frame that has already arrived on ETM, and the processing
of such frame has already been queued into the task executor; only to be
flushed as a result of flushing the task executor. If this happens, the frame
is considered to be never have arrived. This causes a freeze on the app,
because ETM'll wait until this frame arrives to declare flushing has completed.

PiperOrigin-RevId: 631524332
2024-05-07 13:15:46 -07:00
tonihei
6ac60c6dff Disable enhanced Java 8 desugaring
This avoids that apps have to depend on this additional config

Issue: androidx/media#1312
PiperOrigin-RevId: 631447767
2024-05-07 09:26:36 -07:00
Copybara-Service
096904301f Merge pull request #1299 from cedricxperi:encoding-dts-uhd-p2-issue
PiperOrigin-RevId: 631405992
2024-05-07 06:47:13 -07:00
samrobinson
9942255894 Allow any pcm encoding raw input pre-effects in AudioGraphInput.
AudioGraphInput now accepts a range of inputs, as long as the effects
provided modify the audio to be int 16.

As part of this, add the workaround to DefaultCodec to ensure pcm
encoding is correct, and remove parameterized tests that are not valid.

PiperOrigin-RevId: 631404152
2024-05-07 06:39:09 -07:00
microkatz
6363017e88 Fix DTS:X Profile 2 encoding attributes for passthrough playback 2024-05-07 12:05:37 +00:00
Cedric T
de2bc944ca Fix ENCODING_DTS_UHD_P2 Issue 2024-05-07 12:05:37 +00:00
tonihei
16df05ec29 Upgrade Gradle and AGP
The newer versions include a bugfix that automatically highlights
when our project requires enhanced Java 8 desugaring.

Issue: androidx/media#1312
PiperOrigin-RevId: 631373018
2024-05-07 04:20:55 -07:00
michaelkatz
75733e294e Fix GitHub ref url typo in 'non-square Dash Thumbnail' release note
PiperOrigin-RevId: 631368681
2024-05-07 04:02:40 -07:00
tofunmi
b2d30a5722 Fallback to hevc transcoding for hdr AV1 files
PiperOrigin-RevId: 631362735
2024-05-07 03:34:31 -07:00
claincly
4aa15e9463 Change test golden files, as default color space chagned
Degamming is removed in cb4b2ea55c, update the test golden files to match
the new working color space.

PiperOrigin-RevId: 631361692
2024-05-07 03:31:32 -07:00
bachinger
4841f8f8b3 Run ExoPlayerTest with preloading enabled and disabled
Replace with parametrized test when  https://issuetracker.google.com/316040980
is resolved.

PiperOrigin-RevId: 631096883
2024-05-06 09:58:09 -07:00
bachinger
0ab6ea5668 Add preload pool to media period MediaPeriodQueue
The pool is created and the queue uses holder instances found
to enqueue. No preloading is done yet though.

PiperOrigin-RevId: 631053172
2024-05-06 08:07:49 -07:00
kimvde
4a54db7cc7 Remove VideoSinkProvider class member from MCVR
PiperOrigin-RevId: 631037709
2024-05-06 07:31:02 -07:00
kimvde
a03f30bea9 Add surface setters on VideoSink
PiperOrigin-RevId: 631025710
2024-05-06 06:31:39 -07:00
kimvde
506944dcfd Move effect setters to VideoSink
PiperOrigin-RevId: 631011252
2024-05-06 05:23:54 -07:00
bachinger
2c912aa697 Handle displayTitle and title in legacy conversions
When converting `MediaMetadata` to the legacy `MediaDescriptionCompat`
the selection and order of properties to use has been aligned with the
behavior of media1. This selection is relevant for users that use a
platform or legacy controller or browser. Before and up to the current
API version 34, this includes System UI, Android Auto/Automotive and
AVRCP (Bluetooth).

PiperOrigin-RevId: 630999535
2024-05-06 04:21:19 -07:00
Googler
1ef0b7c616 Automated Code Change
PiperOrigin-RevId: 630995654
2024-05-06 04:04:20 -07:00
kimvde
6add3a1dba Add release method to VideoSink
PiperOrigin-RevId: 630958612
2024-05-06 01:01:40 -07:00
jbibik
8a8dfbed71 Fix link typo with missing #
Without it, the DAC doesn't render the full sentence. And the link is not actually linking to the proper constructors.

#minor-release

PiperOrigin-RevId: 630395271
2024-05-03 08:22:10 -07:00
sheenachhabra
24305c043e Remove forCancellation flag from Transformer/Muxer.release() method
PiperOrigin-RevId: 630337930
2024-05-03 03:18:24 -07:00
sheenachhabra
10e29be8b6 Allocate correct size for keys and ilst boxes in Mp4Muxer
The keys and ilst boxes in the MP4 muxer were allocated
with a fixed size of 200 bytes. This was not enough to
store the keys and values of large metadata entries, which
could cause the muxer to throw an exception. This CL allocates
the correct size for the keys and ilst boxes based on the size of the metadata entries.

PiperOrigin-RevId: 630331680
2024-05-03 02:47:14 -07:00
tofunmi
620cb32667 effect: use constants for error colors in shaders
PiperOrigin-RevId: 630194321
2024-05-02 15:21:40 -07:00
claincly
d59f1cb6e3 Add test for seeking composition playback
PiperOrigin-RevId: 630184355
2024-05-02 14:46:39 -07:00
tofunmi
cb4b2ea55c remove degammaing: change setSdrWorkingColorSpace default
The second stage of the changes remove the conversion to linear colors in the SDR effects pipeline by default.

also resolves Issue: androidx/media#1050

PiperOrigin-RevId: 630108296
2024-05-02 10:35:48 -07:00
claincly
45ccc6978a Add setVideoSurface override
Also adds first frame rendered test for playing back compositions.
- This test checks the output pixels using an `ImageReader` to retrieve the
output bitmap

PiperOrigin-RevId: 630100817
2024-05-02 10:14:07 -07:00
samrobinson
cb846f0b0d Move raw audio decoder channel count workaround to DefaultCodec.
PiperOrigin-RevId: 630071329
2024-05-02 08:31:28 -07:00
tonihei
7cf2fd9486 Postpone AdTagLoader listener deregistration to receive final error
When the AdTagLoader is deactivated because of a player error, the
error callback is already pending on the app's main thread, but not
yet executed. This means the VideoAdPlayerCallback instances
registered in AdTagLoader won't receive this error event if the
Player.Listener is immediately removed from AdTagLoader.

This can be fixed by postponing the deregistration until after
already pending messages have been handled. As this means other
callbacks can be triggered now with player==null, this check needs
to be added to other callbacks to avoid handling stale events.

Issue: androidx/media#1334
PiperOrigin-RevId: 630068222
2024-05-02 08:19:04 -07:00
kimvde
000d1ff0a6 Always set effects surface and resolution together in MCVR
This change is for simplicity.

PiperOrigin-RevId: 630066664
2024-05-02 08:12:19 -07:00
claincly
2e3c3eb678 Fix wrong output timestamp in seeking
Set `VideoSink`'s offset during seeking in `MCVR.onPositionReset()`

This one is necessary in some cases, where `onProcessedStreamChange()` is not
invoked during a seek. For example, when seeking when playback has ended.

PiperOrigin-RevId: 630056723
2024-05-02 07:29:57 -07:00
kimvde
d059e97b28 Use VideoSink directly in MCVR where possible
PiperOrigin-RevId: 630030889
2024-05-02 05:24:13 -07:00
tonihei
0893275841 Add RendererCapabilities.isFormatSupported helper method
This makes the same method that currently exists as
DefaultTrackSelector.isSupported more widely available
as a utility.

PiperOrigin-RevId: 629991830
2024-05-02 02:06:56 -07:00
kimvde
ec9b38b817 Simplify VideoSinkProvider surface handling in MCVR
PiperOrigin-RevId: 629975032
2024-05-02 00:50:39 -07:00
kimvde
bdb8d8e329 Make VideoSink final in MCVR
This is to be able to set some values on the VideoSink before it's
initialized (for example, the effects)

PiperOrigin-RevId: 629966220
2024-05-02 00:06:39 -07:00
Copybara-Service
d3850722d3 Merge pull request #1300 from hakonschia:fix-dash-thumbnails-cropping
PiperOrigin-RevId: 629774942
2024-05-01 11:08:53 -07:00
microkatz
acc5a3bcd3 Updated non-Square thumbnail unit test to contain non-Square thumbnails 2024-05-01 16:26:58 +00:00
microkatz
690bb1ace3 Add release note for DASH non-square thumbnail grid fix 2024-05-01 16:26:58 +00:00
microkatz
6d62d3437c Format with google-java-format 2024-05-01 16:26:58 +00:00
Håkon Schia
cf41ba3a3d Create new ImageRenderer in render_tiledImageNonSquare_rendersAllImagesToOutput to allow it to use a separate bitmap from the other tests 2024-05-01 16:26:58 +00:00
Håkon Schia
e27f527ed1 Revert changes in ImageRenderTest from 3a030da83b49b9f6c0e414955b543433221d4c41 and create a new unit test for non square images instead 2024-05-01 16:26:58 +00:00
Håkon Schia
9ced27a030 Use inputFormat.tileCountHorizontal to calculate tileStartXCoordinate for cropping the correct tile from outputBitmap
To find the column of an index in a matrix the formula "column = index % width" should be used, not "column = index % height"

If inputFormat.tileCountVertical was equal to 1 then it would not throw an error, but instead result in the first tile of the bitmap always being returned. If inputFormat.tileCountVertical was larger than 1 then Bitmap.createBitmap() would throw an error as it would attempt to go outside the bounds of outputBitmap

ImageRenderTest has been updated to test for 2x3 images so that tileCountVertical != tileCountHorizontal. These tests passed previously because they were equal, so using tileCountVertical produced the same results as tileCountHorizontal
2024-05-01 16:26:57 +00:00
rohks
feb512544a Fix issue with updating the last rebuffer time
The last rebuffer time was being updated erroneously, even in the absence of rebuffering events, resulting in incorrect `bs` (buffer starvation) key in CMCD.

Issue: androidx/media#1124
PiperOrigin-RevId: 629731796
2024-05-01 08:35:02 -07:00
rohks
e25bd07a81 Parse initialization data from AV1 tracks
Initialization data is not passed to `MediaCodecRenderer` as it is not required for playing AV1 video.

See: https://developer.android.com/reference/android/media/MediaCodec#CSD
PiperOrigin-RevId: 629729301
2024-05-01 08:23:43 -07:00
tonihei
1af86d4c4d Fix issue where subtitles starting before a seek position are skipped
These subtitles were skipped because they are marked as shouldBeSkipped
based on their timestamps. The fix removes this flag entirely in
SimpleSubtitleDecoder because TextRenderer handles potential skipping
if needed.

PiperOrigin-RevId: 629717970
2024-05-01 07:34:40 -07:00
tonihei
fb982c2d54 Don't enforce SimpleDecoder skipping for samples before start time
We currently enforce the skipping if the sample has a timestamp less
than the start time. While this may be the default desired behavior
for most implementations, it prevents an implementation from outputting
a sample with such a timestamp.

This change updates the logic to pre-fill the shouldBeSkipped flag
based on the input timestamp, and only check this flag on the output
buffer. None of the implementations in our library change timestamps
of samples, so this is equivalent to the previous code.

PiperOrigin-RevId: 629708873
2024-05-01 06:42:36 -07:00
rohks
5805287620 Remove an extra call to updateRebufferingState method
`updateRebufferingState` is invoked immediately preceding this `if-else`, with no alteration of state occurring in between, making this invocation unnecessary.

PiperOrigin-RevId: 629694531
2024-05-01 05:13:15 -07:00
tonihei
c9aab56d9c Add Mp4 object type for JPEG
PiperOrigin-RevId: 629683068
2024-05-01 04:05:42 -07:00
Copybara-Service
6e8f3a8f97 Merge pull request #1189 from v-novaltd:dsparano-exo245
PiperOrigin-RevId: 629476777
2024-04-30 11:31:53 -07:00
tonihei
703b9368c3 Add ExoPlayer.setPriority
This lets apps update the task manager priority and send the
priority message to all renderers so that they can adjust their
resources if needed.

PiperOrigin-RevId: 629426058
2024-04-30 08:49:16 -07:00
Rohit Singh
a09c2f1701 Add boolean input to MpeghReader 2024-04-30 16:36:51 +01:00
Rohit Singh
247cad934a Update dump files 2024-04-30 16:31:50 +01:00
Rohit Singh
0a436ad491 Use inclusive language 2024-04-30 16:31:50 +01:00
Rohit Singh
1ab91a64c2 Refactor and add release notes 2024-04-30 16:31:50 +01:00
Rohit Singh
e1294c0d5c Format with google-java-format 2024-04-30 16:31:50 +01:00
Daniele Sparano
838083e610 Update dump files 2024-04-30 16:31:50 +01:00
Daniele Sparano
029b8bad86 Fix H264 transformer test, fix H265 byterange case; re-enable file H262 case 2024-04-30 16:31:50 +01:00
Rohit Singh
3cafb08a32 Fix condition to send dummy end of input and update dump files 2024-04-30 16:31:50 +01:00
Rohit Singh
a7f5c3f5b6 Update dump files 2024-04-30 16:31:50 +01:00
Rohit Singh
4b14bc2c3e Format with google-java-format 2024-04-30 16:31:50 +01:00
Daniele Sparano
b82f4b8e28 Tidy up dummy pusi, do not apply to H262 streams 2024-04-30 16:31:50 +01:00
Daniele Sparano
85826ebc19 Fix dummy pusi solution for byte range and key frame only NAL stream cases 2024-04-30 16:31:49 +01:00
Tofunmi Adigun-Hameed
c002ff6a6f Merge pull request #419 from v-novaltd:vnova-104 2024-04-30 16:31:49 +01:00
sheenachhabra
72013446c4 Update error message to be more specific
PiperOrigin-RevId: 629405290
2024-04-30 07:28:35 -07:00
sheenachhabra
6956d8099a Rename Muxer.addMetadata to addMetadataEntry
This is to make it clear that the method adds a single metadata entry, not a collection of metadata entries.

PiperOrigin-RevId: 629398485
2024-04-30 06:55:50 -07:00
sheenachhabra
bc77cef403 Rollback of 08abc964ab
PiperOrigin-RevId: 629382753
2024-04-30 05:41:45 -07:00
tofunmi
28655d27a7 test: use Ascii.equalsIgnoreCase for device model matching
PiperOrigin-RevId: 629349367
2024-04-30 02:54:38 -07:00
Rohit Kumar Singh
43f098da0f Merge Issue: androidx/media#882: Extend MPEG2TS implementation with MPEG-H support
Imported from GitHub PR https://github.com/androidx/media/pull/882

Merge 27a4c43de6294a5482b85ff8e2b4501057f3e946 into a49b625cc5

COPYBARA_INTEGRATE_REVIEW=https://github.com/androidx/media/pull/882 from androidx:ts_mpegh_reader_patch 27a4c43de6294a5482b85ff8e2b4501057f3e946
PiperOrigin-RevId: 629132035
2024-04-29 11:33:38 -07:00
ibaker
96bc9e9652 Propagate ID3 TCON frame to MediaMetada.genre
This change also includes mapping the numeric ID3v1 codes to their
string equivalents before setting them into `MediaMetadata`. This
mapping already existed, but it was previously only used when parsing
MP4 `gnre` atoms.

Issue: androidx/media#1305
PiperOrigin-RevId: 629113480
2024-04-29 10:38:51 -07:00
rohks
c6492e01e4 Remove redundant final in PesReader methods
Since the class is final, declaring the overridden methods as final is unnecessary.

PiperOrigin-RevId: 629103982
2024-04-29 10:12:05 -07:00
tonihei
74bb4ac98d Fix lint errors in shortform demo app
PiperOrigin-RevId: 629080780
2024-04-29 08:50:06 -07:00
tonihei
a49b625cc5 Add renderer message to update priority
This can be used to set the new codec importance values.

PiperOrigin-RevId: 629073176
2024-04-29 08:17:37 -07:00
tonihei
344fc8a8c0 Add IntDef for priority values
This makes it easier to reference these values in documentation
and method parameters.

PiperOrigin-RevId: 629072314
2024-04-29 08:14:20 -07:00
tianyifeng
e180e263a5 Refresh HlsMediaPlaylist with delivery directives when possible
When refreshing the media playlist, we should try to request via a url with [delivery directives](https://datatracker.ietf.org/doc/html/draft-pantos-hls-rfc8216bis#section-6.2.5). However, when initially loading the media playlist or when the last loading with delivery directives encountered an error, we should not allow using those directives.

PiperOrigin-RevId: 629060177
2024-04-29 07:24:35 -07:00
ibaker
b0e48175f0 Add ID3 TCON genre to MP3 test samples
This change adds a 'free-form' text genre to the existing
`bear-id3.mp3` sample, and adds a new sample with a 'numeric' genre ([9
is Metal](https://mutagen-specs.readthedocs.io/en/latest/id3/id3v2.4.0-frames.html#appendix-a-genre-list-from-id3v1)).

The samples were modified with:

```shell
$ id3edit --set-genre "Gorpcore" bear-id3.mp3
$ id3edit --set-genre "9" bear-id3-numeric-genre.mp3
```

Reading the numeric genre with `exiftool` shows the mapping back to
'Metal':

```
$ exiftool bear-id3-numeric-genre.mp3 | grep Genre
Genre                           : Metal
```

The playback dumps don't contain the genre because it's not yet
propagated to `MediaMetadata.genre`. That is done in a follow-up
change.

Issue: androidx/media#1305
PiperOrigin-RevId: 629043506
2024-04-29 06:03:39 -07:00
bachinger
d292f80926 Remove MSG_DO_SOME_WORK when requesting playlist update
This removes a window of inconsistency between the timeline
known to the player and the most recent timeline in the
`MediaSourceList` by removing the `MSG_DO_SOME_WORK` when
sending `MSG_PLAYLIST_UPDATE_REQUESTED`. `MSG_DO_SOME_WORK`
is then sent again when the playlist update is requested.

PiperOrigin-RevId: 629021752
2024-04-29 04:06:13 -07:00
tofunmi
7089253bef Effect:migrate setEnableColorTransfers to setSdrWorkingColorSpace
Part of a two stage change to remove the conversion to linear colors in the SDR effects pipeline by default. Changes the boolean to an intdef, introducing a third option that gets all sdr input into the same colorspace.

This is a planned API breaking change, but this change should not change the behavior of the pipeline.

PiperOrigin-RevId: 629013747
2024-04-29 03:26:58 -07:00
claincly
43de3b67cf Fix PassthroughShaderProgram flush
PiperOrigin-RevId: 629007018
2024-04-29 02:51:27 -07:00
ibaker
854e8aad32 Add Dumper.addIfNonDefault methods
Remove the duplicate implementations in `PlaybackOutput` and
`DumpableFormat`.

PiperOrigin-RevId: 628419737
2024-04-26 09:00:44 -07:00
ibaker
e759b44c45 Remove @Nullable from Dumper.add methods
`checkNotNull` was added to the `Object` variant in b83f12c4ba. It
doesn't seem to have caused any test failures, so I guess we never
pass `null` in here - and might as well update the annotation to match
reality. And then for consistency we should ban `null` from the
`byte[]` overload too.

PiperOrigin-RevId: 628419003
2024-04-26 08:56:56 -07:00
bachinger
38813dd30e Migrate DefaultAnalyticsCollectorTest to use the playlist API
Some test cases are still using `ConcatenatingMediaSource`
even if they do not test specific features of the concatenating
source. Apparently these test have a slightly different timing
behavior when it comes to updating the `MediaPeriodQueue` and
emitting change events with analytics.

Using the playlist API ensures testing the future-proof code path.

PiperOrigin-RevId: 628413460
2024-04-26 08:35:58 -07:00
claincly
4be30bb308 Support seeking when playing back a composition
PiperOrigin-RevId: 628382976
2024-04-26 06:06:23 -07:00
ibaker
5666678d8a Use Dumper.addTime in more places
This ensures that `C.TIME_UNSET` is more clear in dump files. Some of
these call-sites will **never** pass `C.TIME_UNSET`, but it seems
clearest to always use `addTime` and maybe it will ensure when these
sites are copied in future, `addTime` will be used in the new location
too.

PiperOrigin-RevId: 628363183
2024-04-26 04:20:56 -07:00
ibaker
e194225b32 Fix parsing some MP4 metadata fields we wrongly assumed were 1 byte
This fixes parsing the `gnre` and `tmpo` values, as seen in the test
dump changes in this CL.

Issue: androidx/media#1305
PiperOrigin-RevId: 628352773
2024-04-26 03:30:14 -07:00
Googler
08abc964ab Box: Implement ctts box
Add ctts box implementation to handle muxing B-frame videos.
Add method convertPresentationTimestampsToCompositionOffset to
provide sample offsets. Return empty ctts box in case of video
does not contain B-frame. Add ctts box to MoovStructure to handle
muxing the video containing B-frames.

PiperOrigin-RevId: 628346257
2024-04-26 02:57:53 -07:00
ibaker
d76ee54ca6 Add two MP4 samples with metadata
The first has a string genre, and various other values set, generated
from `sample.mp4` with the command below [1].

The second has a numeric genre, to test `gnre` atom parsing. This
parsing is currently broken, the fix is in a follow-up change. This
file was also generated from `sample.mp4` with the command below [2].

This change also includes `CommentFrame.text` in its `toString`
representation, otherwise there's no difference between e.g. different
levels of `ITUNESADVISORY` in the extractor dump files.

Issue: androidx/media#1305

-----

[1]

```shell
$ AP_PADDING="DEFAULT_PAD=0" \
    AtomicParsley sample.mp4 \
    --artist "Test Artist" \
    --album "Test Album" \
    --tracknum 2/12 \
    --disk 2/3 \
    --year 2024  \
    --genre "Gorpcore" \
    --bpm 120 \
    --compilation true \
    --advisory clean \
    --gapless true \
    --sortOrder artist "Sorting Artist" \
    --sortOrder album "Sorting Album" \
    --preventOptimizing \
    -o sample_with_metadata.mp4
```

[2]
```shell
$ AP_PADDING="DEFAULT_PAD=0" \
    AtomicParsley sample.mp4 \
    --genre "Metal" \
    --preventOptimizing \
    -o sample_with_numeric_genre.mp4
```

PiperOrigin-RevId: 628345458
2024-04-26 02:53:33 -07:00
ibaker
acb3a54dee Add MediaMetadata to playback test dump files
This change also adds some runtime redirection of calls to
`Dumper.add(String, Object)` to `add(String, byte[])` if
`value instanceof byte[]`. This simplifies the implementation of
`PlaybackOutput.dumpIfNotEqual` and seems like a reasonable amound of
'magic' for a test utility.

Issue: androidx/media#1305
PiperOrigin-RevId: 628119473
2024-04-25 10:35:18 -07:00
tofunmi
5ee6c9b16d ultraHdr test: add checks for devices with invalid color formats
PiperOrigin-RevId: 628101730
2024-04-25 09:37:16 -07:00
kimvde
bf266c96a9 Set stream offset on video sink
PiperOrigin-RevId: 628084729
2024-04-25 08:32:23 -07:00
kimvde
a6eef7b8d8 Set clock on VideoSink
PiperOrigin-RevId: 628083794
2024-04-25 08:28:14 -07:00
kimvde
c87940eb27 AudioGraph refactoring: configure mixer and add sources in one place
PiperOrigin-RevId: 628076773
2024-04-25 08:02:00 -07:00
tonihei
13a3aa7e77 Add TestPlayerRunHelper run(player).untilBackgroundThreadCondition(..)
This method is useful for cases where the target condition can
become true outside of a message on the main thread. To ensure we
don't execute the rest of the test method in parallel with other
code, we have to introduce artifical messages on the main thread
that check the target condition.

PiperOrigin-RevId: 628072444
2024-04-25 07:43:19 -07:00
kimvde
00ce572a4f Always reconfigure video sink for video after image
Before this CL, the video sink was not reconfigured for the second video
in a sequence with video-image-video. For example, the stream offset
and listener were not set for the second video.

PiperOrigin-RevId: 628065991
2024-04-25 07:19:07 -07:00
bachinger
0e3b05c67d Add metadata field durationMs
PiperOrigin-RevId: 628038241
2024-04-25 05:05:42 -07:00
tonihei
ed1cf35f30 Extend async crypto flag to audio
This is only supported from API 35

PiperOrigin-RevId: 628014091
2024-04-25 03:07:44 -07:00
tonihei
d0d6ce52a5 Import androidx.media
This imports all the classes and resources needed by our code.

We still have the nominal dependency on the artifact as we need
to access the Parcelable CREATORs of MediaSessionCompat.Token,
MediaDescriptionCompat, RatingCompat and MediaBrowserCompat.MediaItem.

Mechanical import steps:
 - Put all files under a new 'legacy' package and change all import
   statements accordingly.
 - Reformat to adhere to Media3 java style guide
 - Remove all existing @RestrictTo annotations and replace them with
   top-level @RestrictTo(LIBRARY) on all classes in the new package.
 - Remove @NonNull annotations and fixed nullability test errors
 - Fix HTML javadoc build errors
 - Fix Lint errors (but not warnings)

The code still contains many lint warnings that will be fixed
separately.

PiperOrigin-RevId: 627999285
2024-04-25 01:56:23 -07:00
tonihei
43d1fa933c Remove flakiness from MCCPlaybackStateCompatActionsWithMediaSessionTest
The tests were reigstering a listener to wait for the first event, but
this first even may have happened already by the time the listener is
registered. Instead we can wait until the controller is connected and
assume that the initial state already arrived.

PiperOrigin-RevId: 627683245
2024-04-24 04:27:44 -07:00
tonihei
f9ea4f0444 Fix error-prone warning comparing CharSequence with String
PiperOrigin-RevId: 627679923
2024-04-24 04:11:56 -07:00
kimvde
579386ff27 Set VideoFrameMetadataListener on VideoSink
PiperOrigin-RevId: 627652670
2024-04-24 02:04:23 -07:00
ibaker
3322092070 Fix MP4 ID3 sort tag mapping
The ID3 tags are documented here:
https://wiki.hydrogenaud.io/index.php?title=Foobar2000:ID3_Tag_Mapping

The MP4 fourcc types are documented here:
https://mutagen.readthedocs.io/en/latest/api/mp4.html#mutagen.mp4.MP4Tags

From the field definitions at the top of this file:

* `TYPE_SORT_ALBUM = 0x736f616c = 'soal'`
* `TYPE_SORT_ARTIST = 0x736f6172 = 'soar'`
* `TYPE_SORT_ALBUM_ARTIST = 0x736f6161 = 'soaa'`

Issue: androidx/media#1302

#minor-release

PiperOrigin-RevId: 627486902
2024-04-23 13:29:40 -07:00
claincly
124c70ac26 Add MIME type to match any image
PiperOrigin-RevId: 627486539
2024-04-23 13:27:42 -07:00
rohks
8ff9e4a838 Add test for H.264 I-frames only track in TsExtractorTest
Sample is created by re-encoding the existing H.264 sample with `ffmpeg`.

PiperOrigin-RevId: 627470063
2024-04-23 12:30:11 -07:00
kimvde
abd0ff7352 Remove configure methods
Pass the parameters to the constructor instead

PiperOrigin-RevId: 627420999
2024-04-23 09:59:56 -07:00
tonihei
bf9f8a3719 Treat playback after stop as a new playback
This implies we should report it as STATE_JOINING_FOREGROUND
instead of STATE_BUFFERING.

PiperOrigin-RevId: 627406584
2024-04-23 09:09:15 -07:00
tofunmi
73f614b14d Effect: support disabling color transfers when HDR->SDR tonemapping
also makes the setter more flexible by ignoring the value of the setter when the output is hdr rather than throwing (since all HDR content must be have a linear color space)

PiperOrigin-RevId: 627388436
2024-04-23 08:02:30 -07:00
Googler
f2276f613d Fix SocketTimeoutException in CronetDataSource.
In some versions of Cronet, the request provided by the callback is not always the same. This leads to callback not completing and request timing out.

The fix changes from having one `UrlRequestCallback` per `CronetDataSource` to one `UrlRequestCallback` per `UrlRequest`. Everytime a current request is canceled, the current callback is closed.

PiperOrigin-RevId: 627379153
2024-04-23 07:21:20 -07:00
sheenachhabra
b813bd3976 Use silence audio in RawAssetLoader tests
This is avoid dependency on `MediaExtractor` whose
behaviour is not consistent across different API versions.

PiperOrigin-RevId: 627330485
2024-04-23 03:38:31 -07:00
bachinger
4091303c7e Read device volume directly from binder with legacy session
PiperOrigin-RevId: 627328652
2024-04-23 03:31:33 -07:00
bachinger
e866cb02d6 Make replaceAdTagParameters unstable API for now
PiperOrigin-RevId: 627323264
2024-04-23 03:04:51 -07:00
kimvde
8da6938782 Always initialize VideoSink in renderer
Instead of initializing the video sink outside the renderer with an
empty format for composition preview, we initialize it in the renderer
with the input format for video.

PiperOrigin-RevId: 627313708
2024-04-23 02:20:18 -07:00
kimvde
e3caed1441 Move VideoSinkProvider.initialize to VideoSink
PiperOrigin-RevId: 627290721
2024-04-23 00:37:01 -07:00
Googler
a43ffa8898 Add replaceAdTagParameters() to ImaServerSideAdInsertion.AdsLoader.
PiperOrigin-RevId: 627114711
2024-04-22 12:09:59 -07:00
claincly
7aed9d40a0 Clean up nullness annotation
PiperOrigin-RevId: 627114088
2024-04-22 12:07:07 -07:00
Googler
430fafded6 Boxes: Update STTS duration calculation.
Update the function convertPresentationTimestampsToDurationsVu
to return a list of duration in decoding order,used in the
creation of STTS boxes.

PiperOrigin-RevId: 627052898
2024-04-22 08:59:06 -07:00
sheenachhabra
03a041c452 Pass BufferInfo in writeSampleData() method in Transformer/Muxer.java
This is to eventually replace Transformer/Muxer.java with Muxer/Muxer.java

PiperOrigin-RevId: 627043808
2024-04-22 08:23:34 -07:00
sheenachhabra
86ef571644 Replace trackIndex with TrackToken in Transformer
This is to eventually replace Transformer/Muxer.java with Muxer/Muxer.java

PiperOrigin-RevId: 627027254
2024-04-22 07:20:38 -07:00
sheenachhabra
7c7e7ea629 Add API to disable sample copy in Mp4Muxer
PiperOrigin-RevId: 627002635
2024-04-22 05:26:39 -07:00
tofunmi
8ae9e81196 add test for speed adjustments, audio removed and a forced audio track
add coverage for key use case for speed adjustments

PiperOrigin-RevId: 626957912
2024-04-22 02:00:46 -07:00
claincly
716aedd019 Fix image up-side-down in when playing a Composition
When playing a Composition, the color transfer of an image is incorrectly
passed down to be SMPTE170M, but it should be SRGB.

PiperOrigin-RevId: 626425396
2024-04-19 11:37:15 -07:00
tofunmi
fb037b9847 TimestampWrapper: fix signaling input capacity
fixes https://github.com/androidx/media/issues/821

PiperOrigin-RevId: 626407880
2024-04-19 10:40:59 -07:00
tofunmi
0bc5ac24b0 Effect: remove duplicate inputColorInfo checks
We currently check certain properties about inputColorInfo twice: once in checkColors in the DVFP and once when creating the samplers in the defaultshaderprogam. The inputcolorinfo shouldn't change between these two components so removing the checks in the shader program to have one source of truth for inputColorInfo checks, which will make the code simpler when it comes to adding to color-related features (like the ones related to removing de-gamma-ing)

PiperOrigin-RevId: 626400960
2024-04-19 10:18:33 -07:00
bachinger
09f2cda43c Promote IMA DAI API to stable
PiperOrigin-RevId: 626064956
2024-04-18 09:49:48 -07:00
tofunmi
300e83414d Effect: Change link in shader ahead of deletion
PiperOrigin-RevId: 626044561
2024-04-18 08:38:41 -07:00
tianyifeng
50fefe698d Avoid non-primary playlists continuously reloading for LL-HLS streams
For LL-HLS, the non-primary playlists originally keep reloading even after the primary playlist has been changed to another one. The reason being this is to check if the hinted(#EXT-X-PRELOAD-HINT) resource has been published or removed. If removed, the loading of it should be canceled, per the suggestion in the HLS spec:

"A Client SHOULD cancel a request for a hinted resource if it is not present in a subsequent Playlist update, such as in an EXT-X-PRELOAD-HINT tag or as part of another tag such as EXT-X-PART.  The client SHOULD ignore the results of such requests."

However, keeping the non-primary playlists reloading is not optimal. As a solution, we trigger the playlist reloading only when there is a preload chunk loading instead of every time after we have processed the playlist. Compared to the original implementation, this will save the requests of reloading non-primary playlist after we have taken action upon the preload chunk being published or removed.

Issue: androidx/media#1240
PiperOrigin-RevId: 626038032
2024-04-18 08:11:19 -07:00
tonihei
e1c62df256 Remove media1 public API dependencies from session module
This is the preparation to import the media1 classes as
private copies into media3.

- Reword Javadoc to use @code instead of @link to media1 types. This
  avoids accidentally linking to the future internal types.
- Use fully qualified names for the converter methods to and from
  MediaSessionCompat.Token to ensure they keep the publicly available
  type.
- Add new public variable that is directly referenced from our code
  instead of referring the the media1 equivalent.
- Clean up tests that are using media1 types to make assertions on
  media3 fields and vice versa (mostly when using LegacyConversions
  in the test method). This also makes the tests more DAMP than DRY.
  (also moved LegacyConversionsTest to a unit test as it doesn't test
  cross-process communication)

PiperOrigin-RevId: 626000082
2024-04-18 05:33:10 -07:00
kimvde
34c31b0a33 Fix SequenceAssetLoader incorrectly reporting MediaItem change
Before this CL, if all the video (resp. audio) samples were fed before
the audio (resp. video) output format was reported, the
SequenceAssetLoader was incorrectly reporting a MediaItem change with a
null format.

PiperOrigin-RevId: 625978268
2024-04-18 03:44:18 -07:00
sheenachhabra
4aa2fb883f Add RawAssetLoader and deprecate TextureAssetLoader
All the changes are based on existing implementations
and their related tests.

No new functionality is being added.

PiperOrigin-RevId: 625756836
2024-04-17 11:48:43 -07:00
andrewlewis
2f8ce053b9 Avoid crash when testing spatialization of high channel count audio
For audio with more than 12 channels, no channel mask was determined, which
meant that the code to check spatializability would throw because of creating
an invalid audio format.

Return early if the channel mask was invalid instead (and assume spatialization
isn't possible).

PiperOrigin-RevId: 625618683
2024-04-17 03:03:01 -07:00
andrewlewis
a58a99e84d Don't constrain audio for playout in Transformer
Transformer's input shouldn't be constrained to the number of playable audio channels on the current device because the media may be edited (to mix channels for example) or encoded for playback on another device (a server for example).

PiperOrigin-RevId: 625604243
2024-04-17 01:55:51 -07:00
michaelkatz
83d1600c7e Fix typos in 1.4.0-alpha01 release notes
PiperOrigin-RevId: 625332081
2024-04-16 08:03:17 -07:00
andrewlewis
3be49a5841 Work around incorrect channel count for raw audio
The raw audio decoder's output audio format is stereo when the number of input
channels is (for example) 10 channels. Add a temporary workaround that uses the
input channel count for raw audio. This code should be removed in future when
we bypass the decoder entirely for raw audio.

Tested manually on a WAVE file with 18 audio channels.

PiperOrigin-RevId: 625307624
2024-04-16 06:21:31 -07:00
Copybara-Service
ea48fe579e Merge pull request #1272 from stevemayhew:p-add-hook-for-load-error-handler
PiperOrigin-RevId: 625285300
2024-04-16 04:48:27 -07:00
sheenachhabra
794900bfb8 Update addMetadata method in Transformer/Muxer.java
This is to align the interface with Muxer/Muxer.java and
then finally replace it.

PiperOrigin-RevId: 625283725
2024-04-16 04:40:13 -07:00
Ian Baker
e13d7e632e Fix javadoc link reference 2024-04-16 11:49:06 +01:00
Ian Baker
5fd1dc2e4e Add release note 2024-04-16 11:44:07 +01:00
Ian Baker
001ebb68f3 Formatting, nullness and javadoc rewording 2024-04-16 11:42:31 +01:00
Steve Mayhew
566c0b3eea Allows setting LoadErrorHandlingPolicy for DRM
The `DefaultDrmSessionManager` allows setting this policy.  This change
simply plumbs the setting up to the `DefaultDrmSessionManagerProvider`
2024-04-16 11:42:31 +01:00
Copybara-Service
236c341168 Merge pull request #1266 from hubert-mazur:looped_playback
PiperOrigin-RevId: 625260110
2024-04-16 02:54:47 -07:00
ibaker
c01babe9bb Log JSON loading exception in demo app
This change also switches from media3's `Log` class (marked with
`@UnstableApi`) to `android.util.Log` which is what we would expect
apps to use.

Issue: androidx/media#1283
PiperOrigin-RevId: 625252745
2024-04-16 02:24:17 -07:00
Marc Baechinger
a6b540545d Minor cleanup 2024-04-16 10:54:45 +02:00
kimvde
1c0345e69f Make VideoSinkImpl non-static
PiperOrigin-RevId: 624999257
2024-04-15 10:13:25 -07:00
kimvde
41d5571660 Allow sink provider to be flushed before initialized
VideoSink.initialize will be added in a next CL and we want to allow
flush to be called before and after initialize.

PiperOrigin-RevId: 624946957
2024-04-15 07:05:28 -07:00
kimvde
00e3753d62 Fix buffer lost when flushing AudioGraphInput
Before this CL, currentInputBufferBeingOutput was set to null without
adding the buffer to the queue of available buffers, which was making
this buffer unusable. After multiple seeks, playback was stuck because
the AudioGraphInput had no input buffer left.

PiperOrigin-RevId: 624943271
2024-04-15 06:50:13 -07:00
kimvde
0a741cad36 Allow sink provider speed to be set at any time
VideoSink.initialize will be added in a next CL and we want to allow
setPlaybackSpeed to be called at any time.

PiperOrigin-RevId: 624942845
2024-04-15 06:47:33 -07:00
kimvde
42335893da Remove unnecessary call in MediaCodecVideoRenderer
Before this CL, the FrameMetadataListener was set in
onReadyToInitializeCodec while it had already been set when handling
message MSG_SET_VIDEO_FRAME_METADATA_LISTENER.

PiperOrigin-RevId: 624940824
2024-04-15 06:38:05 -07:00
ibaker
a701c2f035 Tighten clearkey "default.url" workaround
This ensures it only applies to known-problematic versions of the
clearkey plugin.

PiperOrigin-RevId: 624901919
2024-04-15 03:42:57 -07:00
tonihei
11257ecacb Forward presumed no-op seeks to handler methods in (Simple)BasePlayer
Some seek operations are currently filtered in the base classes if
the target index is not explicitly specified and the implicitly
assumed operation doesn't have an obvious target index. (Example:
calling seekToNext() at the last item in a playlist)

This is too opinionated because the actual player implementation
using this base class may be able to handle this seek request (e.g.
by adding new items on the fly or using other logic to select
the most suitable next item).

This can be solved by forwarding all seek requests to the respective
handler methods even if they are a presumed no-op. Also clarify the
Javadoc that the provided index is just an assumption if it wasn't
provided explicitly in the method call.

PiperOrigin-RevId: 624887116
2024-04-15 02:38:29 -07:00
Marc Baechinger
20e98ca125 Add release notes 2024-04-15 11:01:04 +02:00
tofunmi
c74603b66b Allow bt601 as sdr colorspace when checking sdr colors
PiperOrigin-RevId: 624877126
2024-04-15 01:57:52 -07:00
Marc Baechinger
ee6961f958 Format with google-java-format 2024-04-15 10:54:49 +02:00
Hubert Mazur
e41f76ea85 Introduce a new optional argument for repeat mode
Add a new string command line optional argument to allow the playback
to run in loop. This would help to use the app in the automated video
tests. The change does not enable the option view for switching the loop
mode in the UI as providing an extra argument implies force, not
optional, loop playback. The extra option is provided with "repeat_mode"
key and one of the possible modes can be specified: NONE|ONE|ALL. The
available options correspond to the Player API to ensure compability.
2024-04-15 10:54:49 +02:00
kimvde
71e7e0f2cf Make VideoFrameProcessor.flush() more resilient
Allow flush to be called before registerInputStream. It's less error
prone to allow methods to be called in any order.

PiperOrigin-RevId: 624873772
2024-04-15 01:43:13 -07:00
kimvde
b7a92ce47a Always set sink provider offset in onReadyToInitializeCodec
Before this CL, the offset was set:
- in onPositionReset for composition preview
- in onReadyToInitializeCodec for ExoPlayer
The code flow is easier to reason about if the path for both use cases
is as shared as possible.

PiperOrigin-RevId: 624870150
2024-04-15 01:29:45 -07:00
kimvde
df3c245250 Remove need to call setVideoEffects before initialize in sink provider
PiperOrigin-RevId: 624869759
2024-04-15 01:26:49 -07:00
kimvde
fa0fb38ca6 Handle clip start position equal to end position in Transformer
After this CL, Transformer will throw if the clipping start and end
positions are the same because MediaMuxer doesn't support writing a
file with no samples. This should work once we default to the in-app
muxer.

Issue: androidx/media#1242
PiperOrigin-RevId: 624861950
2024-04-15 00:53:38 -07:00
ibaker
c151d13a1d Fix Kotlin "local dependency" instructions
The previous syntax doesn't seem to work. I assume I tested it when I
wrote 2eafa570e9,
so maybe it's stopped working since? Or maybe I'm wrong and it never
worked. This syntax was originally proposed in Issue: google/ExoPlayer#6339 and
seems to work today.

PiperOrigin-RevId: 624161848
2024-04-12 06:48:26 -07:00
huangdarwin
25e99af9e7 More strongly discourage use of DebugSurfaceView
This was always intended as a debug API only, but its inclusion in media3.common and public visibility has led to partners sometimes experimenting with this API and complaining when it doesn't work as expected.

PiperOrigin-RevId: 624158798
2024-04-12 06:34:06 -07:00
Copybara-Service
f13c879cd0 Merge pull request #1255 from phcannesson:fix-cast-media-item-conversion
PiperOrigin-RevId: 624147863
2024-04-12 05:45:50 -07:00
Marc Baechinger
5788286b68 add regression test for DefaultMediaItemConverter 2024-04-12 14:16:24 +02:00
tofunmi
1f40451631 UltraHDR: use HdrCapabilitiesUtil to assume device supports hdr editing
PiperOrigin-RevId: 624122752
2024-04-12 04:00:58 -07:00
bachinger
fc1d60beb9 Do not set a duration for live streams
A live window with changing duration can't be properly
displayed in a media notification. The duration constantly
changes and creates a nervous jumping seekbar that is not
really useful.

This change sets the duration for live streams to `C.TIME_UNSET`
when publishing the player state to the platform session. This
way no duration is sent to the platform session which prevents
media controls from drawing a seekbar.

Issue: androidx/media#1256
PiperOrigin-RevId: 624112541
2024-04-12 03:14:41 -07:00
claincly
8ba44ad2b1 Use Builder in deprecated constructors
PiperOrigin-RevId: 623919957
2024-04-11 13:21:32 -07:00
claincly
b1127ed735 Add support for codec importance
Set an importance value when configuring the codec in `Codec.Factory`,

PiperOrigin-RevId: 623902251
2024-04-11 12:19:29 -07:00
tofunmi
a154c98faa Fix test setup for exportUltraHdrImageThenHdrVideo_exportsHdr
make sure compostion.experimentalSetRetainHdrFromUltraHdrImage(true) so that we get hdr output

PiperOrigin-RevId: 623773784
2024-04-11 03:44:53 -07:00
kimvde
0b9180aa4f Clean-ups in VideoSinkProvider Javadoc
PiperOrigin-RevId: 623737397
2024-04-11 00:54:59 -07:00
huangdarwin
47964ff696 Make a method static
This methods doesn't need to be non-static, and can have less state assumed if static

PiperOrigin-RevId: 623466017
2024-04-10 05:47:37 -07:00
ibaker
556ddf4b30 Remove SVG link TODOs now exoplayer2 is no longer published
This removes the TODOs without updating the links, because the
DAC-hosted images are not co-located with the hosted javadoc (unlike
when these images were referenced on exoplayer.dev before 10342507f7),
and therefore we would need to include the full path anyway, at which
point it seems clearer and more robust to keep using a fully-qualified
URL with the domain too.

PiperOrigin-RevId: 623452217
2024-04-10 04:40:33 -07:00
Googler
d71e062780 Add recommendation on setting frame rate for images
PiperOrigin-RevId: 623214178
2024-04-09 10:43:13 -07:00
bachinger
5a84e09a0e Use zero offset when delegating EMSG sample data
When delegating EMSG samples in `HlsSampleStreamWrapper`,
the offset passed into `sampleMetadata(..)` of the delegate
`TrackOutput` must be zero because it is called immediately
after `sampleData(..)` is called.

The condition to trigger this issue is that more than one
metadata samples are pending in `pendingMetadataSampleInfos`
of `FragmentedMp4Extractor` which produces non-zero offsets.

Issue: androidx/media#1002
Issue: androidx/media#1203
PiperOrigin-RevId: 623210835
2024-04-09 10:32:35 -07:00
huangdarwin
24e92bb04f Update TODO link for mastering luminance
PiperOrigin-RevId: 623186293
2024-04-09 09:13:17 -07:00
michaelkatz
2622e566d3 Version bump to media3:1.4.0-alpha01
#minor-release

PiperOrigin-RevId: 623185060
2024-04-09 09:09:22 -07:00
Marc Baechinger
14fb3860e0 Update release notes 2024-04-09 17:35:40 +02:00
Paul-Hubert Cannesson
2e90d1d7c6 Fix album title metadata in media item conversion 2024-04-09 17:11:22 +02:00
samrobinson
81b9739bda Consolidate dump files for item effect vs composition effect.
PiperOrigin-RevId: 623161140
2024-04-09 07:33:38 -07:00
michaelkatz
2c015a5417 Update RELEASENOTES for 1.4.0-alpha01
#minor-release

PiperOrigin-RevId: 623158370
2024-04-09 07:20:18 -07:00
samrobinson
24b86e73cb Group together PCM audio samples by fixed size in CapturingMuxer dumps.
Reduces flakiness of tests that assert on PCM audio. Tests now have to
clearly choose how they want the capturing muxer to handle pcm audio.

Note that the only dump files that have changed are those that deal
with PCM audio (.wav, sowt, twos, silence). Because of the continuous
nature of PCM, timestamps are not part of the dump.

PiperOrigin-RevId: 623155302
2024-04-09 07:04:49 -07:00
tianyifeng
9c72fa8a7a Add reset to BasePreloadManager to release all the holding sources
Compared to `release`, the `reset` method doesn't release the preload manager instance. This applies to the use case that an app wants to discard all the sources but keep the preload manager active for later usage.

Also rename the `releaseSourceInternal` to `removeSourceInternal`, as the latter sounds more generic for different preload manager implementations.

PiperOrigin-RevId: 623148723
2024-04-09 06:30:32 -07:00
ibaker
5d6f514897 Remove references to LegacyPlayerView
This is an internal name for the exoplayer2 `PlayerView` that was never
published as part of media3.

PiperOrigin-RevId: 623120907
2024-04-09 04:12:42 -07:00
michaelkatz
5e85823ea0 Use the onPresentationEnded callback to detect end of offloaded audio
In offloaded audio playback, the `DefaultAudioSink` should use the `AudioTrack.StreamEventCallback` `onPresentationEnded` to note whether the AudioTrack has completed playing all pending data.

PiperOrigin-RevId: 622885399
2024-04-08 10:23:55 -07:00
ibaker
fad3257072 Rollback of c5e894e2d6
PiperOrigin-RevId: 622866208
2024-04-08 09:21:23 -07:00
tonihei
516d4ce1fd Reduce androidx.media usage in UI module to API < 21.
The androidx.media library is only used for its compat MediaStyle.
On API 21 and above, the logic can be easily inlined, and only
on API < 21, the androidx.media handling can be used.

This allows to remove the androidx.media dependency completely
once the minSdk has been increased to 21.

PiperOrigin-RevId: 622855469
2024-04-08 08:50:23 -07:00
Googler
c2356e3989 Rollback of c5e894e2d6
PiperOrigin-RevId: 622292092
2024-04-05 15:11:29 -07:00
sheenachhabra
2a5b9afb88 Update Media3 version number
PiperOrigin-RevId: 622211426
2024-04-05 10:15:38 -07:00
sheenachhabra
d833d59124 Update Media3 version number
PiperOrigin-RevId: 622211426
(cherry picked from commit 2a5b9afb88)
2024-04-05 10:09:43 -07:00
sheenachhabra
1792723be2 Update release notes for 1.3.1 bug fix release
PiperOrigin-RevId: 622189733
(cherry picked from commit 5fc35a6045)
2024-04-08 16:56:58 +00:00
tofunmi
c8aaaa8a85 Ultra Hdr Test: skip devices that don't support format
PiperOrigin-RevId: 622195071
2024-04-05 09:09:16 -07:00
sheenachhabra
5fc35a6045 Update release notes for 1.3.1 bug fix release
PiperOrigin-RevId: 622189733
2024-04-05 08:50:27 -07:00
tianyifeng
28c70e5e54 Add remove(MediaSource) to BasePreloadManager
Both `remove(MediaItem)` and `remove(MediaSource)` return a boolean suggesting that whether the preload manager is holding the corresponding `MediaSource` and it has been removed.

PiperOrigin-RevId: 622185427
2024-04-05 08:27:27 -07:00
tofunmi
d4df814502 Effect: Change link to public available one in shader
PiperOrigin-RevId: 622178740
2024-04-05 08:04:01 -07:00
bachinger
08cc6e673d Add basic multi-player support to DefaultLoadControl
This change makes sure the `DefaultLoadControl` would work
when passed to multiple players. It makes sure and unit tests
that the loading state of a player is maintained for each player
that is using `DefaultLoadControl`.

The targetBufferSize of the `DefaultAllocator` is increased
linearly for each player and memory is allocated in a simple
first-come-first-serve manner.

PiperOrigin-RevId: 622126523
2024-04-05 03:27:51 -07:00
tonihei
e0fa697edf Refine "join" mode in video renderer for surface changes.
The join mode is used for two cases: surface switching and mid-playback
enabling of video.

In both cases, we want to pretend to be ready despite not having rendered
a new "first frame". So far, we also avoided force-rendering the first
frame immediately because it causes a stuttering effect for the
mid-playback enable case. The surface switch case doesn't have this
stuttering issue as the same codec is used without interruption. Not
force-rendering the frame immediately causes the first-frame rendered
callback to arrive too early though, which may lead to cases where
apps hide shutter views too quickly.

This problem can be solved by only avoiding the force-render for the
mid-playback enabling case, but not for the surface switching case.

PiperOrigin-RevId: 622105916
2024-04-05 01:50:14 -07:00
tianyifeng
8867642681 Use DefaultPreloadManager in shortform demo app
The `MediaSourceManager` is removed and its functionalities are replaced by `DefaultPreloadManager`.

PiperOrigin-RevId: 621884502
2024-04-04 09:39:23 -07:00
bachinger
617f9898c3 Add isPlaybackOngoing and stopMediaSessionService
This API additions help an app to implement the lifecycle of a MediaSessionService
properly and in consistency with the `MediaSessionService` being in the foreground
or not.

Not properly implementing `onTaskRemoved` is the main reason for crashes and
confusion. This change provides `MediaSessionService` with a default
implementation that avoids crashes of the service. This default implementation
uses the new API provided with this change just as an app can do.

Issue: androidx/media#1219
PiperOrigin-RevId: 621874838
2024-04-04 09:01:55 -07:00
kimvde
f9ed303bf1 Rollback of 85d4df2d2d
PiperOrigin-RevId: 621863325
2024-04-04 08:15:46 -07:00
kimvde
85d4df2d2d Throw if clip end position is equal to start position
Issue: androidx/media#1242
PiperOrigin-RevId: 621850154
2024-04-04 07:20:07 -07:00
sheenachhabra
d57229ad15 Import string translations
#minor-release

PiperOrigin-RevId: 621828038
2024-04-04 05:38:42 -07:00
sheenachhabra
1a710b06d0 Import string translations
#minor-release

PiperOrigin-RevId: 621828038
(cherry picked from commit d57229ad15)
2024-04-04 05:34:46 -07:00
ibaker
032cad8d09 Remove more unnecessary SDK checks now the min is 19
PiperOrigin-RevId: 621600592
2024-04-03 12:15:24 -07:00
tofunmi
896d147444 Overlay: fix the overlay anchor translation
Makes OverlayFrameAnchor works as described in the OverlaySettings documentation. Currently the code does the opposite e.g setting the anchor to (+1,-1) makes the code anchor to the top left rather than the bottom right.

PiperOrigin-RevId: 621585558
2024-04-03 11:27:43 -07:00
huangdarwin
60bb24a930 Overlay: Add javadoc for why we fly overlays vertically.
Otherwise, apps overriding BitmapOverlay.getVertexTransformation may not
realize this is being done, and may ask why bitmaps are flipped vertically from
what they expect

Reference: https://github.com/androidx/media/issues/1128
PiperOrigin-RevId: 621544348
2024-04-03 09:21:23 -07:00
ibaker
f9b1c82565 Remove complete TODO from TextRenderer
The method in question was added in 80bfa819c0

Also fix typo in another TODO lower down

PiperOrigin-RevId: 621543035
2024-04-03 09:14:54 -07:00
tonihei
6e66885311 Add additional queue add/remove/next icons
PiperOrigin-RevId: 621529526
2024-04-03 08:26:11 -07:00
ibaker
85793ea2ca Update ClippedPlaybackTest to fail on a player error (vs timing out)
Also explicitly use a synchronized list to collect cues. The previous
bare `ArrayList` was probably fine, because the `ConditionVariable`
creates a memory barrier between the main thread and the test thread,
but this seems more explicit (and any performance implications of the
synchronization don't matter for this test).

PiperOrigin-RevId: 621523824
2024-04-03 08:04:57 -07:00
kimvde
bf21f1edd5 Add methods to seek in preview audio pipeline
PiperOrigin-RevId: 621513330
2024-04-03 07:21:01 -07:00
ibaker
59710a5f81 Remove internal instructions from test-generated-goldens/README.md
PiperOrigin-RevId: 621163748
2024-04-02 07:15:35 -07:00
sheenachhabra
308c4c4fbf Take fragment duration in Ms instead of Us
PiperOrigin-RevId: 621144165
2024-04-02 05:44:46 -07:00
Googler
136baa148f Rollback of f4e444bdd2
PiperOrigin-RevId: 620271247
2024-03-29 10:07:56 -07:00
claincly
b584abfaba Clarify error message to remind user of forceAudioTrack
PiperOrigin-RevId: 620042879
2024-03-28 13:40:07 -07:00
jbibik
98b0d24379 Add a new empty Compose Demo as a skeleton
PiperOrigin-RevId: 620020593
2024-03-28 12:30:20 -07:00
huangdarwin
0730a5976b Color: Add undefined values to toString methods
This way, we can identify the undefined values later, if they're in use often.

PiperOrigin-RevId: 619967637
2024-03-28 09:54:48 -07:00
ibaker
c5e894e2d6 Ensure DownloadHelper doesn't leak unreleased Renderer instances
Issue: androidx/media#1224
PiperOrigin-RevId: 619935786
2024-03-28 08:17:18 -07:00
sheenachhabra
b4e6b9a694 Update java doc for processedInputs field
PiperOrigin-RevId: 619902389
2024-03-28 06:08:22 -07:00
tofunmi
272fada10e Signal assetloader output format in image case
the output format conatins key information about the output of the assetloader being hdr, so we must signal the output format, not the input format to the sample exporter

fixes mh ultraHdr test failures.
Also discovered images created are very device specfic so got rid of the pixel tests, we have pixel tests in the effects library that cover the same case.

PiperOrigin-RevId: 619899249
2024-03-28 05:56:39 -07:00
ibaker
b60cd2c033 Rollback of e665e2aee8
PiperOrigin-RevId: 619871653
2024-03-28 04:04:01 -07:00
ibaker
5fe906f1e9 Rollback of e665e2aee8
PiperOrigin-RevId: 619871653
(cherry picked from commit b60cd2c033)
2024-03-28 04:00:11 -07:00
kimvde
04a3889998 Reset maxPositionOfRemovedSources in DefaultAudioMixer
If the mixer is reset without resetting maxPositionOfRemovedSources and
then reused, the value of maxPositionOfRemovedSources can be outdated,
leading to an incorrect number of bytes being output by the mixer.

PiperOrigin-RevId: 619832502
2024-03-28 01:22:25 -07:00
tofunmi
828f6d87f9 Make calculateSpeedAdjustedTime() output monotonically increasing
calculate based on the output of consecutive calls rather than the speed provider speed change point to ensure the timestamps are monotonically increasing.

PiperOrigin-RevId: 619584001
2024-03-27 10:55:59 -07:00
Copybara-Service
7b5522fc58 Merge pull request #1054 from jekopena:main
PiperOrigin-RevId: 619573181
(cherry picked from commit 8fe70332ee)
2024-03-27 10:24:32 -07:00
Copybara-Service
8fe70332ee Merge pull request #1054 from jekopena:main
PiperOrigin-RevId: 619573181
2024-03-27 10:24:32 -07:00
sheenachhabra
55289b4392 Rename BasicMp4Writer to Mp4Writer
PiperOrigin-RevId: 619560211
2024-03-27 09:44:42 -07:00
ibaker
d684cdb330 Add PlayerView.setControllerAnimationEnabled(boolean)
Issue: androidx/media#1227
PiperOrigin-RevId: 619558900
2024-03-27 09:40:09 -07:00
ibaker
4caed3cfb2 Add PlayerView.setControllerAnimationEnabled(boolean)
Issue: androidx/media#1227
PiperOrigin-RevId: 619558900
(cherry picked from commit d684cdb330)
2024-03-27 09:36:22 -07:00
ibaker
ebfd540817 Fix javadoc on PlayerView.setControllerVisibilityListener
#minor-release

PiperOrigin-RevId: 619536799
2024-03-27 08:20:38 -07:00
ibaker
26ce3f012a Fix javadoc on PlayerView.setControllerVisibilityListener
#minor-release

PiperOrigin-RevId: 619536799
(cherry picked from commit ebfd540817)
2024-03-27 08:17:03 -07:00
sheenachhabra
58e8300ea2 Make isMetadataSupported method public
Moved few other public methods from `Mp4Utils` class into the
corresponding classes which needs them.

PiperOrigin-RevId: 619535658
2024-03-27 08:16:37 -07:00
sheenachhabra
66547cc331 Remove Mp4Writer interface
Since the public class has already been split into `Mp4Muxer` and
`FragmentedMp4Muxer`, there is no need for having common interface
for internal implementation.

In the follow up CL `BasicMp4Writer` will be renamed to `Mp4Writer`
which is more appropriate and aligns with public class names.

PiperOrigin-RevId: 619486876
2024-03-27 04:28:07 -07:00
jbibik
5a318deb40 Downgrade kotlin plugin version to 1.9.0
Earlier upgrade in 276e0655f4 was too high, since Android Studio Iguana is still bundled with Kotlin plugin with version `232-1.9.0-release-358-AS10227`. The result of the mismatched plugin is a build failure like:

`Module was compiled with an incompatible version of Kotlin. The binary version of its metadata is 1.9.0, expected version is XXX`

Although according to https://plugins.jetbrains.com/plugin/6954-kotlin, the 1.9.23 is already available. So we will be able to upgrade again soon.

Version 1.9.0 is still good enough for the compose compiler to be 1.5.0+ according to https://developer.android.com/jetpack/androidx/releases/compose-kotlin#pre-release_kotlin_compatibility

PiperOrigin-RevId: 619278402
2024-03-26 12:43:44 -07:00
huangdarwin
24e1796c50 Effect: Improve setEnableColorTransfers javadoc.
PiperOrigin-RevId: 619250163
2024-03-26 11:15:34 -07:00
ibaker
7a105e0e57 Fix XingSeeker @param tags - follow-up to 4fde35c9cc
PiperOrigin-RevId: 619249887
2024-03-26 11:11:58 -07:00
tianyifeng
8f2f3bb7e4 Allow target preload status to be null to indicate not to preload
PiperOrigin-RevId: 619246259
2024-03-26 11:03:10 -07:00
kimvde
98dac54816 Fix negative position for clipped media
With this CL:
- The large timestamp offset added by ExoPlayer so that decoders
don't see any negative timestamps is removed before passing the
timestamp to the AudioGraph.
- Clipped media timestamps are offset by the clipping start position
before being passed to the AudioGraph.
- The offset added to the audio buffer timestamps is removed when
computing the audio sink position, to convert them back to the
timestamps passed by the player.

PiperOrigin-RevId: 619225990
2024-03-26 10:05:11 -07:00
sheenachhabra
8d65b75185 Rename setFragmentedMp4Enabled to setOutputFragmentedMp4
PiperOrigin-RevId: 619216854
2024-03-26 09:34:23 -07:00
sheenachhabra
8eb1390f80 Create FragmentedMp4Muxer class
This CL aims to separate Fragmented MP4 related logic in a separate public class.
Earlier all the logic was in a single class `Mp4Muxer`.

PiperOrigin-RevId: 619206661
2024-03-26 09:02:43 -07:00
tonihei
737bf08314 Don't apply performance point workaround from API 35
The workaround check is now part of CTS and we should be able
to rely on the PerformancePoints values (or at least can be sure
that they cover all CDD requirements)

#minor-release

PiperOrigin-RevId: 619201331
2024-03-26 08:42:49 -07:00
tofunmi
f4fefd19f7 Document and test multi asset ultraHDR support
PiperOrigin-RevId: 619200688
2024-03-26 08:39:44 -07:00
tonihei
a5d0cb51bc Don't apply performance point workaround from API 35
The workaround check is now part of CTS and we should be able
to rely on the PerformancePoints values (or at least can be sure
that they cover all CDD requirements)

#minor-release

PiperOrigin-RevId: 619201331
(cherry picked from commit 737bf08314)
2024-03-26 08:38:31 -07:00
ibaker
d00ca1e343 Plumb MP3 average bitrate from metadata frames into Format
Issue: androidx/media#1081

#minor-release

PiperOrigin-RevId: 619185083
2024-03-26 07:40:08 -07:00
ibaker
88ebc89da2 Plumb MP3 average bitrate from metadata frames into Format
Issue: androidx/media#1081

PiperOrigin-RevId: 619185083
(cherry picked from commit d00ca1e343)
2024-03-26 07:36:46 -07:00
tonihei
6e0f8e3b0d Remove decode-only flag
No known component is using this flag anymore and it has been
deprecated for a while for custom renderers and decoders.

PiperOrigin-RevId: 619154299
2024-03-26 05:28:27 -07:00
tofunmi
ef2314c404 Move bitmap decoding out of datasource util
PiperOrigin-RevId: 619139208
2024-03-26 04:10:38 -07:00
tofunmi
65e94480f4 Transformer: add single-asset ultraHDR image to HLG HDR vid transcoding
PiperOrigin-RevId: 619138202
2024-03-26 04:06:41 -07:00
tonihei
0f42dd4752 Use output start time instead of deprecated isDecodeOnly in CeaDecoder
PiperOrigin-RevId: 619133908
2024-03-26 03:47:18 -07:00
andrewlewis
c3c964627f Log internal Transformer lifecycle for debugging
Add logging similar to `ExoPlayerImpl` to make bug reports more useful.

PiperOrigin-RevId: 619117500
2024-03-26 02:31:31 -07:00
ibaker
6cb25119fb In-line versions only used by exoplayer-media2 extension
Also remove an unused `androidxTestServicesStorageVersion` version.

Issue: androidx/media#1216
PiperOrigin-RevId: 618990983
2024-03-25 16:21:29 -07:00
ibaker
dca3c61c5b In-line versions only used by exoplayer-media2 extension
Also remove an unused `androidxTestServicesStorageVersion` version.

Issue: androidx/media#1216
PiperOrigin-RevId: 618990983
(cherry picked from commit 6cb25119fb)
2024-03-25 16:18:02 -07:00
sheenachhabra
2eaece5ed9 Move setMaxDelayBetweenSamplesMs on Transformer builder
This property is transformer specific and does not belong to
muxer interface.
This is to eventually replace muxer interface in Transformer module with
muxer interface in Muxer module.

PiperOrigin-RevId: 618895836
2024-03-25 11:02:15 -07:00
Googler
f4e444bdd2 Internal change
PiperOrigin-RevId: 618879473
2024-03-25 10:12:34 -07:00
tonihei
ab0391167c Include nullness of MediaMetadata.extras in equals method
This ensures MediaMetadata with just non-null extras is not
considered equal to MediaMetadata.EMPTY. This makes sure the
contents are bundled when a controller sets the extras in a
new MediaItem

Issue: androidx/media#1176

#minor-release

PiperOrigin-RevId: 618876642
2024-03-25 10:05:15 -07:00
tonihei
3657831923 Include nullness of MediaMetadata.extras in equals method
This ensures MediaMetadata with just non-null extras is not
considered equal to MediaMetadata.EMPTY. This makes sure the
contents are bundled when a controller sets the extras in a
new MediaItem

Issue: androidx/media#1176

PiperOrigin-RevId: 618876642
(cherry picked from commit ab0391167c)
2024-03-25 10:02:23 -07:00
tonihei
73c0ebb214 Additional clean-up and formatting 2024-03-25 15:02:31 +00:00
ibaker
fd268eed46 Remove unecessary re-setting of group from session Gradle files
These TODOs precede <unknown commit> when the group was set in the top-level
`build.gradle` file.

Issue: androidx/media#1215
PiperOrigin-RevId: 618835040
2024-03-25 07:33:05 -07:00
ibaker
06a4036539 Remove unecessary re-setting of group from session Gradle files
These TODOs precede <unknown commit> when the group was set in the top-level
`build.gradle` file.

Issue: androidx/media#1215
PiperOrigin-RevId: 618835040
(cherry picked from commit fd268eed46)
2024-03-25 07:30:24 -07:00
Juan Carlos Penalver
8673e6d39a Removing label from toLogString. 2024-03-25 12:00:14 +00:00
Juan Carlos Penalver
54c23e2856 Reverting changes in gradle-wrapper.properties 2024-03-25 12:00:14 +00:00
Juan Carlos Penalver
0a04e7908b Addressing PR feedback. 2024-03-25 12:00:14 +00:00
Juan Carlos Penalver
591020065a Adding IllegalStateException to Format build and unit tests. 2024-03-25 12:00:14 +00:00
Juan Carlos Penalver
e9e47f4fe6 Removing id from Label and ensuring label/labels consistency in Format.Builder. 2024-03-25 12:00:14 +00:00
Juan Carlos Penalver
63fb68e99e Reverting breaking changes by keeping label and adding labels. 2024-03-25 12:00:14 +00:00
Juan Carlos Penalver
df763220c8 Replacing label with a list of Label elements in Format. 2024-03-25 12:00:14 +00:00
ibaker
d997ba367c Rollback of 7cffae9cd0
PiperOrigin-RevId: 618799275
2024-03-25 04:30:55 -07:00
Copybara-Service
c352e2c7b8 Merge pull request #1213 from MGaetan89:update_guava
PiperOrigin-RevId: 618797532
2024-03-25 04:21:53 -07:00
sheenachhabra
483d2bb9e7 Add Muxer interface in muxer module
The immediate plan is to replace `Transformer Muxer interface`
with this one.
It was not straight forward to move/change `Transformer Muxer interface`
hence this intermediate step.
The follow up CL will also remove fragmented MP4 related code from
`Mp4Muxer` and move it into `FragmentedMp4Muxer implements Muxer`.

PiperOrigin-RevId: 618789265
2024-03-25 03:40:15 -07:00
Gaëtan Muller
d66a3032c1 Update Guava to 33.0.0-android
Following the recommendation in `constants.gradle`:
d13a0f4ec6/constants.gradle (L29-L31)

This PR updates Guava to the version used in the Android repository: 33.0.0.

The changelog for Guava 33.0.0 is available [here](https://github.com/google/guava/releases/tag/v33.0.0).
2024-03-22 16:14:41 +00:00
huangdarwin
d165af9a85 Test: Use AssumptionViolatedException for format support detection.
This is the most widely-used test-skipping method I'm aware of, so I figured this
would be a great method to scale usage of AssumptionViolatedException.

PiperOrigin-RevId: 618160931
2024-03-22 06:41:18 -07:00
sheenachhabra
16aac07bce Add support for processing 3 byte NAL start code in Mp4Muxer
Issue: androidx/media#725

Ideally the test to transmux a `ts` file (having 3 bytes NAL start code)
should go into `Mp4MuxerEndToEndTest`but `Mp4MuxerEndToEndTest` uses `MediaExtractor` and `MediaExtractor` is returning samples with `4 byte NAL start code` which will not exercise the newly added code path.
Hence the test is added in `TransformerWithInAppMuxerEndToEndTest` which
internally uses `media3 extractor` and feeds samples with `3 bytes NAL start code`
only.

PiperOrigin-RevId: 617985866
2024-03-21 15:49:12 -07:00
kimvde
6fc4f0263f Add methods required for seek to AudioGraph
Seeking will consist of the following steps:
- Block the AudioGraph input data.
- Flush the AudioGraph.
- Seek the ExoPlayers.
- Unblock the AudioGraph input data.

PiperOrigin-RevId: 617868124
2024-03-21 09:31:51 -07:00
tonihei
ed505df2ca Partial revert of 3a7d31a599
The original change did not set the color info in the codec
for standard SDR infos. This was meant to help with consistency
to avoid a situation where the information is partially set and
later the bitstream provides slightly different values (all in
standard SDR though).

We can revert this part because the bitstream may change anyway
and the decoder needs to handle this internally. And more
importantly, it also avoids removing this information when encoding
the format again in Transformer.

PiperOrigin-RevId: 617582066
2024-03-20 11:51:25 -07:00
tonihei
5fc9ddab0b Partial revert of 3a7d31a599
The original change did not set the color info in the codec
for standard SDR infos. This was meant to help with consistency
to avoid a situation where the information is partially set and
later the bitstream provides slightly different values (all in
standard SDR though).

We can revert this part because the bitstream may change anyway
and the decoder needs to handle this internally. And more
importantly, it also avoids removing this information when encoding
the format again in Transformer.

PiperOrigin-RevId: 617582066
(cherry picked from commit ed505df2ca)
2024-03-20 11:48:23 -07:00
sheenachhabra
2491dd07e1 Process all samples before writing them to mdat
This refactoring is required to support 3 byte NAL start code, in which
the sample ByteBuffer might change after AnnexB to Avcc conversion.
This would required changes in the corresponding BufferInfo as well.

PiperOrigin-RevId: 617538338
2024-03-20 09:33:10 -07:00
jbibik
276e0655f4 Upgrade Kotlin version to 1.9.22
This will allow us to use the latest Compose complier version (from https://developer.android.com/jetpack/androidx/releases/compose-kotlin#pre-release_kotlin_compatibility) for the future Compose Demo.

PiperOrigin-RevId: 617509694
2024-03-20 07:44:52 -07:00
tonihei
3a7d31a599 Don't set codec color info for default SDR
Some media can read color info values from the bitstream
and may partially set some of the SDR default values in
Format.ColorInfo. Setting these default values for SDR can
confuse some codecs and may also prevent adaptive ABR
switches if not all ColorInfo values are set in exactly the
same way.

We can avoid any influence of HDR color info handling by
disabling setting the color info MediaFormat keys for SDR
video and also avoid codec reset at format changes if both
formats are SDR with slightly different ColorInfo settings.

To identify "SDR" ColorInfo instances, we need to do some
fuzzy matching as many of the default values are assumed to
match the SDR profile even if not set.

Issue: androidx/media#1158
PiperOrigin-RevId: 617473937
2024-03-20 04:58:13 -07:00
tonihei
b0adf2fe43 Don't set codec color info for default SDR
Some media can read color info values from the bitstream
and may partially set some of the SDR default values in
Format.ColorInfo. Setting these default values for SDR can
confuse some codecs and may also prevent adaptive ABR
switches if not all ColorInfo values are set in exactly the
same way.

We can avoid any influence of HDR color info handling by
disabling setting the color info MediaFormat keys for SDR
video and also avoid codec reset at format changes if both
formats are SDR with slightly different ColorInfo settings.

To identify "SDR" ColorInfo instances, we need to do some
fuzzy matching as many of the default values are assumed to
match the SDR profile even if not set.

Issue: androidx/media#1158
PiperOrigin-RevId: 617473937
(cherry picked from commit 3a7d31a599)
2024-03-20 04:55:06 -07:00
sheenachhabra
3272ad50f3 Skip AnnexB to Avcc conversion for AV1 video format
The AV1 video stream does not contain NAL unit which is a concept
specific to H.264/H.265.
This was not caught before muxer does an in place replacement of
`NAL start code` with `NAL length`. In the absence of `NAL start code`
it was automatically a no-op.

PiperOrigin-RevId: 617193317
2024-03-19 09:18:44 -07:00
sheenachhabra
e14156aa3b Rename test classes having duplicate names
PiperOrigin-RevId: 616887534
2024-03-18 11:16:48 -07:00
huangdarwin
33a87a451c Test: Remove EnsuresNonNull from media3 editing tests.
nullness checks were removed a while ago from editing, so no need for them now.

Bit neater to have less code to parse too.

Also, removes RequiresNonNull

PiperOrigin-RevId: 616887502
2024-03-18 11:13:10 -07:00
huangdarwin
d2dc901b6a Test: Fix failing HDR sequence test by swapping assumption.
Oops, missed this one in 1adb2b270d

PiperOrigin-RevId: 616871770
2024-03-18 10:28:47 -07:00
huangdarwin
e446f20a70 Test: Remove nullness for testid
This also makes it more consistent with newer testId tests that don't have nullness, so tests don't look inconsistent, and was pretty easy to do :P

PiperOrigin-RevId: 616856888
2024-03-18 09:47:12 -07:00
huangdarwin
1adb2b270d Test: Fix failing HdrEditingTest by swapping assumption.
This was broken by 2fa38d15dd, which added an assumes
method, but missed the `!` operator for the tests where HDR is
unsupported. Add an assumes method that assumes a lack of support
for HDR.

Tested on the failing device (Pixel 7) and confirmed this fixes
the test on that device, to throw AssumptionViolatedException
instead of allowing test logic to run after failing the
assumption.

PiperOrigin-RevId: 616846588
2024-03-18 09:12:33 -07:00
huangdarwin
4c85a04d07 Test: Use AssumptionViolatedException for OpenGL Tone-map support.
PiperOrigin-RevId: 616827385
2024-03-18 08:00:02 -07:00
huangdarwin
0731b07954 Test: Use format arg for assumeDeviceSupportsHdrEditing.
PiperOrigin-RevId: 616825970
2024-03-18 07:53:23 -07:00
huangdarwin
2fa38d15dd Test: Use AssumptionViolatedException for HDR capability check.
Also, use a common util method

PiperOrigin-RevId: 616815502
2024-03-18 07:06:17 -07:00
claincly
e8612a0c02 Add warning log if no output is set
PiperOrigin-RevId: 616796787
2024-03-18 05:33:17 -07:00
tianyifeng
2c8d07c2dd Inform DefaultPreloadManager when player uses PreloadMediaSource
Add a new method `onUsedByPlayer(PreloadMediaSource)` for `PreloadMediaSource.PreloadControl`, which will be invoked when the player starts to use the `PreloadMediaSource`, or calling `PreloadMediaSource.preload` while the player is already using that source. `DefaultPreloadManager` will immediately preload the next source when receiving `onUsedByPlayer` event.

PiperOrigin-RevId: 616789121
2024-03-18 04:54:49 -07:00
tonihei
87f4a3ca71 Add some clarifications around CommandButton.iconUri to Javadoc
PiperOrigin-RevId: 616775044
2024-03-18 03:43:36 -07:00
huangdarwin
cbc654a721 GL: Use GLES20.GL_FALSE and GL_TRUE instead of hardcoded value.
PiperOrigin-RevId: 616759833
2024-03-18 02:35:55 -07:00
tofunmi
d269b93755 Transformer: Take effects into account when signalling duration
PiperOrigin-RevId: 616224079
2024-03-15 13:21:12 -07:00
huangdarwin
3136deb9b3 Test: Remove extraneous testIds.
PiperOrigin-RevId: 616213378
2024-03-15 12:39:43 -07:00
tofunmi
4d1ede5432 Ultra HDR: release texture after use
PiperOrigin-RevId: 616209205
2024-03-15 12:23:45 -07:00
tofunmi
fe640da5e8 Transformer: add speedChange API
PiperOrigin-RevId: 616163061
2024-03-15 10:02:37 -07:00
tofunmi
762065fae0 Add api to find duration after an effect is applied
PiperOrigin-RevId: 616157067
2024-03-15 09:41:40 -07:00
Googler
415d779c62 Explicitly check that AudioGraph input is PCM 16
AudioGraph implicitly assumes that input will be PCM 16 bit, and not float.
Make the check explicit.

PiperOrigin-RevId: 616149131
2024-03-15 09:14:04 -07:00
tofunmi
b9843af6a0 SpeedChangingAudioProcessor: process all callbacks after audio ends
PiperOrigin-RevId: 616143969
2024-03-15 08:54:26 -07:00
huangdarwin
b126bae93d Effect: Add EGL_EXT_gl_colorspace_bt2020_hlg support, on API 34+
Confirmed that the HLG extension displays properly on Pixel 7 Pro, API 34 and Samsung S24, API 34. On these devices, this fixes the washed out HLG preview issue on API 34, where the PQ ext had a washed out look, and where the HLG ext is supported (this bug didn't occur on API 33, only 34).

More info on manual tests done to sanity-check:
* Test cases: Transformer debug SurfaceView and ExoPlayer.setVideoEffects
* Test inputs: HLG and PQ
* Test devices: Pixel 7 Pro (API 33 & 34), Samsung Galaxy S24 (API 34)
* Added debugging: Logging colorInfo used in GlUtil.createEglSurface

No regressions were seen. HLG extension is used more in API 34, and behavior stays the same on API 33. Only human-visible change without logging is that HLG content looks better on API 34, for Samsung S24 and Pixel 7 Pro.

PiperOrigin-RevId: 616131192
2024-03-15 08:06:49 -07:00
tofunmi
c0ffc94d15 Add GlEffect that asynchronously adjusts input presentation times
Single asset export only effect.

PiperOrigin-RevId: 616114153
2024-03-15 06:56:25 -07:00
ibaker
48cffc849a Fix proguard rule for DefaultVideoFrameProcess.Factory.Builder.build()
Issue: androidx/media#1187

#minor-release

PiperOrigin-RevId: 616112879
2024-03-15 06:50:16 -07:00
ibaker
961d204c2c Fix proguard rule for DefaultVideoFrameProcess.Factory.Builder.build()
Issue: androidx/media#1187

#minor-release

PiperOrigin-RevId: 616112879
(cherry picked from commit 48cffc849a)
2024-03-15 06:46:53 -07:00
ibaker
e9ed874e51 Don't emit a CuesWithTiming for zero-duration Subtitle events
It's a bit arguable whether the `Subtitle` implementation supports
zero-duration events, since `getEventTimeCount` is documented as
effectively "the number of times the cues returns by `getCues(long)`
changes", and zero-duration events violate that. However, the current
`WebvttSubtitle` impl **does** produce zero-duration events, so it
seems safer to handle them gracefully here and then, as a possible
follow-up, fix the `WebvttSubtitle` impl (or remove it completely).

Issue: androidx/media#1177

#minor-release

PiperOrigin-RevId: 616095798
2024-03-15 05:26:21 -07:00
ibaker
d195b094b4 Don't emit a CuesWithTiming for zero-duration Subtitle events
It's a bit arguable whether the `Subtitle` implementation supports
zero-duration events, since `getEventTimeCount` is documented as
effectively "the number of times the cues returns by `getCues(long)`
changes", and zero-duration events violate that. However, the current
`WebvttSubtitle` impl **does** produce zero-duration events, so it
seems safer to handle them gracefully here and then, as a possible
follow-up, fix the `WebvttSubtitle` impl (or remove it completely).

Issue: androidx/media#1177

PiperOrigin-RevId: 616095798
(cherry picked from commit e9ed874e51)
2024-03-15 05:22:47 -07:00
tofunmi
f39fe82bba Support ultra HDR in effect
adding sending gainmap to shader program and applying gainmap to base in shader

PiperOrigin-RevId: 616070582
2024-03-15 03:22:54 -07:00
Copybara-Service
8a169d104f Merge pull request #1117 from loliball:dev_wav_align_fix
PiperOrigin-RevId: 615820438
(cherry picked from commit e9a28beb44)
2024-03-14 10:17:49 -07:00
Copybara-Service
e9a28beb44 Merge pull request #1117 from loliball:dev_wav_align_fix
PiperOrigin-RevId: 615820438
2024-03-14 10:17:49 -07:00
Rohit Singh
c84a3279d3 Add unit test 2024-03-14 16:12:40 +00:00
kimvde
e40ce150bf Implement AudioGraph.flush()
When flushing the AudioGraph, the AudioMixer will be preserved but the
sources will be recreated. This is probably a bit less efficient but
makes the logic simpler. Indeed, if we had to keep the sources alive,
we would need to add a way to reconfigure them with a new timestamp for
seeking. We would also need to change the way sources are ended because
they are currently removed when they are ended. Also, it is acceptable
to have a small delay when seeking, which means that performance is less
critical than for playback.

PiperOrigin-RevId: 615775501
2024-03-14 07:49:07 -07:00
andrewlewis
9da878956a Add short form content demo to project
#minor-release

PiperOrigin-RevId: 615756117
2024-03-14 06:29:01 -07:00
andrewlewis
6f0b70ea78 Add short form content demo to project
#minor-release

PiperOrigin-RevId: 615756117
(cherry picked from commit 9da878956a)
2024-03-14 06:25:23 -07:00
sheenachhabra
80247bc32c Remove deprecated methods from Mp4Muxer class
PiperOrigin-RevId: 615736494
2024-03-14 04:59:02 -07:00
kimvde
3248b7962a Add clipFloatOutput parameter to AudioMixer
PiperOrigin-RevId: 615720340
2024-03-14 03:44:37 -07:00
huangdarwin
ca6031deab Update old method name.
getSupportedEncoderNamesForHdrEditing became getSupportedEncodersForHdrEditing at some point, but this comment wasn't updated before...

PiperOrigin-RevId: 615712707
2024-03-14 03:11:03 -07:00
christosts
5f6e5bcda2 Composition preview: image renderer does not forward VideoSink events
PiperOrigin-RevId: 615479550
2024-03-13 11:10:02 -07:00
sheenachhabra
668a172683 Rename MuxerWrapper.release() method
PiperOrigin-RevId: 615399319
2024-03-13 06:54:19 -07:00
sheenachhabra
644d9a3461 Remove usage of deprecated methdods from Mp4Muxer tests
PiperOrigin-RevId: 615392633
2024-03-13 06:31:00 -07:00
sheenachhabra
dfe9fba17d Remove non actionable TODOs from Mp4Muxer code
PiperOrigin-RevId: 615372415
2024-03-13 05:07:34 -07:00
ibaker
12aa637fa1 Add section comments to settings.gradle
PiperOrigin-RevId: 615005773
2024-03-12 05:38:53 -07:00
ibaker
c41213c273 Move test-session-xxx modules from core_settings to settings
This ensures these modules are only configured when directly working
on the library, rather than when depending on it locally. These modules
only contain tests, they shouldn't be depended on by any apps (and are
not published via Maven).

PiperOrigin-RevId: 615004801
2024-03-12 05:35:31 -07:00
ibaker
860f18f29c Move test-session-xxx modules from core_settings to settings
This ensures these modules are only configured when directly working
on the library, rather than when depending on it locally. These modules
only contain tests, they shouldn't be depended on by any apps (and are
not published via Maven).

PiperOrigin-RevId: 615004801
(cherry picked from commit c41213c273)
2024-03-12 05:30:06 -07:00
michaelkatz
8b219b0ae6 Start playing period-enabled renderers when setting playWhenReady true
Renderers may be enabled for subsequent media items as soon as the current media item's renderer's isEnded() returns true. Currently, when a player is set to pause, it stops all renderers that are `STATE_STARTED`. When a player is set to play, it starts all renderers that are enabled. This would include renderers that were enabled early for the subsequent media item. The solution is to only start renderers that are enabled by the current playing period.

Issue: androidx/media#1017
PiperOrigin-RevId: 614734437
2024-03-11 11:31:12 -07:00
michaelkatz
561dafcdea Start playing period-enabled renderers when setting playWhenReady true
Renderers may be enabled for subsequent media items as soon as the current media item's renderer's isEnded() returns true. Currently, when a player is set to pause, it stops all renderers that are `STATE_STARTED`. When a player is set to play, it starts all renderers that are enabled. This would include renderers that were enabled early for the subsequent media item. The solution is to only start renderers that are enabled by the current playing period.

Issue: androidx/media#1017
PiperOrigin-RevId: 614734437
(cherry picked from commit 8b219b0ae6)
2024-03-11 11:27:26 -07:00
tonihei
cbed80ecf3 Always set PARAMETER_KEY_TUNNEL_PEEK when tunneling
This should already be the default, but some devices seem
to not adhere to this contract and assume the default is unset.

Issue: androidx/media#1169
PiperOrigin-RevId: 614697283
2024-03-11 09:49:09 -07:00
tonihei
c8ae6d1142 Always set PARAMETER_KEY_TUNNEL_PEEK when tunneling
This should already be the default, but some devices seem
to not adhere to this contract and assume the default is unset.

Issue: androidx/media#1169
PiperOrigin-RevId: 614697283
(cherry picked from commit cbed80ecf3)
2024-03-11 09:46:07 -07:00
christosts
6f109ffa6a Composition preview: play multiple images
PiperOrigin-RevId: 614690669
2024-03-11 09:28:40 -07:00
christosts
e399ea19bb Composition preview: move audio and video components
PiperOrigin-RevId: 614673253
2024-03-11 08:29:38 -07:00
sheenachhabra
aba395ca8b Add Mp4OrientationData class
Mp4Muxer now has a single method to accept different
types of metadata.

PiperOrigin-RevId: 614646331
2024-03-11 06:45:15 -07:00
tonihei
e4a55844d0 Add device-specific opt-ins for async MediaCodecAdapter
Some devices just don't work very well with the synchronous
model, but are currently still excluded from our approximate
API 31 check. This change allows to include additional devices
or device groups by passing in the Context to the default
adapter.

It also adopts the workaround added in ebceee08c6
for Fire TV Smart devices that exhibit this issue.

PiperOrigin-RevId: 614642545
2024-03-11 06:29:46 -07:00
tonihei
3f3d60eb6a Add device-specific opt-ins for async MediaCodecAdapter
Some devices just don't work very well with the synchronous
model, but are currently still excluded from our approximate
API 31 check. This change allows to include additional devices
or device groups by passing in the Context to the default
adapter.

It also adopts the workaround added in ebceee08c6
for Fire TV Smart devices that exhibit this issue.

PiperOrigin-RevId: 614642545
(cherry picked from commit e4a55844d0)
2024-03-11 06:27:15 -07:00
tonihei
410c0492cc Force external surround sound flag if requested by device
Some FireOS6 devices ask to force the external surround global
flag and ignore any signals from the HDMI connection.

This is the equivalent change of e341944d1e

PiperOrigin-RevId: 614634499
2024-03-11 05:55:43 -07:00
tonihei
fffbf9ac4e Force external surround sound flag if requested by device
Some FireOS6 devices ask to force the external surround global
flag and ignore any signals from the HDMI connection.

This is the equivalent change of e341944d1e

PiperOrigin-RevId: 614634499
(cherry picked from commit 410c0492cc)
2024-03-11 05:52:52 -07:00
tonihei
0e42c8945f Automatically add icon drawables for icon constants
Having a default icon available allows apps to only specify the
icon constant without having to define an icon drawable themselves
as Media3 can fill in the icon resource for backwards compatibility.

The switch util method allows R8 to easily remove unused icons, so
having default icons won't affect APK size unless the constants are
used to set up the CommandButtons.

PiperOrigin-RevId: 614623909
2024-03-11 05:06:21 -07:00
tonihei
18cbbf3850 Reorder audio capability checks
Using the more accurate check available on later API versions
first is likely better than falling back to a fallback solution
from older API versions.

PiperOrigin-RevId: 614612628
2024-03-11 04:17:35 -07:00
tonihei
a85d9e251c Reorder audio capability checks
Using the more accurate check available on later API versions
first is likely better than falling back to a fallback solution
from older API versions.

PiperOrigin-RevId: 614612628
(cherry picked from commit 18cbbf3850)
2024-03-11 04:14:31 -07:00
tonihei
eb6f607717 Document MergingMediaSource tag contract
Issue: androidx/media#883

#minor-release

PiperOrigin-RevId: 613970048
2024-03-08 10:16:23 -08:00
tonihei
a72a23266b Document MergingMediaSource tag contract
Issue: androidx/media#883

#minor-release

PiperOrigin-RevId: 613970048
(cherry picked from commit eb6f607717)
2024-03-08 10:11:55 -08:00
tofunmi
a975c75748 SpeedChangingAudioProcessor: fix outputTime calculation
minor fix for arithmetic error in calculated added in f4c60c52b9 (speed is outputTime (change in y) divided by inputTime (change in x), this calculation is inverted in code).

Changed test to cover the case.

PiperOrigin-RevId: 613966027
2024-03-08 10:01:55 -08:00
ibaker
4bca1ac47b Add opt-in flag for the MIDI module for apps with a local dependency
PiperOrigin-RevId: 613938538
2024-03-08 08:17:02 -08:00
ibaker
4db96acee6 Add opt-in flag for the MIDI module for apps with a local dependency
PiperOrigin-RevId: 613938538
(cherry picked from commit 4bca1ac47b)
2024-03-08 08:13:55 -08:00
claincly
16ef146482 Allow playing mixed input types.
These input types include images, video without audio, and video with audio.
While playing these inputs, the video frame presentation is always synced with
audio.

PiperOrigin-RevId: 613921719
2024-03-08 07:02:51 -08:00
ibaker
f9032a5893 Add checkNotNull(uri) to DataSpec constructor
This check is already present in `DataSpec.Builder.build()` but there
are many public constructors which bypass the builder (only some of
which are deprecated), so this adds an additional check.

PiperOrigin-RevId: 613908358
2024-03-08 05:59:10 -08:00
tofunmi
f4c60c52b9 Calculate outputTime based on inputTime and audio speed change
PiperOrigin-RevId: 613894863
2024-03-08 04:47:12 -08:00
ibaker
7f5b1a98e9 Use Guava's toByteArray & fromByteArray methods where possible
Also remove intermediate object allocations in
`Util.toByteArray(int...)`.

`Util.toByteArray(InputStream)` is kept (but deprecated) because it's
been part of the library for a while and might be in use by some apps.
The others are much newer, so the chance of usages outside the library
is very low, so we just remove them directly.

PiperOrigin-RevId: 613878453
2024-03-08 03:27:29 -08:00
christosts
9f9d955f0d Preview clipped media in composition preview
PiperOrigin-RevId: 613609878
2024-03-07 09:32:11 -08:00
ibaker
5b48ef4e53 Add tests for Util.toByteArray
The implementation of these methods is changed in a follow-up CL, and
these tests help to ensure nothing breaks.

This doesn't include tests for `toByteArray(InputStream)` or
`toByteArray(int)` because these implementations are fully replaced by
Guava equivalents in a follow-up CL.

PiperOrigin-RevId: 613581845
2024-03-07 07:51:04 -08:00
ibaker
ab8b77a6d3 Use try-with-resources for input and output streams in TestUtil
Many of these streams were previously never closed.

PiperOrigin-RevId: 613580471
2024-03-07 07:47:59 -08:00
claincly
0f72126c20 Add getLastTimestampUs() method
PiperOrigin-RevId: 613579674
2024-03-07 07:44:58 -08:00
ibaker
914874566e Remove unused TestUtil.getBitmap method
PiperOrigin-RevId: 613579444
2024-03-07 07:41:14 -08:00
ibaker
0ff80d7da0 Statically import Assertions methods in FakeExoMediaDrm
PiperOrigin-RevId: 613578959
2024-03-07 07:37:50 -08:00
ibaker
a604600126 Add workarounds for NoSuchMethodError from DRM framework exceptions
Issue: androidx/media#1145

#minor-release

PiperOrigin-RevId: 613573868
2024-03-07 07:16:28 -08:00
ibaker
e55621496c Add workarounds for NoSuchMethodError from DRM framework exceptions
Issue: androidx/media#1145

PiperOrigin-RevId: 613573868
(cherry picked from commit a604600126)
2024-03-07 07:13:01 -08:00
kimvde
f02dc8e528 Implement AudioGraphInput.flush
PiperOrigin-RevId: 613563855
2024-03-07 06:33:02 -08:00
ibaker
7cffae9cd0 Apply common_library_config in test_session_current/build.gradle
This is the only `build.gradle` file that currently doesn't apply this
config, and it seems to lead to desugaring errors when apps depend on
the library locally.

PiperOrigin-RevId: 613559535
2024-03-07 06:14:25 -08:00
tofunmi
5b7774fcaf Composition: clarify javadoc to setTransmuxAudio\Video
Document that assoicated effects are ignored if these setters are set

PiperOrigin-RevId: 613518167
2024-03-07 02:58:30 -08:00
tofunmi
2dc2e5daf1 Composition: clarify javadoc to setTransmuxAudio\Video
Document that assoicated effects are ignored if these setters are set

PiperOrigin-RevId: 613518167
(cherry picked from commit 5b7774fcaf)
2024-03-07 02:55:30 -08:00
ibaker
afacf2cdb7 Set Format.frameRate for single-frame MP4 tracks
Issue: androidx/media#1051
PiperOrigin-RevId: 613516802
2024-03-07 02:53:05 -08:00
ibaker
41771d7fa3 Set Format.frameRate for single-frame MP4 tracks
Issue: androidx/media#1051
PiperOrigin-RevId: 613516802
(cherry picked from commit afacf2cdb7)
2024-03-07 02:49:59 -08:00
michaelkatz
71bfdd1bce Start early-enabled renderers only after advancing the playing period
Renderers may be enabled for subsequent media items as soon as the current media item's renderer's isEnded() returns true. When a renderer is being enabled and the player is 'playing', that renderer is also started. When playing a mixed playlist of images and content with audio & video, the player may skip some image items because the early-starting of the audio renderer causes a clock update.

A solution is to only start the "early-enabled" renderers at the point of media transition and add a condition on DefaultMediaClock to use the standalone clock when reading-ahead and the renderer clock source is not in a started state.

Issue: androidx/media#1017
PiperOrigin-RevId: 613231227
(cherry picked from commit 638b2a3c86)
2024-04-05 13:05:36 +00:00
michaelkatz
638b2a3c86 Start early-enabled renderers only after advancing the playing period
Renderers may be enabled for subsequent media items as soon as the current media item's renderer's isEnded() returns true. When a renderer is being enabled and the player is 'playing', that renderer is also started. When playing a mixed playlist of images and content with audio & video, the player may skip some image items because the early-starting of the audio renderer causes a clock update.

A solution is to only start the "early-enabled" renderers at the point of media transition and add a condition on DefaultMediaClock to use the standalone clock when reading-ahead and the renderer clock source is not in a started state.

Issue: androidx/media#1017
PiperOrigin-RevId: 613231227
2024-03-06 08:50:42 -08:00
bachinger
a0a40871b5 Pass player ID to methods of LoadControl
The old methods are deprecated and are called from the new
method for backwards compatibility of custom implementations.

'DefaultLoadControl' is unchanged, but `ExoPlayerImplInternal`
already calls the new methods passing in the `PlayerId`,

PiperOrigin-RevId: 613197190
2024-03-06 06:48:02 -08:00
andrewlewis
a90a7049e8 Fix typo
PiperOrigin-RevId: 613156951
2024-03-06 03:51:11 -08:00
andrewlewis
3fdd3bdb7a Fix typo
PiperOrigin-RevId: 613156951
(cherry picked from commit a90a7049e8)
2024-03-06 03:47:22 -08:00
ibaker
b6cb9c1b90 Fix some invalid javadoc references caught by a new JDK version
PiperOrigin-RevId: 612808322
(cherry picked from commit 3a43bd7687)
2024-04-02 18:43:29 +00:00
tonihei
672d149a73 Remove invalid command comparison
The removed check searched for a player command inside a list of
session commands, which is not allowed by the IntDef definition
and only worked because both types map to a Java int.

PiperOrigin-RevId: 612758442
(cherry picked from commit c79ac5ba21)
2024-04-02 18:36:27 +00:00
Copybara-Service
e28d772423 Merge pull request #1025 from v-novaltd:dsparano-exo209
PiperOrigin-RevId: 612485043
(cherry picked from commit bbdaf2b092)
2024-04-02 18:36:27 +00:00
tianyifeng
cf9ff4de45 Avoid position jumping back when controller replaces the current item
When the controller replaces the current item, the masking position will be changed to the default position of the new item for a short while, before the correct position comes from the session. This will interrupt the current position fetched from the controller when the playback doesn't interrupted by the item replacing.

Issue: androidx/media#951

PiperOrigin-RevId: 611417539
(cherry picked from commit 1bdc58de0b)
2024-04-02 18:36:22 +00:00
ibaker
1d2116c53a Add fps-awareness to DefaultTrackSelector
This change aims to prioritise tracks that have a 'smooth enough for
video' frame rate, without always selecting the track with the highest
frame rate.

In particular MP4 files extracted from motion photos sometimes have two
HEVC tracks, with the higher-res one having a very low frame rate (not
intended for use in video playback). Before this change
`DefaultTrackSelector` would pick the low-fps, high-res track.

This change adds a somewhat arbitrary 10fps threshold for "smooth video
playback", meaning any tracks above this threshold are selected in
preference to tracks below it. Within the tracks above the threshold
other attributes are used to select the preferred track. We deliberately
don't pick the highest-fps track (over pixel count and bitrate), because
most users would prefer to see a 30fps 4k track over a 60fps 720p track.

This change also includes a test MP4 file, extracted from the existing
`jpeg/pixel-motion-photo-2-hevc-tracks.jpg` file by logging
`mp4StartPosition` in
[`MotionPhotoDescription.getMotionPhotoMetadata`](b930b40a16/libraries/extractor/src/main/java/androidx/media3/extractor/jpeg/MotionPhotoDescription.java (L123))
and then using `dd`:

```
mp4StartPosition=2603594

$ dd if=jpeg/pixel-motion-photo-2-hevc-tracks.jpg \
    of=mp4/pixel-motion-photo-2-hevc-tracks.mp4 \
    bs=1 \
    skip=2603594
```

----

This solution is in addition to the `JpegMotionPhotoExtractor` change
made specifically for these two-track motion photos in
5266c71b3a.
We will keep both changes, even though that change is not strictly
needed after this one, because adding the role flags helps to
communicate more clearly the intended usage of these tracks. This
change to consider FPS seems like a generally useful improvement to
`DefaultTrackSelector`, since it seems unlikely we would prefer a 5fps
video track over a 30fps one.

Issue: androidx/media#1051
PiperOrigin-RevId: 611015459
(cherry picked from commit c7e00b12b4)
2024-04-02 18:34:46 +00:00
michaelkatz
3521ccda9b Fallback to legacy sizerate check if CDD H264 PerfPoint check fails
Some devices supporting Performance Points for decoder coverage are missing coverage over the CDD requirements for H264. For these cases ExoPlayer should fall back to legacy resolution and frame rate support checks. If there is a stream evaluated as a PerformancePointCoverageResult of COVERAGE_RESULT_NO, then ExoPlayer checks for coverage of the 720p H264 CDD requirement.

Issue: google/ExoPlayer#10898

Issue: androidx/media#693

Issue: androidx/media#966
PiperOrigin-RevId: 609740128
(cherry picked from commit 23a301fc5d)
2024-04-02 18:30:13 +00:00
christosts
3c10b41ffa ExoPlayerImplInternal.releaseInternal(): unblock the app thread
This change makes ExoPlayerImplInternal.releaseInternal() unblock the
app thread if a runtime exception is thrown while releasing components
from the playback thread.

Before this change, if a runtime exception occurred during releasing
components in the playback thread, ExoPlayer.release() would wait for
`releaseTimeoutMs` and then raise a player error. With this change,
the player error is reported only when the playback thread is blocked
but if there is a runtime exception, the application thread is
unblocked.

The impact of this change is potentially fewer ANRs on
ExoPlayer.release() at the expense of less error reporting.

PiperOrigin-RevId: 609702549
(cherry picked from commit 0480eff6a1)
2024-04-02 18:27:25 +00:00
christosts
25e8dc5e8b ForwardingAudioSink: add override for release()
We forgot to add it when we added AudioSink.release(). The commit
includes a test that ensures ForwardingAudioSink overrides all the
methods defined in the AudioSink interface.

PiperOrigin-RevId: 609402258
(cherry picked from commit 440d2ab162)
2024-04-02 18:24:37 +00:00
michaelkatz
81e91c25f1 Use playing period TrackSelectorResult in track reselection update
If the reading period has already advanced and a track reselection procs that only affects the reading period media, then ExoPlayer may try and apply the reading period's track selection incorrectly unto the playing period. ExoPlayer should apply the playing period's track selection to the playing period instead.

PiperOrigin-RevId: 609375077
(cherry picked from commit 4192924622)
2024-04-02 18:24:37 +00:00
michaelkatz
ed71172ade Allow renderer retry for audio track offload initialization failure
If render error occurs due to AudioTrack initialization failure in offload mode, then ExoPlayer should allow retry as subsequent attempt will be with DefaultAudioSink disabling offload.

PiperOrigin-RevId: 609304897
(cherry picked from commit 9046f2edb6)
2024-04-02 18:24:33 +00:00
tianyifeng
2ae79959ef Fix a bug in retaining streams when preload a PreloadMediaPeriod again
The `PreloadMediaPeriod.selectTracksForPreloading` can be called for multiple times at the preloading stage (before the period is being played). For example, when the period resumes preloading. This change fix the assertion failure in `ProgressiveMediaPeriod.selectTracks` caused by the wrong implementation of `PreloadMediaPeriod.selectTracksForPreloading` when it is trying to retain the previously preloaded streams.

Also the `TrackSelectorResult` parameter is changed to a list of `ExoTrackSelection`. We should compare the selections only rather than considering the `RendererConfiguration` in the `TrackSelectorResult` to decide whether to retain the streams, as for preloading case the renderers haven't consumed the samples yet.

PiperOrigin-RevId: 609126868
(cherry picked from commit d952a06214)
2024-04-02 18:21:05 +00:00
michaelkatz
2f47151131 Allow empty information attributes in RTSP Session Description
Issue: androidx/media#1087
PiperOrigin-RevId: 608534659
(cherry picked from commit 52c1d60d39)
2024-04-02 17:08:26 +00:00
Googler
04ce83691e Fix failure to write negative PTS sample
Fixes an issue caused by no support for negative audio PTS and edit lists
in FrameworkMuxer, Android versions before 11

PiperOrigin-RevId: 607690507
(cherry picked from commit e43f96687c)
2024-04-02 16:57:22 +00:00
ibaker
b218d910ad Fix docs on playUntilStartOfMediaItem to match playUntilPosition
The behaviour and docs of `playUntilPosition` were changed in
00c7a9bcbb.

This change also affects `playUntilStartOfMediaItem` (since it delegates
to `playUntilPosition`), so the same doc change should also be made
here.

#minor-release

PiperOrigin-RevId: 607364897
(cherry picked from commit fa3212e73e)
2024-04-02 16:41:12 +00:00
claincly
396ae86fdd Fix forward for 216f3fedb8
The original change missed copying the newly added flag in `buildUpon()`, which
caused some test flakes.

PiperOrigin-RevId: 607232373
(cherry picked from commit ae0da442b1)
2024-04-02 16:41:12 +00:00
ibaker
61a3127468 Demo app: Clarify that only Widevine DRM content can be downloaded
Issue: androidx/media#1085
PiperOrigin-RevId: 606921440
(cherry picked from commit a0727fe4d7)
2024-04-02 16:41:12 +00:00
bachinger
879bcb5d99 Check whether the session activity pending intent is an activity
PiperOrigin-RevId: 606613694
(cherry picked from commit 89571c0a92)
2024-04-02 16:41:11 +00:00
tofunmi
c58adb097a Add release notes for recent transformer features
PiperOrigin-RevId: 606565385
(cherry picked from commit caf584152d)
2024-04-02 16:41:03 +00:00
claincly
5fd1f61c84 Loosen the requirement to register every input frame
VideoFrameProcessor requires every input frame to be registered before they are
rendered to its input Surface. This CL adds the option to register the input
frame only once. This is useful for camera inputs where not all input frames
come with changing FrameInfo.

PiperOrigin-RevId: 606294894
(cherry picked from commit 216f3fedb8)
2024-04-02 16:14:01 +00:00
michaelkatz
c4688fc557 Fallback to including track language name if display name is not found
Issue: androidx/media#988
PiperOrigin-RevId: 606193299
(cherry picked from commit 0b0c419c73)
2024-04-02 16:13:56 +00:00
huangdarwin
2ec19a5da5 HDR: Add color-space conversion for PQ tone-map.
Previously, we missed the BT2020->BT709 color-space conversion.

A user-visible impact of this is that red and green channels used to be
undersaturated, but now are more correctly saturated.

PiperOrigin-RevId: 605411926
(cherry picked from commit a5e47982f4)
2024-04-02 16:12:42 +00:00
tofunmi
39f26e6041 DefaultAssetLoaderFactory: Simplify file extension retrival
Change the file extension retrieval back to how it was before 5488d33da8 to reduce the change of false negatives in `isImage()`

PiperOrigin-RevId: 605281186
(cherry picked from commit 4d29d8f012)
2024-04-02 16:11:10 +00:00
huangdarwin
9825e21a71 Effect: Remove extra checkStateNotNull by reordering logic.
PiperOrigin-RevId: 603660773
(cherry picked from commit ae85ba9ee9)
2024-04-02 16:11:10 +00:00
huangdarwin
ecaff24e46 Effect: Use element instead of peek, when throwing if null.
If nullness should result in an exception, we should throw as soon as possible,
so that stack traces are easier to follow.

Did a quick scan of media3.effect+transformer and this covers all uses of
peek that immediately throw there.

PiperOrigin-RevId: 603393366
(cherry picked from commit dd7846ee1c)
2024-04-02 16:11:10 +00:00
huangdarwin
bfa492bf4f HDR: Don't assume that swapping between BT709 and BT601 needs tone-map.
VideoFrameProcessor treats BT601 and BT709 as roughly equivalent now, so we
shouldn't be making checks that assume BT709 <-> requires tone-mapping.

Also, the color transfer is a better determinant for tone-mapping than color range, so use just the transfer to determine if tone-mapping is required.

PiperOrigin-RevId: 603083100
(cherry picked from commit cebe6d8ba5)
2024-04-02 16:11:10 +00:00
Ian Baker
d13a0f4ec6 Merge branch 'release' into release-1.3.0 2024-03-07 09:25:30 +00:00
Googler
4d0af794df Internal changes only
Internal changes

PiperOrigin-RevId: 613155879
2024-03-06 03:44:42 -08:00
ibaker
b1b8b2e6f9 Remove some deprecated DataSpec constructors
PiperOrigin-RevId: 613137809
2024-03-06 02:26:11 -08:00
tofunmi
f8c407cfb6 TransformerInternal: pass outputformat to sampleExporter in image input
Pass firstAssetLoaderOutputFormat to videoSampleExporter for non-video use cases, so that the downstream components like the videoFrameProcessor can be set up with the right output color. Surface creation is still in the VSP so can't do this for all use cases currently.

also moves getDecoderOutputColor() to TransformerUtil, since it is used in multiple places and doesn't make sense for once to have reference to the other.

PiperOrigin-RevId: 613113958
2024-03-06 00:45:28 -08:00
andrewlewis
11b14d7594 Set profile for DV profile 10 AV1
PiperOrigin-RevId: 612918953
2024-03-05 11:53:44 -08:00
tonihei
9abe9e2a97 Refine auto-update logic of CommandButton.isEnabled
We currently update this value for controllers to match the
availability of the associated command. This however makes it
impossible to mark a button as unavailable if the command is
available. This can be refined by only setting the 'enabled'
field to false if the command is not available, not the other
way round. And we should also enable the button by default as
disabling is the unusual case not many apps will use.

In addition, this change fixes missing update logic when the
player commands changed and it adds some additional test coverage
for all these cases.

PiperOrigin-RevId: 612881016
2024-03-05 10:08:17 -08:00
tonihei
8b59888766 Add missing icon constants for repeat/shuffle off
PiperOrigin-RevId: 612858065
2024-03-05 08:56:57 -08:00
tianyifeng
5e31cd9df3 Add BasePreloadManager and DefaultPreloadManager
`BasePreloadManager` coordinates the preloading for multiple sources based on the priorities defined by their `rankingData`. Customization is possible by extending this class. Apps will implement `TargetPreloadStatusControl` to return preload manager the target preload status for a given `rankingData` of the source.

`DefaultPreloadManager` extends from the above base class and uses `PreloadMediaSource` to preload media samples of the sources into memory. It also uses an integer `rankingData` that indicates the index of an item on the UI, and the priority of the items is determined by their adjacency to the current playing item. Apps can set the index of current playing item via `DefaultPreloadManager.setCurrentPlayingIndex` when the user swiping is detected.

PiperOrigin-RevId: 612829642
2024-03-05 07:14:18 -08:00
ibaker
3a43bd7687 Fix some invalid javadoc references caught by a new JDK version
PiperOrigin-RevId: 612808322
2024-03-05 05:48:34 -08:00
Googler
e175a772db Move AudioGraph effects to configure method
Move old configure behavior to private configureMixer.
registerInput() is now required after reset().

PiperOrigin-RevId: 612795418
2024-03-05 04:46:36 -08:00
tonihei
c79ac5ba21 Remove invalid command comparison
The removed check searched for a player command inside a list of
session commands, which is not allowed by the IntDef definition
and only worked because both types map to a Java int.

PiperOrigin-RevId: 612758442
2024-03-05 02:20:18 -08:00
Copybara-Service
bbdaf2b092 Merge pull request #1025 from v-novaltd:dsparano-exo209
PiperOrigin-RevId: 612485043
2024-03-04 09:55:00 -08:00
claincly
305f24f947 Clarify ExoPlayer.setVideoEffects() javadoc
PiperOrigin-RevId: 612464321
2024-03-04 08:45:38 -08:00
Daniele Sparano
0cdae9af20 Read resolution for debug text view from VideoSize object to reflect changes from video effects 2024-03-04 14:09:54 +00:00
tofunmi
bcfad4b3b4 Move hdrMode from defaultAssetLoaderFactory constructors to create()
Plumbing hdrMode through the default asset loader factory via the constructor is problematic because it breaks API boundaries. It means there is another way to set hdrMode outside of Composition.java and TransformationRequest.java, which is error prone and cause problems if someone an app starts customizing the assetloaderfactory. It also means custom asset loaders can't receive this information without hacking around.

The introduction of the composition-level settings class makes this approach easily extensible for other settings applied on the composition level but use in an individual asset level basis (e.g. ultraHDR support).

PiperOrigin-RevId: 611466920
2024-02-29 07:41:18 -08:00
ibaker
7395c9a159 Remove deprecated CronetDataSourceFactory
PiperOrigin-RevId: 611431225
2024-02-29 04:59:35 -08:00
christosts
1355f4734d Composition preview tests with surfaces
Add abilitiy to use real surfaces in instrumentation tests
using the ActivityScenarioRule and an activity class for testing
purposes.

PiperOrigin-RevId: 611421490
2024-02-29 04:19:44 -08:00
sheenachhabra
bba45b8b35 Rename DefaultMp4Writer to BasicMp4Writer
PiperOrigin-RevId: 611421036
2024-02-29 04:16:15 -08:00
tianyifeng
1bdc58de0b Avoid position jumping back when controller replaces the current item
When the controller replaces the current item, the masking position will be changed to the default position of the new item for a short while, before the correct position comes from the session. This will interrupt the current position fetched from the controller when the playback doesn't interrupted by the item replacing.

Issue: androidx/media#951

#minor-release

PiperOrigin-RevId: 611417539
2024-02-29 04:07:17 -08:00
claincly
27d78e69d7 Clarify setVideoEffect() javadoc
PiperOrigin-RevId: 611147963
2024-02-28 10:31:42 -08:00
Googler
87c4d60c37 Allow CronetDataSource's read buffer size to be configured.
PiperOrigin-RevId: 611146397
2024-02-28 10:27:59 -08:00
sheenachhabra
6809c0a642 Change Mp4Writer to an interface
The Mp4Writer does not have any default implementation,
hence it can be an interface rather than an abstract class.

PiperOrigin-RevId: 611110415
2024-02-28 08:28:59 -08:00
Googler
08993b6fb1 Have VideoSampleExporter output orientation match input
This should enable trim optimization to work correctly in more cases.

PiperOrigin-RevId: 611096958
2024-02-28 07:40:53 -08:00
christosts
55bfe4f95c Composition preview: do not report errors on release
PiperOrigin-RevId: 611096895
2024-02-28 07:37:15 -08:00
ibaker
09ac916119 Remove DefaultTrackSelector.NO_ORDER ordering
This implementation generates lint errors because neither the `first`
nor `second` parameters are used, and that's generally
unexpected/incorrect for a `Comparator` implementation since it should
always consider both its parameters.

PiperOrigin-RevId: 611039632
2024-02-28 02:58:41 -08:00
ibaker
19cd156a8c Add Mp4ExtractorTest case for pixel-motion-photo-2-hevc-tracks.mp4
A follow-up change will add the frame rate to the single-frame track.

Issue: androidx/media#1051
PiperOrigin-RevId: 611018319
2024-02-28 01:23:01 -08:00
ibaker
c7e00b12b4 Add fps-awareness to DefaultTrackSelector
This change aims to prioritise tracks that have a 'smooth enough for
video' frame rate, without always selecting the track with the highest
frame rate.

In particular MP4 files extracted from motion photos sometimes have two
HEVC tracks, with the higher-res one having a very low frame rate (not
intended for use in video playback). Before this change
`DefaultTrackSelector` would pick the low-fps, high-res track.

This change adds a somewhat arbitrary 10fps threshold for "smooth video
playback", meaning any tracks above this threshold are selected in
preference to tracks below it. Within the tracks above the threshold
other attributes are used to select the preferred track. We deliberately
don't pick the highest-fps track (over pixel count and bitrate), because
most users would prefer to see a 30fps 4k track over a 60fps 720p track.

This change also includes a test MP4 file, extracted from the existing
`jpeg/pixel-motion-photo-2-hevc-tracks.jpg` file by logging
`mp4StartPosition` in
[`MotionPhotoDescription.getMotionPhotoMetadata`](b930b40a16/libraries/extractor/src/main/java/androidx/media3/extractor/jpeg/MotionPhotoDescription.java (L123))
and then using `dd`:

```
mp4StartPosition=2603594

$ dd if=jpeg/pixel-motion-photo-2-hevc-tracks.jpg \
    of=mp4/pixel-motion-photo-2-hevc-tracks.mp4 \
    bs=1 \
    skip=2603594
```

----

This solution is in addition to the `JpegMotionPhotoExtractor` change
made specifically for these two-track motion photos in
5266c71b3a.
We will keep both changes, even though that change is not strictly
needed after this one, because adding the role flags helps to
communicate more clearly the intended usage of these tracks. This
change to consider FPS seems like a generally useful improvement to
`DefaultTrackSelector`, since it seems unlikely we would prefer a 5fps
video track over a 30fps one.

Issue: androidx/media#1051
PiperOrigin-RevId: 611015459
2024-02-28 01:09:50 -08:00
claincly
626a8adfd8 Test effect-enabled playback
This new test is for `ExoPlayer.setVideoEffects()`. It plays the
one-second-long video, applies an overlay that prints the video frame timestamp
onto the frame, captures the output frame and compares the captured output
frame with golden.

PiperOrigin-RevId: 610781590
2024-02-27 09:44:24 -08:00
Googler
6f28eeff31 Pick max H.264 level when trim optimizing
Instead of always starting with the transcoded H.264 level, take the maximum
from transcoded and transmuxed levels

PiperOrigin-RevId: 610759438
2024-02-27 08:27:38 -08:00
Rohit Singh
1994ba991c Add release note and update comment 2024-02-27 15:59:59 +00:00
Rohit Singh
b254c4625d Format with google-java-format 2024-02-27 15:30:22 +00:00
loliball
f88c9ad68c Fixed missing skip padding issue when reading odd sized chunks from wav files. 2024-02-27 15:30:22 +00:00
Googler
c3aec4f19d Comments for AudioGraph constructor
Add /*effects=*/ at callsites of AudioGraph constructor.

PiperOrigin-RevId: 610741692
2024-02-27 07:12:53 -08:00
sheenachhabra
94e0a27a81 Add unified addMetadata() method in Mp4Muxer
PiperOrigin-RevId: 610710011
2024-02-27 04:34:45 -08:00
Googler
0e0e1c4f1a Tests for composition audio effects
Add tests for the changes to AudioGraph that support composition audio effects

PiperOrigin-RevId: 610691768
2024-02-27 03:04:20 -08:00
Googler
477ace1be9 Composition audio effects
Implement composition-level audio effects in AudioGraph.

PiperOrigin-RevId: 610689632
2024-02-27 02:54:08 -08:00
tofunmi
0480bc31a8 Rename media/bitmap out of media and rename
PiperOrigin-RevId: 610418418
2024-02-26 08:40:19 -08:00
sheenachhabra
63a8fff69e Use ByteBuffer.remaining() instead of ByteBuffer.limit() in BoxUtil
PiperOrigin-RevId: 610414628
2024-02-26 08:24:35 -08:00
huangdarwin
e98858424a Test: Expand GL tone-map pixel difference threshold.
PiperOrigin-RevId: 610374358
2024-02-26 05:13:17 -08:00
michaelkatz
a45e734bb0 Create audio offload failure recovery playback tests
These audio offload failure recovery tests model the DefaultAudioSink failing at audio track init and write operations in offload mode. Playback should recover and try again as DefaultAudioSink will disable offload mode.

PiperOrigin-RevId: 610372935
2024-02-26 05:06:04 -08:00
sheenachhabra
99e7156561 Update media3 version for 1.3.0 stable release
PiperOrigin-RevId: 609745599
(cherry picked from commit 9be7a7ab7f)
2024-02-26 12:15:21 +00:00
sheenachhabra
c6a6b81d96 Update release notes section for 1.3.0 stable release
PiperOrigin-RevId: 609407248
(cherry picked from commit 82065e699a)
2024-02-26 12:15:05 +00:00
sheenachhabra
a5f3db4cfe Fix java doc for setAudioProcessors and setVideoEffects method
PiperOrigin-RevId: 609778651
2024-02-23 11:05:12 -08:00
sheenachhabra
9be7a7ab7f Update media3 version for 1.3.0 stable release
PiperOrigin-RevId: 609745599
2024-02-23 09:10:23 -08:00
tofunmi
5a892509f7 remove media/bitmap/input_images
move the images into the respective places in the file extension directory so they file the pre-existing structure

PiperOrigin-RevId: 609744673
2024-02-23 09:07:03 -08:00
michaelkatz
23a301fc5d Fallback to legacy sizerate check if CDD H264 PerfPoint check fails
Some devices supporting Performance Points for decoder coverage are missing coverage over the CDD requirements for H264. For these cases ExoPlayer should fall back to legacy resolution and frame rate support checks. If there is a stream evaluated as a PerformancePointCoverageResult of COVERAGE_RESULT_NO, then ExoPlayer checks for coverage of the 720p H264 CDD requirement.

Issue: google/ExoPlayer#10898

Issue: androidx/media#693

Issue: androidx/media#966
PiperOrigin-RevId: 609740128
2024-02-23 08:48:09 -08:00
sheenachhabra
284d17cb13 Add release reason argument in the MuxerWrapper.release() method
Also called `muxer.release()` in other tests where it is
appropriate.

PiperOrigin-RevId: 609736956
2024-02-23 08:34:04 -08:00
claincly
68a78b9218 When effects are enabled, opportunistally render to VFP
Even when there's no display surface, MCVR can render frames to VFP, becuase by
the time the frame is processed:

- If there's still no surface, VFP will drop the frame;
- If there's surface, the processed frame would be rendered.

In short, placeholder surface is not needed in effect enabled playback. FWIW,
it is used to swallow frames directly from MediaCodec when there's no output
surface.

PiperOrigin-RevId: 609705222
2024-02-23 06:07:54 -08:00
christosts
0480eff6a1 ExoPlayerImplInternal.releaseInternal(): unblock the app thread
This change makes ExoPlayerImplInternal.releaseInternal() unblock the
app thread if a runtime exception is thrown while releasing components
from the playback thread.

Before this change, if a runtime exception occurred during releasing
components in the playback thread, ExoPlayer.release() would wait for
`releaseTimeoutMs` and then raise a player error. With this change,
the player error is reported only when the playback thread is blocked
but if there is a runtime exception, the application thread is
unblocked.

The impact of this change is potentially fewer ANRs on
ExoPlayer.release() at the expense of less error reporting.

PiperOrigin-RevId: 609702549
2024-02-23 05:54:37 -08:00
huangdarwin
601d6ed587 Update GL thread name, per package name
PiperOrigin-RevId: 609686878
2024-02-23 04:29:31 -08:00
andrewlewis
88c6877418 Slow down dizzy crop demo effect
PiperOrigin-RevId: 609667000
2024-02-23 02:54:43 -08:00
huangdarwin
e4cf72db11 Test: Use TestName testId in TransformerSequenceEffectTest.
Some testcases that got through 0d1b35477d as they were submitted as that CL was in-progress.

PiperOrigin-RevId: 609659607
2024-02-23 02:17:59 -08:00
sheenachhabra
fd8f45b38e Add MdtaMetadataEntry constructor with default locale indicator
PiperOrigin-RevId: 609427529
2024-02-22 10:55:50 -08:00
sheenachhabra
82065e699a Update release notes section for 1.3.0 stable release
PiperOrigin-RevId: 609407248
2024-02-22 10:01:30 -08:00
christosts
440d2ab162 ForwardingAudioSink: add override for release()
We forgot to add it when we added AudioSink.release(). The commit
includes a test that ensures ForwardingAudioSink overrides all the
methods defined in the AudioSink interface.

PiperOrigin-RevId: 609402258
2024-02-22 09:59:15 -08:00
michaelkatz
4192924622 Use playing period TrackSelectorResult in track reselection update
If the reading period has already advanced and a track reselection procs that only affects the reading period media, then ExoPlayer may try and apply the reading period's track selection incorrectly unto the playing period. ExoPlayer should apply the playing period's track selection to the playing period instead.

PiperOrigin-RevId: 609375077
2024-02-22 08:08:18 -08:00
huangdarwin
0d1b35477d Test: Use testId throughout media3 tests.
No more instances of this codesearch query after this CL in non-parameterized
tests:
`String\ testId\ \=\ \" f:media3`
PiperOrigin-RevId: 609364413
2024-02-22 07:28:55 -08:00
ibaker
d1ae9ffc52 Add more details about why Extractor.sniff returned false
PiperOrigin-RevId: 609335656
2024-02-22 05:20:16 -08:00
sheenachhabra
41886434ad Remove duplicate Mp4Location class
PiperOrigin-RevId: 609313551
2024-02-22 03:40:35 -08:00
michaelkatz
9046f2edb6 Allow renderer retry for audio track offload initialization failure
If render error occurs due to AudioTrack initialization failure in offload mode, then ExoPlayer should allow retry as subsequent attempt will be with DefaultAudioSink disabling offload.

PiperOrigin-RevId: 609304897
2024-02-22 03:00:10 -08:00
tianyifeng
d952a06214 Fix a bug in retaining streams when preload a PreloadMediaPeriod again
The `PreloadMediaPeriod.selectTracksForPreloading` can be called for multiple times at the preloading stage (before the period is being played). For example, when the period resumes preloading. This change fix the assertion failure in `ProgressiveMediaPeriod.selectTracks` caused by the wrong implementation of `PreloadMediaPeriod.selectTracksForPreloading` when it is trying to retain the previously preloaded streams.

Also the `TrackSelectorResult` parameter is changed to a list of `ExoTrackSelection`. We should compare the selections only rather than considering the `RendererConfiguration` in the `TrackSelectorResult` to decide whether to retain the streams, as for preloading case the renderers haven't consumed the samples yet.

PiperOrigin-RevId: 609126868
2024-02-21 14:41:33 -08:00
huangdarwin
fde6a32156 Transformer: Input decoder output color to VideoSampleExporter.
Previously, the track format was used in VideoSampleExporter. Now, we use a
simulated decoder output format.

As the last expected change for this bug, also adds release notes

PiperOrigin-RevId: 609080629
2024-02-21 12:15:11 -08:00
ibaker
bb5c688543 Update TestPlayerRunHelper to fail on non-fatal errors by default
Also introduce a fluent API that allows callers to ignore non-fatal
errors (while avoiding adding boolean overloads for every method).

**Most** tests want to fail on non-fatal errors (since they likely
indicate user-visible issues like codec errors etc), only tests
explicitly testing fallback in error scenarios should want to ignore
them.

Before this change there were a few `playUntilXXX` methods. These can
now all be triggered via `play(player).untilXXX`, which means
effectively every 'until' condition is available in a 'play until'
variant that calls `play` just before waiting for the condition.

PiperOrigin-RevId: 608988234
2024-02-21 07:39:07 -08:00
huangdarwin
2e9cc2784f Test: Add sequence effect test with bt601 image and bt709 video.
The lack of this test was the *real* root cause for our partner's regression :P

PiperOrigin-RevId: 608956530
2024-02-21 05:22:11 -08:00
Googler
dca7bae416 Allow mismatching H.264/AVC level for trimming or resuming
MediaCodec docs already allude to potentially mismatching H.264 level
between container and bitstream. Relax the initialization data check to
reflect this.

PiperOrigin-RevId: 608942322
2024-02-21 04:20:50 -08:00
sheenachhabra
a82d7e7098 Improve retrieveTrackFormat() java doc and remove catch block
PiperOrigin-RevId: 608939192
2024-02-21 04:11:39 -08:00
sheenachhabra
ee0eac7e31 Fix nit issues in 1.3.0-rc01 release notes
PiperOrigin-RevId: 608580903
(cherry picked from commit ebcb4e8b21)
2024-02-20 16:31:17 +00:00
tofunmi
7a632a43ba Move bitmap decoding into datasource util
PiperOrigin-RevId: 608588505
2024-02-20 06:57:02 -08:00
sheenachhabra
ebcb4e8b21 Fix nit issues in 1.3.0-rc01 release notes
PiperOrigin-RevId: 608580903
2024-02-20 06:22:14 -08:00
tonihei
711d24a12f Clarify purpose of omitting zero duration clipped audio samples
When applying edit lists, we need to output the last partial samples
to have all the necessary data needed for rendering.

The only case where we can omit the sample is for zero duration
audio data that has no additional information.

The current comment and variable name doesn't make this very clear
and this change improves the naming and the comment.

PiperOrigin-RevId: 608579746
2024-02-20 06:17:28 -08:00
christosts
8dd6590fe9 Use application context in CompositingVideoSinkProvider.Builder
PiperOrigin-RevId: 608572065
2024-02-20 05:45:44 -08:00
sheenachhabra
063fbc7b84 Remove FileUtil.java class
PiperOrigin-RevId: 608556329
2024-02-20 04:35:49 -08:00
tofunmi
f1c21f6c07 Rollback of 5a3f18f837
PiperOrigin-RevId: 608551290
2024-02-20 04:09:26 -08:00
michaelkatz
52c1d60d39 Allow empty information attributes in RTSP Session Description
Issue: androidx/media#1087
PiperOrigin-RevId: 608534659
2024-02-20 02:47:40 -08:00
huangdarwin
04bdf3e814 Test: Use Format.colorInfo instead of hardcoded format.
PiperOrigin-RevId: 608399485
2024-02-19 14:21:36 -08:00
huangdarwin
9e352d5c27 Test: Add sequence effect test with bt601.
PiperOrigin-RevId: 608377195
2024-02-19 11:53:09 -08:00
tofunmi
e6facd6a7e Fix: make VFP test runner propagate the right exceptions
PiperOrigin-RevId: 608337651
2024-02-19 07:57:33 -08:00
sheenachhabra
d097fe11d0 Add E2E test for Mp4Muxer to verify overall box structure
There is no super test which covers whole MP4 structure.
In all the E2E test, it verified against `ExtractorOutput` which
would remain same if there are changes in the box structure.

PiperOrigin-RevId: 608310006
2024-02-19 05:31:34 -08:00
sheenachhabra
2cd0cb30cd Use default asset loader factory for remuxing video step
PiperOrigin-RevId: 608308406
2024-02-19 05:22:07 -08:00
tofunmi
5a3f18f837 Make DataSourceBitmapLoader non-final
PiperOrigin-RevId: 608275835
2024-02-19 02:52:58 -08:00
ibaker
3bbb0e7453 Add documented support for android.resource://package/id URIs
These were previously somewhat supported, but the `package` part was
never read (so it only worked if it was either absent or the same as the
current application's package). This change parses and uses the
`package` part.

This partially reverts 35121a2d3d.

This is hard to test for the same reasons as 88f554c74b:

> This is hard to test because to do so robustly requires being able to guaranteed that another test APK will be installed with a known raw resource inside it.

PiperOrigin-RevId: 608270463
2024-02-19 02:28:39 -08:00
Googler
e43f96687c Fix failure to write negative PTS sample
Fixes an issue caused by no support for negative audio PTS and edit lists
in FrameworkMuxer, Android versions before 11

PiperOrigin-RevId: 607690507
2024-02-16 08:03:38 -08:00
ibaker
c872af4bc0 Consolidate requiresSecureDecoder logic in ExoMediaDrm
This change:
1. Updates the implementation of
   `FrameworkMediaDrm.requiresSecureDecoder` to include the
   'force allow insecure decoder' workaround logic.
2. Removes the 'force allow insecure decoder' logic from MCR
3. Removes the `requiresSecureDecoder` field from MCR (it can just
   be a local derived from `codecDrmSession` now).

PiperOrigin-RevId: 607664186
2024-02-16 05:57:50 -08:00
ibaker
fa3212e73e Fix docs on playUntilStartOfMediaItem to match playUntilPosition
The behaviour and docs of `playUntilPosition` were changed in
00c7a9bcbb.

This change also affects `playUntilStartOfMediaItem` (since it delegates
to `playUntilPosition`), so the same doc change should also be made
here.

#minor-release

PiperOrigin-RevId: 607364897
2024-02-15 09:49:51 -08:00
Copybara-Service
fb7438378d Merge pull request #983 from MGaetan89:min_api_19
PiperOrigin-RevId: 607319987
2024-02-15 07:00:17 -08:00
bachinger
4777d62d31 Rollback of 8e2869278c
PiperOrigin-RevId: 607264513
2024-02-15 02:35:12 -08:00
claincly
ae0da442b1 Fix forward for 216f3fedb8
The original change missed copying the newly added flag in `buildUpon()`, which
caused some test flakes.

PiperOrigin-RevId: 607232373
2024-02-15 00:05:10 -08:00
asinclair
8e2869278c Internal Cleanup
PiperOrigin-RevId: 607117264
2024-02-14 15:06:10 -08:00
ibaker
a0727fe4d7 Demo app: Clarify that only Widevine DRM content can be downloaded
Issue: androidx/media#1085
PiperOrigin-RevId: 606921440
2024-02-14 03:28:57 -08:00
Ian Baker
b82f341007 In-line DashTestRunner.MediaDrmBuilder 2024-02-13 17:11:03 +00:00
bachinger
89571c0a92 Check whether the session activity pending intent is an activity
PiperOrigin-RevId: 606613694
2024-02-13 07:28:31 -08:00
Ian Baker
868d2fedcb Update api.txt 2024-02-13 15:11:24 +00:00
Ian Baker
e24febf1e2 Small clean-ups and added @InlineMe annotation 2024-02-13 14:48:15 +00:00
tofunmi
caf584152d Add release notes for recent transformer features
PiperOrigin-RevId: 606565385
2024-02-13 12:23:50 +00:00
Ian Baker
1bf3101269 Remove V19 from AudioTimestampPoller.AudioTimestampV19 2024-02-13 10:26:20 +00:00
Ian Baker
205c8734cc In-line more V19 methods in TrackSelectionParameters, AudioTimestampPoller and CaptionStyleCompat 2024-02-13 10:26:20 +00:00
Ian Baker
c4d9df970c Format with google-java-format 2024-02-13 10:26:20 +00:00
Ian Baker
c0c1c315c5 In-line GlUtil.Api18 and VideoFrameReleaseHelper.DisplayHelperV16/17
Also put back a comment in DownloadTracker that is still relevant on API 19.

Also deprecate PlaceholderSurface.newInstanceV17() in favour of just
newInstance()
2024-02-13 10:26:20 +00:00
Gaëtan Muller
d327cb4795 Code cleanup 2024-02-13 10:26:20 +00:00
Gaëtan Muller
e1ba75c871 Remove some API-dependant classes 2024-02-13 10:26:20 +00:00
Gaëtan Muller
08ab18be77 Remove unnecessary TargetApi annotation 2024-02-13 10:26:20 +00:00
Gaëtan Muller
963e517a5a Remove unnecessary RequiresApi annotation 2024-02-13 10:26:19 +00:00
Gaëtan Muller
973b717914 Remove unnecessary SDK_INT checks 2024-02-13 10:26:19 +00:00
tianyifeng
2b473831c6 Implement onInit() and onRelease() in FakeRenderer
PiperOrigin-RevId: 606301390
2024-02-12 10:57:14 -08:00
claincly
216f3fedb8 Loosen the requirement to register every input frame
VideoFrameProcessor requires every input frame to be registered before they are
rendered to its input Surface. This CL adds the option to register the input
frame only once. This is useful for camera inputs where not all input frames
come with changing FrameInfo.

PiperOrigin-RevId: 606294894
2024-02-12 10:38:42 -08:00
huangdarwin
69f651a40d HDR: Use better color test.
Our previous test video was difficult to use for testing our tone-mapping
algorithm, because it didn't have many different colors. Use a better
video for tone-map tests, by having one with more different colors

PiperOrigin-RevId: 606274843
2024-02-12 09:31:02 -08:00
huangdarwin
2594691950 Clarify speedchange javadoc to mention duration.
The speed is that value only until the next one

PiperOrigin-RevId: 606258937
2024-02-12 08:25:39 -08:00
tofunmi
1a5eb4eecd Support segment-specific speed changes in SpeedChangeEffect
PiperOrigin-RevId: 606204479
2024-02-12 04:03:23 -08:00
michaelkatz
0b0c419c73 Fallback to including track language name if display name is not found
Issue: androidx/media#988
PiperOrigin-RevId: 606193299
2024-02-12 03:07:36 -08:00
tonihei
adc23e8e8b Add icon constants to CommandButton
These allow to set the icon in a standardized way without needing
custom bitmaps or resources. For now, this is just additional
information without backwards-compatible icons or implications.

The same value gets written to the platform session via a new
extras key that can be read and set from sessions not using Media3
yet.

PiperOrigin-RevId: 605670988
2024-02-09 10:37:12 -08:00
ibaker
338aef4830 Fix transformer, effect, muxer and container API dependencies
The public APIs of these modules reference symbols in some of their
dependencies, so these should be API dependencies, not implementation:
> An API dependency is one that contains at least one type that is
> exposed in the library binary interface, often referred to as its ABI
> (Application Binary Interface).

https://docs.gradle.org/current/userguide/java_library_plugin.html#sec:java_library_recognizing_dependencies

Transformer also uses symbols from `lib-common`, but these are already
an API dep of `lib-exoplayer` so no need to duplicate that here.

PiperOrigin-RevId: 605660621
2024-02-09 10:05:54 -08:00
huangdarwin
73c9753229 HDR: Update constant name for clarity.
This matrix converts from BT2020 in RGB, not to XYZ in BT2020,
so put "bt2020" nearer to RGB.

PiperOrigin-RevId: 605654773
2024-02-09 09:45:16 -08:00
sheenachhabra
69c555be0a Move retrieveTrackFormat() method to TestUtil
TestUtil class is more appropriate for the given method.
In the next CL, the only method in FileUtil.java will be moved back
into transformer library and the FileUtil class will be removed.

PiperOrigin-RevId: 605648034
2024-02-09 09:18:14 -08:00
sheenachhabra
8a758c2ed7 Replace setModificationTime API with setTimestampData in Mp4Muxer
The new API will take both `creation time` and `modification time`.

Till now, Mp4Muxer wrote `modification time` in both
`creation time` and `modification time` field, which was
incorrect.

PiperOrigin-RevId: 605590623
2024-02-09 04:15:53 -08:00
sheenachhabra
fbf8ac37c3 Version bump to media3:1.3.0-rc01
PiperOrigin-RevId: 605573991
(cherry picked from commit a31a384393)
2024-02-09 11:39:45 +00:00
sheenachhabra
43ee291172 Update release notes for media3:1.3.0-rc01
#minor-release

PiperOrigin-RevId: 605561427
(cherry picked from commit c4605b3c90)
2024-02-09 11:34:02 +00:00
sheenachhabra
a31a384393 Version bump to media3:1.3.0-rc01
#minor-release

PiperOrigin-RevId: 605573991
2024-02-09 02:44:25 -08:00
sheenachhabra
c4605b3c90 Update release notes for media3:1.3.0-rc01
#minor-release

PiperOrigin-RevId: 605561427
2024-02-09 01:40:25 -08:00
huangdarwin
a5e47982f4 HDR: Add color-space conversion for PQ tone-map.
Previously, we missed the BT2020->BT709 color-space conversion.

A user-visible impact of this is that red and green channels used to be
undersaturated, but now are more correctly saturated.

PiperOrigin-RevId: 605411926
2024-02-08 13:33:52 -08:00
tianyifeng
38d5635818 Report the skipped silence more deterministically
Issue: androidx/media#1035
#minor-release
PiperOrigin-RevId: 605361126
(cherry picked from commit 9b0cdde7d2)
2024-02-08 19:09:41 +00:00
tianyifeng
9b0cdde7d2 Report the skipped silence more deterministically
Issue: androidx/media#1035
#minor-release
PiperOrigin-RevId: 605361126
2024-02-08 10:40:40 -08:00
tonihei
e492e37baa Move release note to the right section
#minor-release

PiperOrigin-RevId: 605310711
(cherry picked from commit e56e27e725)
2024-02-08 17:30:17 +00:00
ibaker
dbb99fef19 Rollback of 406c0a15be
PiperOrigin-RevId: 605015994
(cherry picked from commit 3a7a665d5d)
2024-02-08 17:30:17 +00:00
ibaker
1dc4377a4b Stop double-encoding CMCD query parameters
`Uri.appendQueryParameter` is documented to encode its arguments, so
calling `Uri.encode` beforehand results in double-encoding.

Issue: androidx/media#1075

#minor-release

PiperOrigin-RevId: 604995441
(cherry picked from commit 7ebfed505c)
2024-02-08 17:30:17 +00:00
tonihei
245e6231d9 Set correct track id when skipping empty tracks in Mp4Extractor
The track id must be the index in the list of published tracks
as it's used as such elsewhere. This is currently not true if we
skip an empty track as all subsequent tracks get a wrong or even
invalid id.

#minor-release

PiperOrigin-RevId: 604929178
(cherry picked from commit 5f9c96ab53)
2024-02-08 17:30:17 +00:00
bachinger
74d0f93dd4 Fix the regex used for validating custom CMCD key names
Relax the regex to only check for hyphen which is required by the specification.

Issue: androidx/media#1028
#minor-release
PiperOrigin-RevId: 604719300
(cherry picked from commit 138532e3fd)
2024-02-08 17:30:17 +00:00
tianyifeng
9f28e7d81b Improve AudioCapabilities with AudioManager API in Android 13
PiperOrigin-RevId: 604700601
(cherry picked from commit ccd603acb0)
2024-02-08 17:30:17 +00:00
ibaker
bf8b8749fe JpegMotionPhotoExtractor: Don't emit an image track with no metadata
The current implementation of `JpegMotionPhotoExtractor.sniff` returns
`true` for any image with Exif data (not just motion photos). Improving
this is tracked by b/324033919. In the meantime, when we 'extract' a
non-motion photo with `JpegMotionPhotoExtractor`, the result is
currently a single empty image track and no video track (since there's
no video, since this isn't a motion photo). This 'empty' image track
is usually used to transmit metadata about the video parts of the
image file (in the form of `MotionPhotoMetadata`), but this metadata is
also (understandably) absent for non-motion photos. Therefore there's
no need to emit this image track at all, and it's clearer to emit no
tracks at all when extracting a non-motion photo using
`JpegMotionPhotoExtractor`.

This change also removes a `TODO` that is misplaced, since there's no
image bytes being emitted here (and never was).

PiperOrigin-RevId: 604688053
(cherry picked from commit 7ae3d69e00)
2024-02-08 17:30:16 +00:00
ibaker
7721f387ca Check sampleMimeType rather than containerMimeType for images
These are often the same for image tracks, since we usually drop the
whole image file (both the container and actual encoded image bytes)
into a single sample, but there are cases where we emit a track with
`containerMimeType=image/jpeg` but **no** samples (from
`JpegMotionPhotoExtractor`, to carry some metadata about the image +
video byte offsets).

It's therefore more correct to implement the `supportsFormat` check
based on `sampleMimeType`, so that these 'empty' image tracks are not
considered 'supported' by `ImageRenderer`.

#minor-release

PiperOrigin-RevId: 604672331
(cherry picked from commit eabba49610)
2024-02-08 17:30:16 +00:00
bachinger
dc8d3eaf30 Add constructor that takes only a Context
#minor-release

PiperOrigin-RevId: 604659845
(cherry picked from commit c2273345c5)
2024-02-08 17:30:16 +00:00
tonihei
ca2779e774 Add source prefix to MergingMediaPeriod Format ids
This was already done for the TrackGroup ids in <unknown commit>,
but in some scenarios only the Format instances are known and
it's helpful to be able to identify where they came from.

Issue: androidx/media#883

#minor-release

PiperOrigin-RevId: 604644039
(cherry picked from commit f8f6d80477)
2024-02-08 17:30:16 +00:00
tonihei
a294dc9bc5 Include nullness of RequestMetadata.extras in equals method
This ensures RequestMetadata with just non-null extras is not
considered equal to RequestMetadata.EMPTY. This makes sure the
contents are bundled when a controller sets the extras in a
new MediaItem.

PiperOrigin-RevId: 604632788
(cherry picked from commit 766a15a51e)
2024-02-08 17:30:16 +00:00
ibaker
ad57b41da1 Clearly define the consistency requirements for SequenceableLoader
Add a test for this consistency in `CompositeSequenceableLoaderTest`,
and also make the
`CompositeSequenceableLoaderTest.FakeSequenceableLoader` implementation
more realistic.

#minor-release

PiperOrigin-RevId: 604604103
(cherry picked from commit db74bb9609)
2024-02-08 17:30:16 +00:00
Googler
4a952170a2 Fix Kotlin 2.0 compilation error in session demo app
Since Kotlin 2.0 the compiler became better at detecting incorrect
annotation applications. The @OptIn annotation can't be applied to an
expression, so when compiling with Kotlin 2.0 it results in an error.

PiperOrigin-RevId: 604596657
(cherry picked from commit 718cf1299b)
2024-02-08 17:30:16 +00:00
ibaker
4eea69dd46 Merge Cea608Parser back into Cea608Decoder
This reverses 27caeb8038

Due to the re-ordering of packets done in `CeaDecoder`, there's no way
to use the current implementation to correctly parse these subtitle
formats during extraction (the `SubtitleParser` interface), so we have
to keep the `SubtitleDecoder` implementations.

#minor-release

PiperOrigin-RevId: 604594837
(cherry picked from commit 25498b151b)
2024-02-08 17:30:16 +00:00
ibaker
dd2e4a5978 Merge Cea708Parser back into Cea708Decoder
This reverses 94e45eb4ad

Due to the re-ordering of packets done in `CeaDecoder`, there's no way
to use the current implementation to correctly parse these subtitle
formats during extraction (the `SubtitleParser` interface), so we have
to keep the `SubtitleDecoder` implementations.

#minor-release

PiperOrigin-RevId: 604350951
(cherry picked from commit 51b4fa2cc8)
2024-02-08 17:30:16 +00:00
tonihei
548c4ce799 Fix HlsPlaybackTest flakiness
The new test introduced in 45bd5c6f0a is flaky because we only
wait until the media is fully buffered. However, we can't fully
control how much of this data is initially read by the Robolectric
codec and thus the output dump files (containing these codec
interactions) are flaky.

This can be fixed by fully playing the media once and then seeking
back instead.

#minor-release

PiperOrigin-RevId: 603324068
(cherry picked from commit e3e57c9b99)
2024-02-08 17:30:16 +00:00
michaelkatz
7758e422aa Render last image despite not receiving EoS
If seeking between last image sample and end of the file where the current stream is not final, then EoS sample will not be provided to `ImageRenderer`. ImageRenderer must still produce the last image sample.

PiperOrigin-RevId: 603312090
(cherry picked from commit 62c7ee0fb0)
2024-02-08 17:30:16 +00:00
Copybara-Service
127d0b5f3c Merge pull request #1011 from cedricxperi:dts-lbr-hls-bitrate-unknown-fix
PiperOrigin-RevId: 603302863
(cherry picked from commit f85860c041)
2024-02-08 17:30:16 +00:00
Copybara-Service
ad519e2e7e Merge pull request #1015 from kamaroyl:feat/PsshVersion1
PiperOrigin-RevId: 603016920
(cherry picked from commit dfcc2cb41d)
2024-02-08 17:30:16 +00:00
Copybara-Service
3d87578779 Merge pull request #1031 from garethfenn:hlschunkseek
PiperOrigin-RevId: 603008793
(cherry picked from commit 45bd5c6f0a)
2024-02-08 17:30:04 +00:00
claincly
a18d96c320 Fix blank video when switching on/off screen
This happens when using `ExoPlayer.setVideoEffects()`.

This CL also fixes the first frame not rendered problem, originally solved in
7e65cce967, but rolled back in 5056dfaa2b because the solution introduces
the flash that is observed in b/292111083.

Before media3 1.1 release, the output size of `VideoFrameProcessor` is not
reported to the app. This was changed later after introducing
`CompositingVideoSinkProvider`, where the video size after processing **is**
reported to the app. After this CL, the size is again, not reported.

PiperOrigin-RevId: 602345087
(cherry picked from commit dcae49a561)
2024-02-08 17:29:13 +00:00
tonihei
dfe47219f9 Update skip silence algorithm
The updated algorithm has two main improvements:
 - The silence padding is not constant but a ratio of the original
   silence (up to a defined max) to more naturally represent the
   original gaps.
 - The silence is not instantly going to zero, but uses a ramp down
   and up for a smooth volume transition and also retains a small
   percentage of the original noise for more natural "silences" that
   still contain some background noise.

#minor-release

Issue: google/ExoPlayer#7423
PiperOrigin-RevId: 602322442
(cherry picked from commit bb533332f4)
2024-02-08 17:29:12 +00:00
jbibik
826f20dbbd Remove a redundant TODO in Util
PiperOrigin-RevId: 601820851
(cherry picked from commit eb3173aa90)
2024-02-08 17:29:12 +00:00
tonihei
4560611bd0 Remove misleading @CanIgnoreReturnValue
The return value of onConfigure must not be ignored as it specifies
the output format of the processor, which may be different from the
input format.

#minor-release

PiperOrigin-RevId: 601799440
(cherry picked from commit 2fc5590e7a)
2024-02-08 17:29:12 +00:00
tonihei
4a7442ef3a Replace or suppress deprecated usages
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
(cherry picked from commit ed5b7004b4)
2024-02-08 17:29:12 +00:00
ibaker
0886da450d Add a comment to suggest keeping JUnit version in sync with the Android
source tree - to make importing GTS tests easier.

PiperOrigin-RevId: 601725811
(cherry picked from commit 373822ce45)
2024-02-08 17:29:12 +00:00
Googler
ddca0116b2 Update IMA README to include link to supported platforms
PiperOrigin-RevId: 601720412
(cherry picked from commit 807d98a3d6)
2024-02-08 17:29:12 +00:00
tonihei
e56e27e725 Move release note to the right section
#minor-release

PiperOrigin-RevId: 605310711
2024-02-08 07:31:57 -08:00
tofunmi
4d29d8f012 DefaultAssetLoaderFactory: Simplify file extension retrival
Change the file extension retrieval back to how it was before 5488d33da8 to reduce the change of false negatives in `isImage()`

PiperOrigin-RevId: 605281186
2024-02-08 05:01:03 -08:00
ibaker
3a7a665d5d Rollback of 406c0a15be
PiperOrigin-RevId: 605015994
2024-02-07 09:56:59 -08:00
ibaker
7ebfed505c Stop double-encoding CMCD query parameters
`Uri.appendQueryParameter` is documented to encode its arguments, so
calling `Uri.encode` beforehand results in double-encoding.

Issue: androidx/media#1075

#minor-release

PiperOrigin-RevId: 604995441
2024-02-07 08:44:33 -08:00
tonihei
5f9c96ab53 Set correct track id when skipping empty tracks in Mp4Extractor
The track id must be the index in the list of published tracks
as it's used as such elsewhere. This is currently not true if we
skip an empty track as all subsequent tracks get a wrong or even
invalid id.

#minor-release

PiperOrigin-RevId: 604929178
2024-02-07 03:39:59 -08:00
tofunmi
2cb9d9b383 Export: Add methods to determine the conversion process of a track
PiperOrigin-RevId: 604754827
2024-02-06 13:58:14 -08:00
bachinger
138532e3fd Fix the regex used for validating custom CMCD key names
Relax the regex to only check for hyphen which is required by the specification.

Issue: androidx/media#1028
#minor-release
PiperOrigin-RevId: 604719300
2024-02-06 11:59:20 -08:00
tianyifeng
ccd603acb0 Improve AudioCapabilities with AudioManager API in Android 13
PiperOrigin-RevId: 604700601
2024-02-06 11:57:09 -08:00
sheenachhabra
20053dcdc6 Test output file's metadata using MetadataRetriever
Earlier implementation compared the whole file against a golden
data. The new implementation compares only the metadata being tested.
This will avoid updating the golden data when any unrelated change
(unrelated to scenario being tested) is made.

Added a separate test to compare the whole output file against a golden data.

PiperOrigin-RevId: 604692985
2024-02-06 10:36:47 -08:00
ibaker
7ae3d69e00 JpegMotionPhotoExtractor: Don't emit an image track with no metadata
The current implementation of `JpegMotionPhotoExtractor.sniff` returns
`true` for any image with Exif data (not just motion photos). Improving
this is tracked by b/324033919. In the meantime, when we 'extract' a
non-motion photo with `JpegMotionPhotoExtractor`, the result is
currently a single empty image track and no video track (since there's
no video, since this isn't a motion photo). This 'empty' image track
is usually used to transmit metadata about the video parts of the
image file (in the form of `MotionPhotoMetadata`), but this metadata is
also (understandably) absent for non-motion photos. Therefore there's
no need to emit this image track at all, and it's clearer to emit no
tracks at all when extracting a non-motion photo using
`JpegMotionPhotoExtractor`.

This change also removes a `TODO` that is misplaced, since there's no
image bytes being emitted here (and never was).

PiperOrigin-RevId: 604688053
2024-02-06 10:22:18 -08:00
samrobinson
c768e60bf2 Clearer testing of isEnded state of AudioGraphInput.
PiperOrigin-RevId: 604680924
2024-02-06 10:00:24 -08:00
ibaker
eabba49610 Check sampleMimeType rather than containerMimeType for images
These are often the same for image tracks, since we usually drop the
whole image file (both the container and actual encoded image bytes)
into a single sample, but there are cases where we emit a track with
`containerMimeType=image/jpeg` but **no** samples (from
`JpegMotionPhotoExtractor`, to carry some metadata about the image +
video byte offsets).

It's therefore more correct to implement the `supportsFormat` check
based on `sampleMimeType`, so that these 'empty' image tracks are not
considered 'supported' by `ImageRenderer`.

#minor-release

PiperOrigin-RevId: 604672331
2024-02-06 09:31:37 -08:00
bachinger
c2273345c5 Add constructor that takes only a Context
#minor-release

PiperOrigin-RevId: 604659845
2024-02-06 08:47:03 -08:00
tonihei
f8f6d80477 Add source prefix to MergingMediaPeriod Format ids
This was already done for the TrackGroup ids in <unknown commit>,
but in some scenarios only the Format instances are known and
it's helpful to be able to identify where they came from.

Issue: androidx/media#883

#minor-release

PiperOrigin-RevId: 604644039
2024-02-06 07:45:42 -08:00
tonihei
766a15a51e Include nullness of RequestMetadata.extras in equals method
This ensures RequestMetadata with just non-null extras is not
considered equal to RequestMetadata.EMPTY. This makes sure the
contents are bundled when a controller sets the extras in a
new MediaItem.

PiperOrigin-RevId: 604632788
2024-02-06 06:58:51 -08:00
ibaker
db74bb9609 Clearly define the consistency requirements for SequenceableLoader
Add a test for this consistency in `CompositeSequenceableLoaderTest`,
and also make the
`CompositeSequenceableLoaderTest.FakeSequenceableLoader` implementation
more realistic.

#minor-release

PiperOrigin-RevId: 604604103
2024-02-06 04:25:14 -08:00
andrewlewis
e683b9a506 Expand encoding operating rate workaround
PiperOrigin-RevId: 604602441
2024-02-06 04:15:49 -08:00
Googler
718cf1299b Fix Kotlin 2.0 compilation error in session demo app
Since Kotlin 2.0 the compiler became better at detecting incorrect
annotation applications. The @OptIn annotation can't be applied to an
expression, so when compiling with Kotlin 2.0 it results in an error.

PiperOrigin-RevId: 604596657
2024-02-06 03:47:20 -08:00
ibaker
25498b151b Merge Cea608Parser back into Cea608Decoder
This reverses 27caeb8038

Due to the re-ordering of packets done in `CeaDecoder`, there's no way
to use the current implementation to correctly parse these subtitle
formats during extraction (the `SubtitleParser` interface), so we have
to keep the `SubtitleDecoder` implementations.

#minor-release

PiperOrigin-RevId: 604594837
2024-02-06 03:36:23 -08:00
ibaker
51b4fa2cc8 Merge Cea708Parser back into Cea708Decoder
This reverses 94e45eb4ad

Due to the re-ordering of packets done in `CeaDecoder`, there's no way
to use the current implementation to correctly parse these subtitle
formats during extraction (the `SubtitleParser` interface), so we have
to keep the `SubtitleDecoder` implementations.

#minor-release

PiperOrigin-RevId: 604350951
2024-02-05 10:03:32 -08:00
huangdarwin
e4145a9953 Update javadoc to be the right DrawableOverlay class.
PiperOrigin-RevId: 604337168
2024-02-05 09:13:40 -08:00
tofunmi
4da576f05f Support transmux when both no op effects and regular rotations are set
PiperOrigin-RevId: 604319412
2024-02-05 08:05:32 -08:00
samrobinson
f8352580cb Add AudioGraphInput tests around getOutput behaviour.
PiperOrigin-RevId: 604297126
2024-02-05 06:18:46 -08:00
tofunmi
49c6d25106 Move setting the muxerWrapper rotation out of shouldTranscodeVideo()
Before supporting transmuxing when both no op effects and regular rotations are set, move setting the muxerWrapper rotation out of shouldTranscodeVideo() to ensure the muxerWrapper rotation is only set at the appropriate times.

This cl also ensures the state between the muxerWrapper and the list of video effects is consistent by clearing the list of videoEffects in trim optimization. If trim optimisation is being applied, then EditedMediItem.effects.videoEffects only contains no-op effects or regular rotations that get be applied in the muxer wrapper. Therefore, we should clear the list of video effects to ensure that no effect gets applied twice.

PiperOrigin-RevId: 604292052
2024-02-05 05:54:11 -08:00
samrobinson
029071a342 Improve checks around AudioGraphInput configuring with requested format
Also adds extra AudioGraphInputTest cases.

PiperOrigin-RevId: 603690041
2024-02-02 08:13:54 -08:00
huangdarwin
1bd04cb5d9 Add support for GlProgram GL_FLOAT_VEC4.
https://github.com/androidx/media/issues/1039

PiperOrigin-RevId: 603684630
2024-02-02 07:46:04 -08:00
tofunmi
c79f950d26 ultra HDR: send gainmap downstream if HDR output requested
removing the useHdr parameter from queueInputBitmap() it suggests we support changing between HDR and SDR within a stream, which we don't support. instead, identifying whether to use HDR from the shaderprogram which is informed by the inputColorInfo when the stream is registered.

PiperOrigin-RevId: 603681736
2024-02-02 07:33:15 -08:00
tofunmi
271eb88b48 Remove texture copy from SpeedChangeShaderProgram
Introduces PassthroughShaderProgram to make the effect more efficient.

PiperOrigin-RevId: 603670438
2024-02-02 06:30:18 -08:00
huangdarwin
8b6c8fc480 Test: Remove assertions from test infra.
PiperOrigin-RevId: 603664759
2024-02-02 05:57:30 -08:00
samrobinson
2b52c2d74f Add extra documentation to AudioGraphInput.
PiperOrigin-RevId: 603663084
2024-02-02 05:47:05 -08:00
sheenachhabra
30b60f6c60 Refactor assertFileHasColorTransfer method
PiperOrigin-RevId: 603662313
2024-02-02 05:42:28 -08:00
huangdarwin
ae85ba9ee9 Effect: Remove extra checkStateNotNull by reordering logic.
PiperOrigin-RevId: 603660773
2024-02-02 05:34:11 -08:00
huangdarwin
d87179b463 Effect: Remove stale TODO.
PiperOrigin-RevId: 603632255
2024-02-02 02:55:13 -08:00
huangdarwin
a27511cc50 Effect: Remove inputColorInfo from create() methods.
Transformer export and ExoPlayer previewing both read inputColorInfo from
registerInputStream now, instead of maintaining a consistent input color
throughout multiple streams in a sequence.

Therefore, we can remove inputColor-related arguments and methods now.

PiperOrigin-RevId: 603423509
2024-02-01 11:09:57 -08:00
huangdarwin
dd7846ee1c Effect: Use element instead of peek, when throwing if null.
If nullness should result in an exception, we should throw as soon as possible,
so that stack traces are easier to follow.

Did a quick scan of media3.effect+transformer and this covers all uses of
peek that immediately throw there.

PiperOrigin-RevId: 603393366
2024-02-01 09:32:21 -08:00
huangdarwin
42ac0e5492 Effect: Report errors during registerInputStream
Without this, GLSL compilation errors may lead to the test stalling indefinitely

PiperOrigin-RevId: 603381111
2024-02-01 08:42:43 -08:00
sheenachhabra
198e3fb166 Assert Export output mime type by retrieving output file metadata
PiperOrigin-RevId: 603333340
2024-02-01 04:49:02 -08:00
tonihei
e3e57c9b99 Fix HlsPlaybackTest flakiness
The new test introduced in 45bd5c6f0a is flaky because we only
wait until the media is fully buffered. However, we can't fully
control how much of this data is initially read by the Robolectric
codec and thus the output dump files (containing these codec
interactions) are flaky.

This can be fixed by fully playing the media once and then seeking
back instead.

#minor-release

PiperOrigin-RevId: 603324068
2024-02-01 03:58:37 -08:00
michaelkatz
62c7ee0fb0 Render last image despite not receiving EoS
If seeking between last image sample and end of the file where the current stream is not final, then EoS sample will not be provided to `ImageRenderer`. ImageRenderer must still produce the last image sample.

PiperOrigin-RevId: 603312090
2024-02-01 02:54:36 -08:00
Copybara-Service
f85860c041 Merge pull request #1011 from cedricxperi:dts-lbr-hls-bitrate-unknown-fix
PiperOrigin-RevId: 603302863
2024-02-01 02:09:02 -08:00
huangdarwin
554530a426 Effect: Remove unused setOutputSurfaceInfo method
This hasn't been used, since b466b06ace

PiperOrigin-RevId: 603097097
2024-01-31 10:49:42 -08:00
sheenachhabra
cb7ea09af1 Add regression test of skipping empty track when writing MP4
The implementation of fragmented MP4 caused a regression where muxer
started writing empty tracks even for non fragmented MP4.

PiperOrigin-RevId: 603091348
2024-01-31 10:31:52 -08:00
huangdarwin
cebe6d8ba5 HDR: Don't assume that swapping between BT709 and BT601 needs tone-map.
VideoFrameProcessor treats BT601 and BT709 as roughly equivalent now, so we
shouldn't be making checks that assume BT709 <-> requires tone-mapping.

Also, the color transfer is a better determinant for tone-mapping than color range, so use just the transfer to determine if tone-mapping is required.

PiperOrigin-RevId: 603083100
2024-01-31 10:07:45 -08:00
tonihei
9ba93d386d Reworded comment and formatting fixes 2024-01-31 18:05:33 +00:00
huangdarwin
1163660918 Test: Save test bitmaps in a separate loop from assertions.
This means all bitmaps will save even if an assertion fails somewhere in the test
method

PiperOrigin-RevId: 603067528
2024-01-31 09:12:56 -08:00
sheenachhabra
61603f90f3 Refactor track retrieval into a separate method
This will be be required when we add more method which
required video track.

PiperOrigin-RevId: 603024260
2024-01-31 06:00:58 -08:00
samrobinson
65c354029a Add TODO around using improved buffer assignment logic.
PiperOrigin-RevId: 603019987
2024-01-31 05:36:09 -08:00
Copybara-Service
dfcc2cb41d Merge pull request #1015 from kamaroyl:feat/PsshVersion1
PiperOrigin-RevId: 603016920
2024-01-31 05:17:33 -08:00
sheenachhabra
5147eb1a65 Add audio/video sample mime type in ExportResult
PiperOrigin-RevId: 603013441
2024-01-31 05:00:12 -08:00
Copybara-Service
45bd5c6f0a Merge pull request #1031 from garethfenn:hlschunkseek
PiperOrigin-RevId: 603008793
2024-01-31 04:33:44 -08:00
Cedric T
460280556e Move DTS Express bit-rate change to DefaultAudioSink.java 2024-01-31 12:33:18 +00:00
Cedric T
b915b04594 Fix HLS DTS Express bit-rate unknown issue. 2024-01-31 12:33:18 +00:00
sheenachhabra
fd2ea22e47 Allow AV1 output mime type in FrameworkMuxer
The `MediaMuxer` (FrameworkMuxer) supports AV1 mime type from API 34.
For this to work track `Format/MediaFormat` must have `CSD`
data.

Change also include providing AV1 option in demo app.

Transmuxing of an AV1 mime type input will not work because
`Extractor` does not extract AV1 CSD data.

Verified changes manually via demo app.

PiperOrigin-RevId: 603002380
2024-01-31 04:02:21 -08:00
tonihei
b768ac791a Add e2e test for seeking to beginning of chunk 2024-01-31 11:53:55 +00:00
tonihei
c28c853541 Further adjustments to PR #1015
- Added back parsing of scheme data for version 1 as it's technically
  allowed by the spec.
- Made constructor of PsshAtom private to only publish the data class
  and not the constructor.
- Formatting and Javadoc adjustments
- Additional tests
2024-01-31 11:49:44 +00:00
sheenachhabra
c6cb6c4922 Move FileUtil.java into test_utils module
FileUtil.java can be extended to add more methods for validating
output file. This will be used in Transformer's robolectric tests and
instrumentation tests hence need to move to a common module.

PiperOrigin-RevId: 602789503
2024-01-30 11:33:10 -08:00
huangdarwin
3e59c113d7 Transformer: Allow single-sequence mixing HDR and SDR input.
Previously, input assets had to be all SDR or all HDR.

After this CL, if tone-mapping is requested, HDR and SDR may mix in any order. If tone-mapping is not requested, SDR may precede HDR, but not vice versa, until SDR to HDR tone-mapping is implemented

Some changes to accomplish this include:
1. Inputting the decoded format's color to VideoFrameProcessor.registerInputStream
for each stream.
2. Calculating the estimated decoded format's color for each stream, by estimating
it based on MediaCodec tone-mapping.

PiperOrigin-RevId: 602747837
2024-01-30 09:20:41 -08:00
samrobinson
7c8a31e2b1 Remove redundant boilerplate in AudioGraphTest & AudioGraphInputTest.
* getPcmFormat Util method already sets the mime type as AUDIO_RAW.
* static final AudioFormat consts improve test case readability.

PiperOrigin-RevId: 602740007
2024-01-30 08:53:10 -08:00
Gareth Fenn
173dbc87a2 Seek at a chunk level when seeking to chunk start positions
This avoids issues that can arise due to the slight discrepancies between
chunk start times (obtained from the manifest of segment index) and
the timestamps of the samples contained within those chunks.
2024-01-30 09:24:08 +00:00
sheenachhabra
03d35e3f43 Reset transformer state after resume finishes
PiperOrigin-RevId: 602467396
2024-01-29 12:32:42 -08:00
kamaroyl
b898dbacad Update Pssh Atom Util to expose internal data class, parse v1 PSSH atoms 2024-01-29 13:34:29 +00:00
claincly
dcae49a561 Fix blank video when switching on/off screen
This happens when using `ExoPlayer.setVideoEffects()`.

This CL also fixes the first frame not rendered problem, originally solved in
7e65cce967, but rolled back in 5056dfaa2b because the solution introduces
the flash that is observed in b/292111083.

Before media3 1.1 release, the output size of `VideoFrameProcessor` is not
reported to the app. This was changed later after introducing
`CompositingVideoSinkProvider`, where the video size after processing **is**
reported to the app. After this CL, the size is again, not reported.

PiperOrigin-RevId: 602345087
2024-01-29 04:24:19 -08:00
tonihei
bb533332f4 Update skip silence algorithm
The updated algorithm has two main improvements:
 - The silence padding is not constant but a ratio of the original
   silence (up to a defined max) to more naturally represent the
   original gaps.
 - The silence is not instantly going to zero, but uses a ramp down
   and up for a smooth volume transition and also retains a small
   percentage of the original noise for more natural "silences" that
   still contain some background noise.

#minor-release

Issue: google/ExoPlayer#7423
PiperOrigin-RevId: 602322442
2024-01-29 02:33:28 -08:00
Googler
994e2fc317 Rollback of f9eb8626eb
PiperOrigin-RevId: 601912101
2024-01-26 17:55:30 -08:00
Googler
9e48fcb8fb Rollback of 2e6982be2c
PiperOrigin-RevId: 601911260
2024-01-26 17:50:24 -08:00
Googler
e0be4c2ff4 Rollback of 4d5f844c61
PiperOrigin-RevId: 601910682
2024-01-26 17:45:40 -08:00
tofunmi
4d5f844c61 Clear the list of videoEffects in trim optimization
If trim optimisation is being applied, then `EditedMediItem.effects.videoEffects` only contains no-op effects or regular rotations that get be applied in the muxer wrapper. Therefore, we should clear the list of video effects to ensure that no effect gets applied twice.

This fixes requested rotations being applied twice in trim optimization.

Manually tested to ensure all combinations of trimming+muting+rotating works at intended.

PiperOrigin-RevId: 601853203
2024-01-26 13:33:53 -08:00
jbibik
eb3173aa90 Remove a redundant TODO in Util
PiperOrigin-RevId: 601820851
2024-01-26 11:34:43 -08:00
tonihei
2fc5590e7a Remove misleading @CanIgnoreReturnValue
The return value of onConfigure must not be ignored as it specifies
the output format of the processor, which may be different from the
input format.

#minor-release

PiperOrigin-RevId: 601799440
2024-01-26 10:19:40 -08:00
tonihei
ed5b7004b4 Replace or suppress deprecated usages
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
2024-01-26 10:06:18 -08:00
tofunmi
7424cffce1 Support changing input colorinfo for images
since we now can support taking in the inputColor upon registering the stream, there is no need to hardcode the image input color anymore. We should now be able to support switching between texture and image input which we couldn't before, but this is untested and not necessary.

PiperOrigin-RevId: 601784149
2024-01-26 09:17:29 -08:00
huangdarwin
b1c1c2a6dd Transformer: Plumb hdrMode into AssetLoaders instead of forceInterpret.
This allows us to also plumb whether we're doing MediaCodec tone-mapping,
which will be used in a follow-up CL in the ExoAssetLoaderVideoRenderer.

PiperOrigin-RevId: 601774435
2024-01-26 08:36:21 -08:00
ibaker
373822ce45 Add a comment to suggest keeping JUnit version in sync with the Android
source tree - to make importing GTS tests easier.

PiperOrigin-RevId: 601725811
2024-01-26 04:14:40 -08:00
Googler
807d98a3d6 Update IMA README to include link to supported platforms
PiperOrigin-RevId: 601720412
2024-01-26 03:44:24 -08:00
sheenachhabra
4570ee9275 Fix link to 1.3.0-alpha01 release
PiperOrigin-RevId: 601469906
(cherry picked from commit 605689a020)
2024-01-26 11:15:09 +00:00
tofunmi
2e6982be2c limit transmuxing to regular rotations only
PiperOrigin-RevId: 601710663
2024-01-26 02:46:50 -08:00
sheenachhabra
605689a020 Fix link to 1.3.0-alpha01 release
PiperOrigin-RevId: 601469906
2024-01-25 09:23:17 -08:00
sheenachhabra
7822613cc6 Version bump to media3:1.3.0-beta01
PiperOrigin-RevId: 601441910
(cherry picked from commit 21ab474260)
2024-01-25 16:23:46 +00:00
ibaker
4382aa0b34 Make Cea608Parser and Cea708Parser package-private
It's likely that we will merge these back into their `XXXDecoder`
implementations, but this smaller change allows us to avoid including
these public symbols in the upcoming release.

#minor-release

PiperOrigin-RevId: 601432629
(cherry picked from commit 12157a6b1a)
2024-01-25 16:20:26 +00:00
sheenachhabra
e29e775732 Update release notes for Media3 1.3.0-beta01 release
#minor-release

PiperOrigin-RevId: 601408404
(cherry picked from commit 79b0b8090c)
2024-01-25 16:20:26 +00:00
sheenachhabra
21ab474260 Version bump to media3:1.3.0-beta01
#minor-release

PiperOrigin-RevId: 601441910
2024-01-25 07:28:43 -08:00
ibaker
12157a6b1a Make Cea608Parser and Cea708Parser package-private
It's likely that we will merge these back into their `XXXDecoder`
implementations, but this smaller change allows us to avoid including
these public symbols in the upcoming release.

#minor-release

PiperOrigin-RevId: 601432629
2024-01-25 06:43:57 -08:00
tofunmi
f9eb8626eb Support transmuxing when no op effects and regular rotations are set
PiperOrigin-RevId: 601419245
2024-01-25 05:34:06 -08:00
sheenachhabra
79b0b8090c Update release notes for Media3 1.3.0-beta01 release
#minor-release

PiperOrigin-RevId: 601408404
2024-01-25 04:34:10 -08:00
ibaker
8770286a8e Throw immediately from ExoPlayer.setVideoEffects() if dep not found
This method works by reflectively loading classes from the `lib-effect`
module, in order to avoid a hard dependency on this module for ExoPlayer
users that don't want video effect functionality. This change ensures
that a failure to load the necessary classes fails immediately, instead
of on a later thread inside `MediaCodecVideoRenderer` when the
reflection currently happens.

Also update the javadoc to make the dependency requirement clear.

#minor-release

PiperOrigin-RevId: 601387957
(cherry picked from commit a6812156e6)
2024-01-25 11:42:44 +00:00
jbibik
748fec1ac6 Add a setter of SubtitleParser.Factory to MediaSource.Factory
DASH: `DashMediaSource.Factory` would only propagate it to `DashChunkSource.Factory` -> `BundledChunkExtractor.Factory`

SS: `SSMediaSource.Factory` -> `SsChunkSource.Factory`

HLS: `HlsMediaSource.Factory` -> `HlsExtractorFactory`

Remove nullability of SubtitleParser.Factory across the stack

#minor-release

PiperOrigin-RevId: 601250013
(cherry picked from commit f103a2dcf5)
2024-01-25 11:42:44 +00:00
christosts
55e3dd77c6 Rollback of e364510937
PiperOrigin-RevId: 601187997
(cherry picked from commit 85db94782a)
2024-01-25 11:42:44 +00:00
jbibik
0713d56efc Add setters of SubtitleParser.Factory and experimental toggle
The `SubtitleParser.Factory` is no longer @Nullable and the experimenting toggle is used to enable/disable the use of this factory for subtitle parsing during extraction.

The three places that will hold the "truth" for the `SubtitleParser.Factory` are: BundledChunkExtractor.Factory, SsChunkSource.Factory, DefaultHlsExtractorFactory

DASH: `DashMediaSource.Factory` would only propagate it to `DashChunkSource.Factory` -> `BundledChunkExtractor.Factory`

SS: `SSMediaSource.Factory` -> `SsChunkSource.Factory`

HLS: `HlsMediaSource.Factory` -> `HlsExtractorFactory`

#minor-release

PiperOrigin-RevId: 601151615
(cherry picked from commit 4d7b23f0d1)
2024-01-25 11:42:44 +00:00
sheenachhabra
9581af110a Write "stco" box instead of "co64" for fragmented MP4
As per MP4 spec ISO 14496-12: 8.7.5 Chunk Offset Box, Both "stco" and
"co64" can be used to store chunk offsets. While "stco" supports 32-bit
offsets, "co64" supports 64-bit offsets.
In non fragmented MP4, the mdat box can be extremely large, hence muxer
uses "co64" box.
But for fragmented MP4, muxer does not write any data in this chunk offset
box (present in "moov" box) because all sample related info is present in
"moof" box.
Technically, "co64" box should also work in fragmented MP4because
its empty only but QuickTime player fails to play video if "co64"
box is present in fragmented MP4 output file.

Testing: Verified that QuickTime player does not play video when "co64"
box is present but is able to play when "stco" box is present.

#minor-release

PiperOrigin-RevId: 601147046
(cherry picked from commit 0acf6902e5)
2024-01-25 11:42:44 +00:00
jbibik
db420350f8 Remove SubtitleParser.Factory references from Hls/Ss/DashMediaPeriod
Those classes only needed to have access to a `SubtitleParser.Factory` to get a potentially updated `Format` for TrackGroups. The `SubtitleParser.Factory` was only used to check the support for the `mimeType` and getting some cue-related behaviour.

This introduced complexity in a way that both Periods and Extractors needed to have the same `SubtitleParser.Factory` in their individual stacks. To ensure that the sample queue would get the same transcoded/original format.

Instead, now we expose `getOutputTextFormat` methods on `ChunkExtractor.Factory`, `SsChunkSource.Factory` and `HlsExtractorFactory`. Those are the dependencies that Hls/Ss/DashMediaPeriod can make use of to delegate the format-updating logic to.

#minor-release

PiperOrigin-RevId: 601130714
(cherry picked from commit 966b710897)
2024-01-25 11:42:44 +00:00
rohks
cfb676adaf Add Mp4ExtractorTest for sample with edit list (edts box)
The sample has multiple sync frames for video track.

PiperOrigin-RevId: 601129350
(cherry picked from commit f8dbbc82e2)
2024-01-25 11:42:44 +00:00
sheenachhabra
539a8f9a24 Write sample data offset related fields in tfhd and trun box
This fix makes output playable on VLC player.
The output does not play on QuickTime player which is being fixed in
a separate CL.

#minor-release

PiperOrigin-RevId: 601118813
(cherry picked from commit 806f90922b)
2024-01-25 11:42:44 +00:00
michaelkatz
db0262efdb Keep stream offset alive in ImageRenderer until stream transition
Fix modeled after OutputStreamInfo usage for stream offset in `MediaCodecRenderer`

PiperOrigin-RevId: 601109900
(cherry picked from commit 688622eb47)
2024-01-25 11:42:44 +00:00
tofunmi
a6756c6d40 MuxerWrapper rotation degree fix
Allow setAdditionalRotationDegrees to be called with same rotation after tracks added. This is needed for processes that mux files partially trim optimization so they don't error out after hitting the check state

Manually tested to ensure trim optimization succeeds, automated test added here as well

PiperOrigin-RevId: 601081778
(cherry picked from commit b94c7d08c1)
2024-01-25 11:42:44 +00:00
ibaker
97b8f1add9 Add proguard keep rules for ExoPlayer.setVideoEffects
These symbols in `lib-effect` are referenced via reflection from
`CompositingVideoSinkProvider` in `lib-exoplayer` in order to avoid
a hard dependency from `lib-exoplayer` to `lib-effect`. Without this
keep rule, the symbols can get renamed by R8 resulting in the
invocations failing.

#minor-release

PiperOrigin-RevId: 601074636
(cherry picked from commit e5621cc709)
2024-01-25 11:42:44 +00:00
timpeut
be0d531857 Suppress nullability warnings
PiperOrigin-RevId: 600891113
(cherry picked from commit 9c1aaa7c43)
2024-01-25 11:42:44 +00:00
tianyifeng
733c982a21 Change the behaviour in MediaMetadata.Builder.populate
Populate both `artworkUri` and `artworkData` in
`MediaMetadata.Builder.populate(MediaMetadata)` when at least one of them is non-null.

Issue: androidx/media#964
PiperOrigin-RevId: 600826103
(cherry picked from commit 35ac46b92e)
2024-01-25 11:42:44 +00:00
sheenachhabra
426dd77ac0 Suppress lint warning about missing POST_NOTIFICATIONS permission
For media session related notifications, permission is not required.
https://developer.android.com/develop/ui/views/notifications/notification-permission#exemptions-media-sessions

#minor-release

PiperOrigin-RevId: 600819251
(cherry picked from commit b98e5ac0d4)
2024-01-25 11:42:44 +00:00
sheenachhabra
081baa03b9 Process all tracks before writing fragment in fragmented MP4
Earlier implementation processed each track (pending sample's buffer info)
individually when writing their corresponding "traf" box in a fragment.
The change involves processing all tracks before start writing "traf" boxes.

#minor-release

PiperOrigin-RevId: 600811093
(cherry picked from commit 4c1581a175)
2024-01-25 11:42:44 +00:00
tonihei
a1280b1a23 Add setRemotePlaybackInfo to MediaStyle
This method is needed for some system apps to override the
output switcher when MediaRouter2 can't be used.

PiperOrigin-RevId: 600807119
(cherry picked from commit b64d754670)
2024-01-25 11:42:44 +00:00
siroberts
193cb143ff Change type of setCustomLayout in MediaSession.resultBuilder to List
PiperOrigin-RevId: 600801528
(cherry picked from commit 1f78aa5b2a)
2024-01-25 11:42:44 +00:00
tonihei
236287a513 Use Media3 MediaStyle instead of legacy one
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
(cherry picked from commit 9448f939f4)
2024-01-25 11:42:43 +00:00
tianyifeng
3a222473e9 Internal change
PiperOrigin-RevId: 600784733
(cherry picked from commit 0c0b19e26e)
2024-01-25 11:42:43 +00:00
ibaker
8e97895e9f Test parsing-during-extraction in ClippedPlaybackTest
We keep the previous parsing-during-rendering tests, even though they
can be a bit flaky, because this is an important regression test. The
regression risk is lower for this instrumentation test compared to
robolectric tests with different `ShadowLooper` behaviour.

#minor-release

PiperOrigin-RevId: 600781035
(cherry picked from commit a53f3451dd)
2024-01-25 11:42:43 +00:00
tofunmi
b8ff9cd715 Update METADATA to add clang-format requirement for glsl files
also ran clang-format for good measure

PiperOrigin-RevId: 600759938
(cherry picked from commit acc78125d2)
2024-01-25 11:42:43 +00:00
tofunmi
eda2080279 BaseGlShaderProgram: Remove redundant NoSuchElementException catching
PiperOrigin-RevId: 600738198
(cherry picked from commit cc62f0556c)
2024-01-25 11:42:43 +00:00
ibaker
dd9f61005e Release MediaSession and ExoPlayer in MediaControllerStubTest
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
(cherry picked from commit ca61ac6ca3)
2024-01-25 11:42:43 +00:00
tofunmi
21e6c1c43e Transformer demo: support selecting all media MIME types
It's useful for development and debugging to select a local image
or audio (only) file as well as a video file in the transformer demo
app.

I tested manually that you can select a local video, audio and image
but not e.g. a pdf with the main "choose local file" picker and only
an image with the choose local image picker for the bitmap overlay
demo.

PiperOrigin-RevId: 600722622
(cherry picked from commit 94ce356bc1)
2024-01-25 11:42:43 +00:00
tofunmi
fce23d9d4e Trim optimization fix: check if audio is removed when comparing formats
#minor-release

PiperOrigin-RevId: 600493390
(cherry picked from commit 5863ce7dd5)
2024-01-25 11:42:43 +00:00
tonihei
5ac0c8beee Fix cleared metadata when repeating the same item
Issue: androidx/media#1007

#minor-release

PiperOrigin-RevId: 600477540
(cherry picked from commit c6bf380d50)
2024-01-25 11:42:43 +00:00
sheenachhabra
50e0072dac Do not write empty track (with no samples) in a non fragmented MP4
PiperOrigin-RevId: 600453680
(cherry picked from commit 94bf9fa81d)
2024-01-25 11:42:43 +00:00
tonihei
6632531c4a Catch exceptions when retrieving current device from audio manager
We can just continue to assume that we don't know the current device.
This case happens on the latest Robolectric release where this method
call isn't implemented yet. As we not generally assume that the
method can throw, this workaround can be removed once Robolectric
is updated again.

#minor-release

PiperOrigin-RevId: 600426851
(cherry picked from commit 81615dd5b5)
2024-01-25 11:42:43 +00:00
christosts
05b8e633e3 SimpleBasePlayer: add protected method for thread verification
Add protected method in SimpleBasePlayer for thread verification to help
subclasses verify thread access for additional methods they define and
still report the same message to the user.

Also, remove the DAC link pointing to the ExoPlayer-specific
documentation from the exception message. Users who extend
SimpleBasePlayer have access to the class' javadoc.

PiperOrigin-RevId: 600426692
(cherry picked from commit 9e9c3cbe5e)
2024-01-25 11:42:43 +00:00
andrewlewis
18617b8a60 Prevent using high profile on problematic devices
[Android best
practices](https://developer.android.com/media/optimize/sharing#android_8_81_and_9)
recommend disabling B-frames on API 27, but some devices output B-frames anyway
when H.264/AVC High profile is selected. Add a workaround to force these
devices not to use high profile, to prevent B-frames being output.

`MediaMuxer` likely handles B-frames on these specific devices, but this change
allows the migration to default to in-app muxing to take place without
introducing errors, and it's a temporary workaround until B-frames are properly
supported in the in-app muxer.

PiperOrigin-RevId: 600422238
(cherry picked from commit 6029521898)
2024-01-25 11:42:43 +00:00
tonihei
3e005e62dc Check int and float parameters from external apps for validity
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
(cherry picked from commit c64b271f07)
2024-01-25 11:42:43 +00:00
ibaker
da5e5db3d2 Disable 'skip buffers with identical release times' in GTS tests
This optimization always reports buffers as 'skipped' (i.e. deliberately
not shown), which makes sense for the target case of high FPS content on
a lower refresh rate screen, when lots of the frames will **never** be
shown.

However the optimization also results in reporting buffers as 'skipped'
when decoding is a bit slow, resulting in a frame being released one
vsync late, which then means we have two frames to release in the same
vsync (when the previous vsync was empty). In this case, it would be
more correct to report this as a 'dropped' frame (since it was due to
slow decoding).

Until we can change the logic to distinguish these cases and report them
separately, this CL disables the optimization completely in GTS tests.
This is needed because we often assert there were zero skipped frames,
so slight decoding slowness can cause spurious/flaky test failures (our
threshold for dropped frames is non-zero).

#minor-release

PiperOrigin-RevId: 600406443
(cherry picked from commit 999e154b2a)
2024-01-25 11:42:43 +00:00
tonihei
5b7b19cf3c Add TODO about known feature gap in ImageRenderer
PiperOrigin-RevId: 600404546
(cherry picked from commit b84104e7a1)
2024-01-25 11:42:43 +00:00
andrewlewis
515d2e2578 Skip 1080p test on Nexus 7, API 21
This device doesn't seem to be capable of simultaneous encode/decode at this
resolution. We don't have a good way to check the capability (we are already
checking separate decode/encode capability) so just skip this test to save time
triaging its failures.

PiperOrigin-RevId: 600399564
(cherry picked from commit e82393ed41)
2024-01-25 11:42:43 +00:00
christosts
1dc880cb3b Rollback of e364510937
PiperOrigin-RevId: 600393114
(cherry picked from commit d1d03189eb)
2024-01-25 11:42:43 +00:00
tonihei
432cde6051 Use routed device in AudioCapabilities
From API 23, we may have a preferred device that is most likely used
as the output device.
From API 24, the AudioTrack tells us the actual routed device that is
used for output and we can listen to changes happening mid-playback.
From API 33, we can directly query the default device that will
be used for audio output for the current attributes.

If the routed device is known by any of the methods above, we can add
more targeted checks in methods like isBluetoothConnected to avoid
iterating over all devices that are not relevant.

The knowledge about the routed device will also be useful to check
advanced output capabilities in the future (e.g. for lossless
playback)

PiperOrigin-RevId: 600384923
(cherry picked from commit b1c954fa84)
2024-01-25 11:42:43 +00:00
huangdarwin
dcfa8c60ce Previewing: set VideoFrameReleaseControl after CVSP is created.
This allows us to inject a videoFrameProcessorFactory into
MediaCodecVideoRenderer, without issues about creating the
VideoFrameReleaseControl in the MediaCodecVideoRenderer.

Unfortunately, this does result in more complex CVSP state, where
VideoFrameReleaseControl is no longer final, may be null, and may potentially
change. However, this tries to be careful with assertions to guarantee good
state, and is cleaner than modifying the long-standing MediaCodecVideoRenderer
interface.

Tested that this works on the ExoPlayer demo with setVideoEffects applied, and
using a playlist with SDR->HDR and HDR->SDR items.

PiperOrigin-RevId: 599823412
(cherry picked from commit cb0f5a7fff)
2024-01-25 11:42:43 +00:00
samrobinson
4ac9d449d3 Remove thread blocking for TransformerInternal#getProgress.
Thread-safe interactions with state and value.

PiperOrigin-RevId: 599810672
(cherry picked from commit e364510937)
2024-01-25 11:42:43 +00:00
ibaker
a6812156e6 Throw immediately from ExoPlayer.setVideoEffects() if dep not found
This method works by reflectively loading classes from the `lib-effect`
module, in order to avoid a hard dependency on this module for ExoPlayer
users that don't want video effect functionality. This change ensures
that a failure to load the necessary classes fails immediately, instead
of on a later thread inside `MediaCodecVideoRenderer` when the
reflection currently happens.

Also update the javadoc to make the dependency requirement clear.

#minor-release

PiperOrigin-RevId: 601387957
2024-01-25 02:43:35 -08:00
jbibik
f103a2dcf5 Add a setter of SubtitleParser.Factory to MediaSource.Factory
DASH: `DashMediaSource.Factory` would only propagate it to `DashChunkSource.Factory` -> `BundledChunkExtractor.Factory`

SS: `SSMediaSource.Factory` -> `SsChunkSource.Factory`

HLS: `HlsMediaSource.Factory` -> `HlsExtractorFactory`

Remove nullability of SubtitleParser.Factory across the stack

#minor-release

PiperOrigin-RevId: 601250013
2024-01-24 15:19:50 -08:00
christosts
85db94782a Rollback of e364510937
PiperOrigin-RevId: 601187997
2024-01-24 11:50:24 -08:00
jbibik
4d7b23f0d1 Add setters of SubtitleParser.Factory and experimental toggle
The `SubtitleParser.Factory` is no longer @Nullable and the experimenting toggle is used to enable/disable the use of this factory for subtitle parsing during extraction.

The three places that will hold the "truth" for the `SubtitleParser.Factory` are: BundledChunkExtractor.Factory, SsChunkSource.Factory, DefaultHlsExtractorFactory

DASH: `DashMediaSource.Factory` would only propagate it to `DashChunkSource.Factory` -> `BundledChunkExtractor.Factory`

SS: `SSMediaSource.Factory` -> `SsChunkSource.Factory`

HLS: `HlsMediaSource.Factory` -> `HlsExtractorFactory`

#minor-release

PiperOrigin-RevId: 601151615
2024-01-24 09:55:49 -08:00
sheenachhabra
0acf6902e5 Write "stco" box instead of "co64" for fragmented MP4
As per MP4 spec ISO 14496-12: 8.7.5 Chunk Offset Box, Both "stco" and
"co64" can be used to store chunk offsets. While "stco" supports 32-bit
offsets, "co64" supports 64-bit offsets.
In non fragmented MP4, the mdat box can be extremely large, hence muxer
uses "co64" box.
But for fragmented MP4, muxer does not write any data in this chunk offset
box (present in "moov" box) because all sample related info is present in
"moof" box.
Technically, "co64" box should also work in fragmented MP4because
its empty only but QuickTime player fails to play video if "co64"
box is present in fragmented MP4 output file.

Testing: Verified that QuickTime player does not play video when "co64"
box is present but is able to play when "stco" box is present.

#minor-release

PiperOrigin-RevId: 601147046
2024-01-24 09:40:20 -08:00
jbibik
966b710897 Remove SubtitleParser.Factory references from Hls/Ss/DashMediaPeriod
Those classes only needed to have access to a `SubtitleParser.Factory` to get a potentially updated `Format` for TrackGroups. The `SubtitleParser.Factory` was only used to check the support for the `mimeType` and getting some cue-related behaviour.

This introduced complexity in a way that both Periods and Extractors needed to have the same `SubtitleParser.Factory` in their individual stacks. To ensure that the sample queue would get the same transcoded/original format.

Instead, now we expose `getOutputTextFormat` methods on `ChunkExtractor.Factory`, `SsChunkSource.Factory` and `HlsExtractorFactory`. Those are the dependencies that Hls/Ss/DashMediaPeriod can make use of to delegate the format-updating logic to.

#minor-release

PiperOrigin-RevId: 601130714
2024-01-24 08:40:39 -08:00
rohks
f8dbbc82e2 Add Mp4ExtractorTest for sample with edit list (edts box)
The sample has multiple sync frames for video track.

PiperOrigin-RevId: 601129350
2024-01-24 08:33:02 -08:00
sheenachhabra
806f90922b Write sample data offset related fields in tfhd and trun box
This fix makes output playable on VLC player.
The output does not play on QuickTime player which is being fixed in
a separate CL.

#minor-release

PiperOrigin-RevId: 601118813
2024-01-24 07:52:02 -08:00
michaelkatz
688622eb47 Keep stream offset alive in ImageRenderer until stream transition
Fix modeled after OutputStreamInfo usage for stream offset in `MediaCodecRenderer`

PiperOrigin-RevId: 601109900
2024-01-24 07:10:04 -08:00
tofunmi
b94c7d08c1 MuxerWrapper rotation degree fix
Allow setAdditionalRotationDegrees to be called with same rotation after tracks added. This is needed for processes that mux files partially trim optimization so they don't error out after hitting the check state

Manually tested to ensure trim optimization succeeds, automated test added here as well

PiperOrigin-RevId: 601081778
2024-01-24 04:44:28 -08:00
ibaker
e5621cc709 Add proguard keep rules for ExoPlayer.setVideoEffects
These symbols in `lib-effect` are referenced via reflection from
`CompositingVideoSinkProvider` in `lib-exoplayer` in order to avoid
a hard dependency from `lib-exoplayer` to `lib-effect`. Without this
keep rule, the symbols can get renamed by R8 resulting in the
invocations failing.

#minor-release

PiperOrigin-RevId: 601074636
2024-01-24 04:08:40 -08:00
timpeut
9c1aaa7c43 Suppress nullability warnings
PiperOrigin-RevId: 600891113
2024-01-23 13:34:14 -08:00
tianyifeng
35ac46b92e Change the behaviour in MediaMetadata.Builder.populate
Populate both `artworkUri` and `artworkData` in
`MediaMetadata.Builder.populate(MediaMetadata)` when at least one of them is non-null.

Issue: androidx/media#964
PiperOrigin-RevId: 600826103
2024-01-23 10:08:33 -08:00
sheenachhabra
b98e5ac0d4 Suppress lint warning about missing POST_NOTIFICATIONS permission
For media session related notifications, permission is not required.
https://developer.android.com/develop/ui/views/notifications/notification-permission#exemptions-media-sessions

#minor-release

PiperOrigin-RevId: 600819251
2024-01-23 09:46:50 -08:00
sheenachhabra
4c1581a175 Process all tracks before writing fragment in fragmented MP4
Earlier implementation processed each track (pending sample's buffer info)
individually when writing their corresponding "traf" box in a fragment.
The change involves processing all tracks before start writing "traf" boxes.

#minor-release

PiperOrigin-RevId: 600811093
2024-01-23 09:20:52 -08:00
tonihei
b64d754670 Add setRemotePlaybackInfo to MediaStyle
This method is needed for some system apps to override the
output switcher when MediaRouter2 can't be used.

PiperOrigin-RevId: 600807119
2024-01-23 09:06:37 -08:00
siroberts
1f78aa5b2a Change type of setCustomLayout in MediaSession.resultBuilder to List
PiperOrigin-RevId: 600801528
2024-01-23 08:46:30 -08:00
tonihei
9448f939f4 Use Media3 MediaStyle instead of legacy one
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
2024-01-23 08:34:06 -08:00
tianyifeng
0c0b19e26e Internal change
PiperOrigin-RevId: 600784733
2024-01-23 07:41:15 -08:00
ibaker
a53f3451dd Test parsing-during-extraction in ClippedPlaybackTest
We keep the previous parsing-during-rendering tests, even though they
can be a bit flaky, because this is an important regression test. The
regression risk is lower for this instrumentation test compared to
robolectric tests with different `ShadowLooper` behaviour.

#minor-release

PiperOrigin-RevId: 600781035
2024-01-23 07:27:11 -08:00
tofunmi
acc78125d2 Update METADATA to add clang-format requirement for glsl files
also ran clang-format for good measure

PiperOrigin-RevId: 600759938
2024-01-23 05:49:38 -08:00
tofunmi
cc62f0556c BaseGlShaderProgram: Remove redundant NoSuchElementException catching
PiperOrigin-RevId: 600738198
2024-01-23 03:52:49 -08:00
ibaker
ca61ac6ca3 Release MediaSession and ExoPlayer in MediaControllerStubTest
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
2024-01-23 03:50:04 -08:00
tofunmi
94ce356bc1 Transformer demo: support selecting all media MIME types
It's useful for development and debugging to select a local image
or audio (only) file as well as a video file in the transformer demo
app.

I tested manually that you can select a local video, audio and image
but not e.g. a pdf with the main "choose local file" picker and only
an image with the choose local image picker for the bitmap overlay
demo.

PiperOrigin-RevId: 600722622
2024-01-23 02:35:19 -08:00
tofunmi
5863ce7dd5 Trim optimization fix: check if audio is removed when comparing formats
#minor-release

PiperOrigin-RevId: 600493390
2024-01-22 10:14:11 -08:00
tonihei
c6bf380d50 Fix cleared metadata when repeating the same item
Issue: androidx/media#1007

#minor-release

PiperOrigin-RevId: 600477540
2024-01-22 09:20:36 -08:00
sheenachhabra
94bf9fa81d Do not write empty track (with no samples) in a non fragmented MP4
PiperOrigin-RevId: 600453680
2024-01-22 07:44:55 -08:00
tonihei
81615dd5b5 Catch exceptions when retrieving current device from audio manager
We can just continue to assume that we don't know the current device.
This case happens on the latest Robolectric release where this method
call isn't implemented yet. As we not generally assume that the
method can throw, this workaround can be removed once Robolectric
is updated again.

#minor-release

PiperOrigin-RevId: 600426851
2024-01-22 05:22:50 -08:00
christosts
9e9c3cbe5e SimpleBasePlayer: add protected method for thread verification
Add protected method in SimpleBasePlayer for thread verification to help
subclasses verify thread access for additional methods they define and
still report the same message to the user.

Also, remove the DAC link pointing to the ExoPlayer-specific
documentation from the exception message. Users who extend
SimpleBasePlayer have access to the class' javadoc.

PiperOrigin-RevId: 600426692
2024-01-22 05:20:34 -08:00
andrewlewis
6029521898 Prevent using high profile on problematic devices
[Android best
practices](https://developer.android.com/media/optimize/sharing#android_8_81_and_9)
recommend disabling B-frames on API 27, but some devices output B-frames anyway
when H.264/AVC High profile is selected. Add a workaround to force these
devices not to use high profile, to prevent B-frames being output.

`MediaMuxer` likely handles B-frames on these specific devices, but this change
allows the migration to default to in-app muxing to take place without
introducing errors, and it's a temporary workaround until B-frames are properly
supported in the in-app muxer.

PiperOrigin-RevId: 600422238
2024-01-22 04:55:54 -08:00
tonihei
c64b271f07 Check int and float parameters from external apps for validity
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
2024-01-22 04:08:42 -08:00
ibaker
999e154b2a Disable 'skip buffers with identical release times' in GTS tests
This optimization always reports buffers as 'skipped' (i.e. deliberately
not shown), which makes sense for the target case of high FPS content on
a lower refresh rate screen, when lots of the frames will **never** be
shown.

However the optimization also results in reporting buffers as 'skipped'
when decoding is a bit slow, resulting in a frame being released one
vsync late, which then means we have two frames to release in the same
vsync (when the previous vsync was empty). In this case, it would be
more correct to report this as a 'dropped' frame (since it was due to
slow decoding).

Until we can change the logic to distinguish these cases and report them
separately, this CL disables the optimization completely in GTS tests.
This is needed because we often assert there were zero skipped frames,
so slight decoding slowness can cause spurious/flaky test failures (our
threshold for dropped frames is non-zero).

#minor-release

PiperOrigin-RevId: 600406443
2024-01-22 03:27:17 -08:00
tonihei
b84104e7a1 Add TODO about known feature gap in ImageRenderer
PiperOrigin-RevId: 600404546
2024-01-22 03:16:34 -08:00
andrewlewis
e82393ed41 Skip 1080p test on Nexus 7, API 21
This device doesn't seem to be capable of simultaneous encode/decode at this
resolution. We don't have a good way to check the capability (we are already
checking separate decode/encode capability) so just skip this test to save time
triaging its failures.

PiperOrigin-RevId: 600399564
2024-01-22 02:52:25 -08:00
christosts
d1d03189eb Rollback of e364510937
PiperOrigin-RevId: 600393114
2024-01-22 02:19:01 -08:00
tonihei
b1c954fa84 Use routed device in AudioCapabilities
From API 23, we may have a preferred device that is most likely used
as the output device.
From API 24, the AudioTrack tells us the actual routed device that is
used for output and we can listen to changes happening mid-playback.
From API 33, we can directly query the default device that will
be used for audio output for the current attributes.

If the routed device is known by any of the methods above, we can add
more targeted checks in methods like isBluetoothConnected to avoid
iterating over all devices that are not relevant.

The knowledge about the routed device will also be useful to check
advanced output capabilities in the future (e.g. for lossless
playback)

PiperOrigin-RevId: 600384923
2024-01-22 01:40:50 -08:00
huangdarwin
cb0f5a7fff Previewing: set VideoFrameReleaseControl after CVSP is created.
This allows us to inject a videoFrameProcessorFactory into
MediaCodecVideoRenderer, without issues about creating the
VideoFrameReleaseControl in the MediaCodecVideoRenderer.

Unfortunately, this does result in more complex CVSP state, where
VideoFrameReleaseControl is no longer final, may be null, and may potentially
change. However, this tries to be careful with assertions to guarantee good
state, and is cleaner than modifying the long-standing MediaCodecVideoRenderer
interface.

Tested that this works on the ExoPlayer demo with setVideoEffects applied, and
using a playlist with SDR->HDR and HDR->SDR items.

PiperOrigin-RevId: 599823412
2024-01-19 07:08:23 -08:00
samrobinson
e364510937 Remove thread blocking for TransformerInternal#getProgress.
Thread-safe interactions with state and value.

PiperOrigin-RevId: 599810672
2024-01-19 06:04:27 -08:00
Copybara-Service
c403df116b Merge pull request #973 from jan-varecka-signageos-io:feat/extractTsAudioType
PiperOrigin-RevId: 599547201
2024-01-18 10:25:47 -08:00
ibaker
34a08e13fc Rollback of 406c0a15be
PiperOrigin-RevId: 599546140
2024-01-18 10:21:53 -08:00
Rohit Singh
50385be7ff Changes based on internal review 2024-01-18 17:25:36 +00:00
ibaker
2e8a81cd4d Update Util.moveItems to explicitly T extends @NonNull Object
PiperOrigin-RevId: 599516707
2024-01-18 08:35:04 -08:00
sheenachhabra
36e99f5264 Remove unnecessary passing around of class variable
PiperOrigin-RevId: 599507570
2024-01-18 08:01:33 -08:00
samrobinson
3e3c746368 Add javadoc to the TransformerState's for pause & resume.
Although not public, documenting what happens in each state allows for
better code understanding at a glance.

As part of this, refactored the #getProgress method to highlight that
the other options are "non standard".

PiperOrigin-RevId: 599505369
2024-01-18 07:52:02 -08:00
sheenachhabra
4b0ff48ca9 Fix release notes
PiperOrigin-RevId: 599499930
2024-01-18 07:25:44 -08:00
tonihei
59dc5b6692 Add missing null and Bundle checks in MediaSession/ControllerStub
PiperOrigin-RevId: 599477547
2024-01-18 05:29:39 -08:00
huangdarwin
616cb943f0 Previewing: Allow inputColorInfo to change, from SDR to HDR.
This also fixes issue introduced by frames being released from a prior version of a
GlShaderProgram

Tested by seeking within a playlist with one SDR then one HDR video.

PiperOrigin-RevId: 599475959
2024-01-18 05:20:18 -08:00
christosts
0e66197419 Rename TimestampIterator argument name in queueInputBitmap()
#minor-release

PiperOrigin-RevId: 599460771
2024-01-18 04:01:27 -08:00
tofunmi
5eb1f4043b disallow go links in Media3 open source code
PiperOrigin-RevId: 599455204
2024-01-18 03:28:31 -08:00
tonihei
e730feb98a Add missing IntDef annotation
PiperOrigin-RevId: 599414024
2024-01-18 00:16:59 -08:00
huangdarwin
1ec193883c HDR: Propagate PQ to SDR OOTF to internal input.
Previously, 8f69bb0d9d updated external input (video input)
but not internal input (image/texture input). Update internal input as
well to match.

PiperOrigin-RevId: 599235813
2024-01-17 11:27:38 -08:00
sheenachhabra
666685bd85 Use 4 Byte size field in fMP4 mdat boxes
Since mdat box can be huge so there is a provision to use 64 bit size field.
In case of fragmented MP4, individual fragments should not have large mdat box
so a 32 bit size field should be sufficient.

PiperOrigin-RevId: 599219041
2024-01-17 10:36:47 -08:00
Michael Katz
b930b40a16
Fix merge error with ffmpeg_jni.cc
Fix merge error with ffmpeg_jni.cc where cherry-pick process included code from nonselected commit.
2024-01-17 17:04:10 +00:00
ibaker
406c0a15be CompositeSequenceableLoader: Prefer buffered position of A/V tracks
Preferring audio and video tracks matches logic we already have in
[`ProgressiveMediaPeriod.getBufferedPositionUs`](f6fe90f30b/libraries/exoplayer/src/main/java/androidx/media3/exoplayer/source/ProgressiveMediaPeriod.java (L403)).

PiperOrigin-RevId: 599154217
2024-01-17 06:33:14 -08:00
Rohit Singh
32576be3e3 Add release note 2024-01-17 13:26:17 +00:00
ibaker
80bfa819c0 Add method to TextRenderer to control whether decoding is done or not
When we default to 'parse during extraction', we will flip the default
of this, to ensure that apps know they are using an
incompatible/deprecated flow for subtitle handling.

PiperOrigin-RevId: 599109304
2024-01-17 02:51:48 -08:00
Rohit Singh
7e21da8b73 Format with google-java-format 2024-01-17 10:51:28 +00:00
Jan Vařečka
286b1f52d9 Add test for MPEG audio with audio type 2024-01-17 10:22:55 +00:00
Jan Vařečka
a83662b8e1 Extract audio type from TS descriptors
The audio type of the stream is defined by ISO/IEC 13818-1 in section 2.6.18.
2024-01-17 10:22:52 +00:00
bachinger
2c8ba50524 Disable double-click detection for TV apps
Issue: androidx/media#962
PiperOrigin-RevId: 598876214
2024-01-16 10:10:09 -08:00
rahulnmohan
27c021fd7b Merge Issue: androidx/media#275: MPEG2-TS: Support DTS, DTS-LBR and DTS:X Profile2
Imported from GitHub PR https://github.com/androidx/media/pull/275

Added below mentioned features.

- Support for extracting DTS LBR(DTS Express) and DTS UHD Profile 2(DTS:X) descriptor ID from PSI PMT
- The DTSReader class is updated for extracting a DTS LBR.
- Newly added DtsUhdReader class for extracting DTS UHD frame.
- The DTSUtil class is updated to parse the DTS LBR or DTS UHD frame and report the format information.

Feature request for ExoPlayer: https://github.com/google/ExoPlayer/issues/11075
Merge 21efa0810db31550d6b215639f9ca2af6a32139a into 104cfc322c

COPYBARA_INTEGRATE_REVIEW=https://github.com/androidx/media/pull/275 from rahulnmohan:dts-mpeg2ts-update 21efa0810db31550d6b215639f9ca2af6a32139a
PiperOrigin-RevId: 598854998
2024-01-16 08:54:43 -08:00
samrobinson
e41b23d2f4 Add thread-safe information & annotations to necessary fields.
This change is a small incremental step towards better thread-safety.

PiperOrigin-RevId: 598852158
2024-01-16 08:43:15 -08:00
andrewlewis
0513a28169 Remove initialization in declaration
PiperOrigin-RevId: 598835989
2024-01-16 07:35:18 -08:00
andrewlewis
fc9900c483 Document setVideoEffects surface limitation
`Surface`s don't expose their size via Java APIs. Recommend apps pass a
`SurfaceView` (which is preferable to `TextureView` as it's more efficient)
or `SurfaceHolder` so they benefit from the player automatically passing the
size down to the video renderer via `MSG_SET_VIDEO_OUTPUT_RESOLUTION`.

PiperOrigin-RevId: 598804258
2024-01-16 04:52:08 -08:00
tofunmi
5488d33da8 Transformer: add api to cutomize image loading
PiperOrigin-RevId: 598793134
2024-01-16 03:56:08 -08:00
christosts
2d89ffc682 Annotate CompositingVideoSinkProvider with RestrictTo
The class is public so that it can be used between different
packages but it is not meant to be used by apps.

PiperOrigin-RevId: 598792759
2024-01-16 03:52:41 -08:00
ibaker
520687af28 Bump media1 dep to 1.7.0
This brings in a fix for Issue: androidx/media#489.

PiperOrigin-RevId: 598771006
2024-01-16 02:05:20 -08:00
tofunmi
0155ae998b Gaussian Blur: support blurring without drawing sharp image on top
PiperOrigin-RevId: 598626481
2024-01-15 09:39:38 -08:00
jbibik
e51c293f75 Plumb SubtitleParser.Factory into MatroskaExtractor
MatroskaExtractor will no longer be wrapped in SubtitleTranscodingExtractor, but instead use SubtitleTranscodingExtractorOutput under the hood.

FLAG_EMIT_RAW_SUBTITLE_DATA flag will be used to toggle between subtitle parsing during extraction (before the sample queue) or during decoding (after the sample queue).

The new extractor dump files generated by `MatroskaExtractorTest` now follow the new parsing logic and hence have mimeType as `x-media3-cues`.

PiperOrigin-RevId: 598616231
2024-01-15 08:32:22 -08:00
bachinger
be2f8c41b7 Fix typo in MediaSessionLegacyStub
PiperOrigin-RevId: 598615782
2024-01-15 08:29:10 -08:00
jbibik
a88d8a415a Plumb SubtitleParser.Factory into AviExtractor
AviExtractor supports text tracks (`AviExtractor.FOURCC_txts` -> `C.TRACK_TYPE_TEXT`) with subtitles.

AviExtractor will no longer be wrapped in SubtitleTranscodingExtractor, but instead use SubtitleTranscodingExtractorOutput under the hood.

FLAG_EMIT_RAW_SUBTITLE_DATA flag will be used to toggle between subtitle parsing during extraction (before the sample queue) or during decoding (after the sample queue).

PiperOrigin-RevId: 598594981
2024-01-15 06:21:33 -08:00
sheenachhabra
4a07d13838 Version bump to media3:1.3.0-alpha01
#minor-release

PiperOrigin-RevId: 598588547
2024-01-15 05:44:03 -08:00
tofunmi
7f087243bb Add supportsMimeType API to bitmapLoader
PiperOrigin-RevId: 597942459
2024-01-12 13:49:38 -08:00
tofunmi
6879698d7e Move setting bitmapFactory options from interface to implementation
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
2024-01-12 11:21:48 -08:00
sheenachhabra
09a547953b Update RELEASENOTES for 1.3.0-alpha01
#minor-release

PiperOrigin-RevId: 597862117
2024-01-12 09:33:58 -08:00
ibaker
d4be30b04d Mark CompositeSequenceableLoader final
Subclasses of this component can customize it by wrapping with the
decorator pattern, and a custom `CompositeSequencableLoaderFactory`
allows access to the list of delegate `SequenceableLoader` instances.

The `final` keyword was removed as part of <unknown commit> but this
component never ended up being subclassed within the library.

Making this class `final` makes upcoming changes easier to reason
about.

PiperOrigin-RevId: 597853429
2024-01-12 09:02:06 -08:00
ibaker
4061d476a1 MP3: Assume an Info header indicates CBR for seeking purposes
The seek table in a Xing/Info header is very imprecise (max resolution
of 255 to describe each of 100 byte positions in the file). Seeking
using a constant bitrate assumption is more accurate, especially for
longer files (which exacerbates the imprecision of the Info header).

VBR files should contain an Xing header, while an Info header is
identical but indicates the file is CBR.

Issue: androidx/media#878
PiperOrigin-RevId: 597827891
2024-01-12 06:48:00 -08:00
christosts
5056dfaa2b Regression fix of ExoPlayer.setVideoEffects()
7e65cce967 introduced a regression on ExoPlayer.setVideoEffects()
where there is flash on the screen after the first few frames are shown.

Before 7e65cce967, the first frames of the content are missed, until
MediaCodecVideoRenderer sends the onVideoSizeChanged() callback. The
first frame is processed but not shown, the onVideoSizeChanged() is
triggered and the renderer receives a video output resolution message as
a response from the UI.

7e65cce967 fixed the missed first frames by setting a surface on the
CompositingVideoSinkProvider before the provider is initialized, and as
as result:
- the first frames are rendered
- the MediaCodecVideoRenderer sends the the onVideoSizeChanged() after
  frames are shown
- the UI sends a video output resolution change
- the MediaCodecVideoRenderer updates the CompositingVideoSinkProvider
  which causes the flash.

The underlying problem is with onVideoSizeChanged() not being
triggered early enough, before the first frame is shown.

Because the flashing is a regression, this commit is reverting
7e65cce967 but keeps the test that was added as ignored, so that the
test is re-enabled as soon as we address the underlying issue.

PiperOrigin-RevId: 597814013
2024-01-12 05:20:46 -08:00
tofunmi
78c419e566 Extension to Gaussian Blur: support changing blur over time
PiperOrigin-RevId: 597809380
2024-01-12 04:53:02 -08:00
jbibik
59afb4fb01 Plumb SubtitleParser.Factory into WebvttExtractor
WebvttExtractor will no longer be wrapped in SubtitleTranscodingExtractor, but instead use SubtitleTranscodingExtractorOutput under the hood.

A new constructor will take a boolean parameter to toggle between subtitle parsing during extraction (before the sample queue) or during decoding (after the sample queue).

PiperOrigin-RevId: 597604942
2024-01-11 11:13:08 -08:00
tofunmi
f2be3fd0cb Trim Opt: Calculate duration based on sample rate from audio format
Calculating the encoded audio buffer duration.

PiperOrigin-RevId: 597591689
2024-01-11 10:28:14 -08:00
jbibik
a728ec8e67 Plumb SubtitleParser.Factory into TsExtractor
PiperOrigin-RevId: 597578122
2024-01-11 09:35:22 -08:00
huangdarwin
c59711f592 Effect: Remove unused arguments in DefaultShaderProgram factories.
Partially addresses the following TODO, by simplifying the DefaultShaderProgram
API surface.
```
// TODO(b/274109008): Refactor DefaultShaderProgram to create a class just for sampling.
```

PiperOrigin-RevId: 597575575
2024-01-11 09:25:25 -08:00
huangdarwin
b4dfbed73d Update javadoc param name to match argument name
PiperOrigin-RevId: 597554111
2024-01-11 07:50:13 -08:00
lpribanic
e93188fe7f Crop and pass thumbnails to ImageOutput
Image grids are now cropped into tiles. The tiles are provided to
ImageOutput at their correct timestamps.

PiperOrigin-RevId: 597553029
2024-01-11 07:45:50 -08:00
tonihei
cd2d7f5da5 Forward getStreamKeys in ClippingMediaPeriod
Not doing this prevents downloads of clipped media.

PiperOrigin-RevId: 597541395
2024-01-11 06:48:52 -08:00
sheenachhabra
085bc6c416 Upgrade robolectric version to 4.11
Testing details: All tests are passing on github branch as well.

PiperOrigin-RevId: 597529943
2024-01-11 05:47:52 -08:00
michaelkatz
0ae7a6bd60 Fix typo of missing closing parentheses in RELEASENOTES
PiperOrigin-RevId: 597496311
2024-01-11 10:48:31 +00:00
michaelkatz
03328848ce Fix typo of missing closing parentheses in RELEASENOTES
PiperOrigin-RevId: 597496311
2024-01-11 02:39:04 -08:00
rohks
0f33ef3906 Improve readability of constant numbers and documentation in DtsUtil
PiperOrigin-RevId: 597493602
2024-01-11 02:25:44 -08:00
tianyifeng
733301d562 Remove the parameter PlayerId from PreloadMediaSource.Factory
Originally a `PlayerId` has to be passed and it should be the same id of the player who is going to play the sources, but it turns out to be unnecessary.

When preloading, we can set a `PlayerId.UNSET` inside of the `PreloadMediaSource`, as there is no ongoing playback. And when the source is handed over to player, player will set the player's `PlayerId`.

PiperOrigin-RevId: 597475119
2024-01-11 00:48:58 -08:00
simakova
d884f19871 Add edit label
PiperOrigin-RevId: 597257431
2024-01-10 08:36:14 -08:00
ibaker
1202f8690c Bump effect and leanback minSdk to 19
These were overriding the previous minimum of 16 and therefore not
included in e54abaa75d.

PiperOrigin-RevId: 597242364
2024-01-10 07:22:00 -08:00
ibaker
3f9e0540b7 Remove non-progressive limitation from DefaultMediaSourceFactory.experimentalParseSubtitlesDuringExtraction
This involves promoting `setTextTranscodingEnabled` to
`ExtractorsFactory`, and also making it experimental, to indicate it's a
short-lived method.

PiperOrigin-RevId: 597235252
2024-01-10 06:46:50 -08:00
jbibik
d6ef48fff8 Plumb SubtitleParser.Factory into Mp4Extractor
Mp4Extractor will no longer be wrapped in SubtitleTranscodingExtractor, but instead use SubtitleTranscodingExtractorOutput under the hood.

FLAG_EMIT_RAW_SUBTITLE_DATA flag will be used to toggle between subtitle parsing during extraction (before the sample queue) or during decoding (after the sample queue).

PiperOrigin-RevId: 597221831
2024-01-10 05:36:08 -08:00
tofunmi
51d60e1f3a GaussianBlur: make short constructor call the longer one
PiperOrigin-RevId: 597212434
2024-01-10 04:42:35 -08:00
tonihei
3596bc332d Use AudioAtributes when determining AudioCapabilities
The capabilities change depending on the attributes, so we should
pass down the actual attributes used during playback and update
the capabilities whenever these change.

PiperOrigin-RevId: 597197507
2024-01-10 03:17:54 -08:00
ibaker
4fde35c9cc MP3: Extract Xing/Info parsing code from XingSeeker
This means in a later change we can still use some of the info for CBR
files, even if we want to ignore the imprecise table of contents and
seek based on a constant bitrate assumption instead.

PiperOrigin-RevId: 597193997
2024-01-10 03:00:30 -08:00
Googler
460501fcd1 Log ExportResult information when running transformer demo app
Log elapsed time, in addition to displaying it on screen.
Reuse logging logic between tests and demo.

PiperOrigin-RevId: 597186692
2024-01-10 02:24:31 -08:00
ibaker
143d782b1c Add private @SeekHeader IntDef to Mp3Extractor
Also use `switch` instead of `if-else`.

PiperOrigin-RevId: 597004322
2024-01-09 12:04:24 -08:00
ibaker
1c1d4d506d MP3: Correct duration calculation in XingSeeker
An audio file can only play sound between two PCM samples (the 'start'
and 'end' of section of a wave form). Therefore when calculating
duration from a count of PCM samples we need to subtract one first (the
'end' sample which has no duration of its own).

This only changes durations by one PCM sample (21us - 22us for 44.1kHz sample
rate).

PiperOrigin-RevId: 596990306
2024-01-09 11:16:49 -08:00
tonihei
ba8f55694a Set PCM encoding in Flac extractor
The extractor knows the PCM encoding of the losslessly
encoded data in the samples and should set it in the
Format to allow downstream components to use this information.

PiperOrigin-RevId: 596974863
2024-01-09 10:28:55 -08:00
ibaker
320dd32be9 Add extractor test for an MP3 file with Info header
Issue: androidx/media#878
PiperOrigin-RevId: 596957503
2024-01-09 09:30:21 -08:00
jbibik
da724c8cc4 Plumb SubtitleParser.Factory into FragmentedMp4Extractor
We introduce SubtitleParser.Factory that supports no formats to be used FragmentedMp4Extractors that will not do any subtitle parsing on the extraction side. We also slowly move away from using SubtitleTranscodingExtractor to SubtitleTranscodingExtractorOutput (hence making it public).

This is required by individual Extractor impls so that they can start using SubtitleTranscodingExtractorOutput rather than be wrapped by SubtitleTranscodingExtractor. The latter is to be deprecated after all the subtitle related Extractors have achieved this migration.

PiperOrigin-RevId: 596942147
2024-01-09 08:33:27 -08:00
ibaker
e54abaa75d Increase minSdk to 19
This is aligned with all other AndroidX libraries, and is required for
us to upgrade to the latest versions of our AndroidX dependencies:
https://android-developers.googleblog.com/2023/10/androidx-minsdkversion-19.html

PiperOrigin-RevId: 596923511
2024-01-09 07:15:21 -08:00
michaelkatz
1f79a0ad93 Bump media3 version to 1.2.1 and update RELEASENOTES
PiperOrigin-RevId: 596916027
(cherry picked from commit 324e1beef2)
2024-01-09 14:46:23 +00:00
michaelkatz
324e1beef2 Bump media3 version to 1.2.1 and update RELEASENOTES
#minor-release

PiperOrigin-RevId: 596916027
2024-01-09 06:39:56 -08:00
tofunmi
dee2d3af73 GlassianBlurTest: move golden images comment next to the test
PiperOrigin-RevId: 596892569
2024-01-09 04:41:46 -08:00
christosts
4198f7e242 Add utility testing Player.Listener in transformer tests
PiperOrigin-RevId: 596891721
2024-01-09 04:36:45 -08:00
microkatz
f0d24cbf58 Fix BitmapOverlay to have public constructor 2024-01-09 12:26:11 +00:00
ibaker
d55b33474e Clarify docs on Player.setMediaItem(s) and replaceMediaItem(s)
These methods sound similar, but have different behaviour. This change
tries to make the distinction clearer, and sign-post from one to the
other.

#minor-release

Issue: androidx/media#910
PiperOrigin-RevId: 595701540
(cherry picked from commit 95e742948c)
2024-01-09 12:17:49 +00:00
bachinger
141f9b760d Return null if media notification controller Future is not done
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
(cherry picked from commit 5c50b27e8f)
2024-01-09 12:17:49 +00:00
Copybara-Service
77d220c507 Merge pull request #369 from Tolriq:fix_invalid_frames
PiperOrigin-RevId: 595650068
(cherry picked from commit 8eda9f2ed2)
2024-01-09 12:17:48 +00:00
bachinger
d1b882ae56 Don't set negative values to setWhen()
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
(cherry picked from commit 426bc94090)
2024-01-09 12:17:48 +00:00
andrewlewis
b9d205ba0f Expand operating rate workaround to T612 chipset
PiperOrigin-RevId: 592916187
(cherry picked from commit 1845a4ae69)
2024-01-09 12:17:48 +00:00
Copybara-Service
b68173aae4 Merge pull request #914 from cemrich:366-forward-time-wrong
PiperOrigin-RevId: 592871532
(cherry picked from commit 966b5178b6)
2024-01-09 12:17:48 +00:00
ibaker
1da24b2875 Add container to Format.toLogString
While investigating Issue: androidx/media#887 I naively assumed the CEA-608
captions were in a TS file, but they're actually in an MP4 (which is
possibly obvious given DASH only supports MP4). This change includes
container info in the `EventLogger` `tracks` output.

PiperOrigin-RevId: 592192752
(cherry picked from commit 6853ffccae)
2024-01-09 12:17:48 +00:00
ibaker
5d7c9142ba Add Widevine license renewal example to demo app
PiperOrigin-RevId: 592182371
(cherry picked from commit 0b8a9a2ca4)
2024-01-09 12:17:48 +00:00
rohks
6236fd38d0 Fix sending negative bufferedDurationUs to CmcdData.Factory
When track is changed during playback, `playbackPositionUs` may be in middle of a chunk and `loadPositionUs` should be the start of that chunk. In this situation `loadPositionUs` can be less than the current `playbackPositionUs`, resulting into negative `bufferedDurationUs`. It translates to having no buffer and hence we should send `0` for `bufferedDurationUs` when creating new instances of `CmcdData.Factory`.

Issue: androidx/media#888

#minor-release

PiperOrigin-RevId: 591099785
(cherry picked from commit 7f6596bab2)
2024-01-09 12:17:48 +00:00
tonihei
4231a1d183 Use different wraparound assumptions for duration readers
The timestamp adjuster also estimates the number of wraparounds
of the 90Khz TS timestamp. It does that by assuming that a new
timestamp is always close to the previous one (in either direction).

This logic doesn't always work for duration estimates because the
timestamp at the end of the media is not close to the one at the
beginning and it may also never be less than the one at the beginning.

This can be fixed by introducing a new estimation model that assumes
the new timestamp is strictly greater than the previous one without
making the assumption that it has to be close to it.

Issue: androidx/media#855

#minor-release

PiperOrigin-RevId: 590936953
(cherry picked from commit 01578780a6)
2024-01-09 12:17:48 +00:00
bachinger
09d30a160e Fix broadcasting notifyChildrenChanged for legacy controllers
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
(cherry picked from commit 4974f960e7)
2024-01-09 12:17:48 +00:00
Copybara-Service
c8a403edcf Merge pull request #753 from stevemayhew:p-fix-issue-9347
PiperOrigin-RevId: 590862514
(cherry picked from commit ab296ef686)
2024-01-09 12:17:39 +00:00
ibaker
33a51906f9 Combine 'matching' versions in media3 bug template
#minor-release

PiperOrigin-RevId: 590586491
(cherry picked from commit 9a766161ee)
2024-01-09 12:11:49 +00:00
Copybara-Service
7d564f8571 Merge pull request #864 from v-novaltd:dsparano-exo129_2
PiperOrigin-RevId: 590234505
(cherry picked from commit f465efeefd)
2024-01-09 12:11:49 +00:00
ibaker
5001f70b3d Fix VorbisComment.populateMediaMetadata key comparison to ignore case
Issue: androidx/media#876

#minor-release

PiperOrigin-RevId: 590215918
(cherry picked from commit 5580b78b13)
2024-01-09 12:11:49 +00:00
Copybara-Service
504bcd804f Merge pull request #867 from equeim:ndk-r26
PiperOrigin-RevId: 590142275
(cherry picked from commit 27f437b65a)
2024-01-09 12:11:49 +00:00
samrobinson
89baa96e32 Fix handling of repeated EOS in SilenceSkippingAudioProcessor.
Issue: androidx/media#712
PiperOrigin-RevId: 589882412
(cherry picked from commit 90a0cbdf3d)
2024-01-09 12:11:49 +00:00
ibaker
e509db273d Fix handling of multiple HEVC tracks in JPEG motion photos
The MP4 data in JPEG motion photos can contain multiple `video/hevc` tracks, but only the first is at a playable frame rate while the others are low-fps, high-res tracks designed for specific use-cases (not direct video playback).

ExoPlayer currently selects the unplayable track by default, because it
has a higher resolution. This change introduces a flag to
`Mp4Extractor` that results in the first video track being marked as
`ROLE_FLAG_MAIN`, and all subsequent video tracks `ROLE_FLAG_ALTERNATE`
- this then results in the playable lower-res track being selected by
default.

PiperOrigin-RevId: 589832072
(cherry picked from commit 5266c71b3a)
2024-01-09 12:11:46 +00:00
tofunmi
7df03f381d TransformerEndToEndTest: replace /*testId=*/ with variable
PiperOrigin-RevId: 589765715
(cherry picked from commit 00d5b6ec99)
2024-01-09 12:08:20 +00:00
ibaker
482d5d69d5 Add extractor and playback tests for Pixel JPEG motion photo
This image has two video tracks in the MP4 data, one is a 'real' video
which we want to play by default, and the other is a low-fps video track
which isn't intended to be directly played, it's encoded in HEVC for
compression and decoding efficiency.

This test demonstrates ExoPlayer's current behaviour default extraction
and playback, which results in selecting the high-res, low-fps track
(actually single sample in this example), instead of playing the actual
video.

PiperOrigin-RevId: 588068908
(cherry picked from commit 6360082b87)
2024-01-09 11:03:33 +00:00
ibaker
ea72856ac8 Add Robolectric e2e test support for HEVC content
PiperOrigin-RevId: 588055594
(cherry picked from commit d4fe3fe318)
2024-01-09 11:03:33 +00:00
Googler
c314123298 Fix nullability issue in MediaControllerImplLegacy
PiperOrigin-RevId: 588035411
(cherry picked from commit e0f1783a54)
2024-01-09 11:03:33 +00:00
michaelkatz
03eae4f9ac Limit processing Opus decode-only frames by seek-preroll in offload
As Opus decoders skip some bytes prior to playback during a seek, the renderer for bypass playback should send samples to the decoder even if they would be decode-only. However, the renderer should not send samples with time preceding that range. This change adds that constraint.

#minor-release

PiperOrigin-RevId: 588014983
(cherry picked from commit d1e38abf93)
2024-01-09 10:48:33 +00:00
tonihei
57187aa899 Map VORBIS channel layout to Android layout
Both the extension OPUS decoder and the OMX/C2 MediaCodec
implementations for OPUS and VORBIS decode into the channel
layout defined by VORBIS. See
https://www.xiph.org/vorbis/doc/Vorbis_I_spec.html#x1-140001.2.3

While this is technically correct for a stand-alone OPUS or VORBIS
decoder, it doesn't match the channel layout expected by Android.
See https://developer.android.com/reference/android/media/AudioFormat#channelMask

The fix is to apply the channel mapping after decoding if needed.
Also add e2e tests with audio dumps for the extension renderer,
including a new 5.1 channel test file.

Issue: google/ExoPlayer#8396

PiperOrigin-RevId: 588004832
(cherry picked from commit b1541b096f)
2024-01-09 10:48:31 +00:00
Copybara-Service
6f8249184b Merge pull request #942 from datdoantelus:CC_708_parser_fix
PiperOrigin-RevId: 596836615
2024-01-09 00:25:58 -08:00
huangdarwin
c6b51003d3 Effect: Allow updating inputColorInfo between streams in VFP.
Whenever the inputColorInfo updates, update the samplingGlShaderProgram.

Also, allow either SDR or gamma2.2 to be used for HDR->SDR tone-mapping
`outputColorInfo` request. This is required because we can't update the
`outputColorInfo`, but plan to always use gamma2.2 for `outputColorInfo` in the
future.

This allows VideoFrameProcessor to work as is for exoplayer previewing, but
only when not seeking. As we haven't plumbed the per-stream inputColorInfo from
ExoPlayer down to VFP.registerInputStream, follow-up CLs will be needed to
properly support previewing with changing inputColorInfo.

PiperOrigin-RevId: 596627890
2024-01-08 10:09:04 -08:00
ibaker
483426ad7b MCR: Ensure mediaCrypto and codec are atomically non-null
`mediaCrypto` is initialized before `codec` in
`maybeInitCodecOrBypass`. Before this change, it was possible for
`maybeInitCodecOrBypass` to complete with `mediaCrypto != null` and
`codec == null`, in particular if it was run as part of clearing the
player surface (since in that case, no video codec is initialized).
This inconsistent state then causes issues during a later invocation of
`maybeInitCodecOrBypass`, when `mediaCrypto` is still non-null, and
`mediaCryptoRequiresSecureDecoder = true`, but the
content has been changed to unencrypted with no associated DRM session.
This results in a playback error, because a secure decoder is
initialized but there's no DRM session available to work with it.

This change ensures that when `maybeInitCodecOrBypass` completes,
either both `mediaCrypto != null` and `codec != null` (i.e. codec
initialization was completed) or `mediaCrypto == null` and
`codec == null` (i.e. codec initialization was not completed). We also
ensure that when nulling out `mediaCrypto` we also set
`maybeInitCodecOrBypass = false`. A later change should be able to
demote `maybeInitCodecOrBypass` from a field to a local in order to
remove any risk of that part of state becoming out of sync. This
resolves the issue, because during the second invocation of
`maybeInitCodecOrBypass` an insecure decoder is now (correctly)
initialized and the unencrypted content is successfully played.

#minor-release

PiperOrigin-RevId: 587713911
(cherry picked from commit 913f6da083)
2024-01-08 16:40:28 +00:00
ibaker
fa268cf84d Don't include null text or bitmaps in Cue.toBundle()
`fromBundle` doesn't distinguish between `FIELD_BITMAP` and `FIELD_TEXT`
being present with a null value, or being absent, so we might as well
avoid including them when the value is null.

I've separated this from a later change to add
`Cue.toSerializableBundle` which will also skip setting a bitmap value
into the `Bundle` if `this.bitmap == null`. This is partly because it
results in changes to a lot of extractor test dump files, and it's
easier to review that as a separate change.

PiperOrigin-RevId: 586626141
(cherry picked from commit 28c210686f)
2024-01-08 16:16:21 +00:00
christosts
3f3287aba3 Exit early progressive loads if the load task is canceled
Add an check when loading progressive media in case the load
is canceled. If the player is released very early, the progressive
media period may carry on with the initial loading unnecessarily.

PiperOrigin-RevId: 586288385
(cherry picked from commit 3d1d8f4439)
2024-01-08 15:55:36 +00:00
tofunmi
d68c36e082 Update emulator device names
PiperOrigin-RevId: 585682881
(cherry picked from commit b598c96c2f)
2024-01-08 15:55:36 +00:00
Copybara-Service
db648316ed Merge pull request #837 from superjohan:fix/android-14-clearkey
PiperOrigin-RevId: 585639025
(cherry picked from commit 5f27b18210)
2024-01-08 15:33:26 +00:00
andrewlewis
19ee78729c Restrict operating rate workaround to SM8550
PiperOrigin-RevId: 585613041
(cherry picked from commit e84a13fb54)
2024-01-08 15:33:26 +00:00
andrewlewis
710c1b9053 Work around codec frame rate issues in Redmi Note 9 Pro
The decoder and encoder won't accept high values for frame rate, so avoid
setting the key when configuring the decoder, and set a default value for the
encoder (where the key is required).

Also skip SSIM calculation for 4k, where the device lacks concurrent decoding
support.

PiperOrigin-RevId: 585604976
(cherry picked from commit 8b38b34b9f)
2024-01-08 15:33:26 +00:00
andrewlewis
97c9e234d2 Avoid value close to overflow for KEY_OPERATING_RATE
Using `Integer.MAX_VALUE` risks causing arithmetic overflow in the codec
implementation.

Issue: androidx/media#810

PiperOrigin-RevId: 585104621
(cherry picked from commit ad40db4489)
2024-01-08 15:33:24 +00:00
ibaker
36f634d8d1 Fix typo in DashManifestParser
PiperOrigin-RevId: 585017285
(cherry picked from commit 479344d74e)
2024-01-08 15:31:29 +00:00
tonihei
4234bc7091 Remove redundant ) in Javadoc
PiperOrigin-RevId: 584910697
(cherry picked from commit 85a54e2e19)
2024-01-08 15:31:29 +00:00
Copybara-Service
33484b0239 Merge pull request #707 from equeim:ffmpeg-6.0
PiperOrigin-RevId: 584893190
(cherry picked from commit 45b51d8c97)
2024-01-08 15:31:27 +00:00
bachinger
5e86c4c20b Add session extras to the state of the controller
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
(cherry picked from commit a063d137b4)
2024-01-08 15:26:08 +00:00
christosts
124eb31fd2 MidiExtractor: mark only the first sample as key-frame
This change fixes a bug with seeking forward in MIDI. When seeking forward,
the progressive media period attempts to seek within the sample queue, if a
key-frame exists before the seeking position. With MIDI, however, we can
only skip Note-On and Note-Off samples and all other samples must be sent
to the MIDI decoder.

When seeking outside the sample queue, the MidiExtractor already
instructs the player to start from the beginning of the MIDI input. With
this change, only the first output sample is a key-frame, thus the
progressive media period can no longer seek within the sample queue and
is forced to seek from the MIDI input start always.

Issue: androidx/media#704

PiperOrigin-RevId: 584321443
(cherry picked from commit ec08db458e)
2024-01-08 15:26:03 +00:00
tonihei
c9f6ad0398 Avoid clipping live offset override to min/max offsets
The live offset override is used to replace the media-defined
live offset after user seeks to ensure the live adjustment adjusts
to the new user-provided live offset and doesn't go back to the
original one.

However, the code currently clips the override to the min/max
live offsets defined in LiveConfiguration. This is useful to
clip the default value (in case of inconsistent values in the media),
but the clipping shouldn't be applied to user overrides as
the player will then adjust the position back to the min/max
and doesn't stay at the desired user position.

See 2416d99857 (r132871601)

PiperOrigin-RevId: 584311004
(cherry picked from commit af0282b9db)
2024-01-08 15:21:28 +00:00
bachinger
ea642a41e9 Add test case to test position conversion when POSITION_UNKNOWN
PiperOrigin-RevId: 584261559
(cherry picked from commit ec478138ba)
2024-01-08 15:18:39 +00:00
bachinger
5752a09a40 Return empty timeline when media info is null
Issue: androidx/media#708
PiperOrigin-RevId: 584054624
(cherry picked from commit 167f50a9ca)
2024-01-08 15:18:39 +00:00
rohks
0038355590 Use .test top level domain for test URI
PiperOrigin-RevId: 583951327
(cherry picked from commit ffbaa090aa)
2024-01-08 15:18:38 +00:00
rohks
aab1c9ada1 Populate MediaMetadata.extras to MediaMetadataCompat
Ensures backward compatibility.

Issue: androidx/media#802
PiperOrigin-RevId: 583425114
(cherry picked from commit 6df240877c)
2024-01-08 15:18:38 +00:00
tonihei
69884e764e Workaround layout problems with Material Design
In some contexts (e.g. BottomSheetDialogFrament), Material Design
themes will override the default of singleLine=false to true. This
causes layout problems because the forward/rewind buttons are no
longer visible with singleLine=true.

This problem can be avoided by explicitly requesting the default
value of false in our layout files.

Issue: androidx/media#511

#minor-release

PiperOrigin-RevId: 582604131
(cherry picked from commit 310e2edcca)
2024-01-08 15:18:38 +00:00
ibaker
b9722764ac Update recommended way to suppress @UnstableApi errors in lint.xml
#minor-release

PiperOrigin-RevId: 582599098
(cherry picked from commit bd7615c0b8)
2024-01-08 15:18:38 +00:00
andrewlewis
7901d1cc0a Expand frame drop workaround to Realme C11
Based on on-device testing, this device seems to have the same issue as Moto G (20) where frames are dropped despite configuring the decoder not to drop frames.

PiperOrigin-RevId: 581943805
(cherry picked from commit 330713f687)
2024-01-08 15:18:36 +00:00
tianyifeng
21461abc1c Parse "f800" as channel count of 5 for Dolby in DASH manifest
Issue: androidx/media#688
PiperOrigin-RevId: 581908905
(cherry picked from commit 79711ebd3f)
2024-01-08 15:08:53 +00:00
Googler
2db9da5c1d Don't crash when receiving a bad playback state
PiperOrigin-RevId: 580942377
(cherry picked from commit e79809616c)
2024-01-08 14:54:21 +00:00
jbibik
f189af5632 Remove old pre-releases from the github bug template
PiperOrigin-RevId: 580554963
(cherry picked from commit 508582d56c)
2024-01-08 14:54:21 +00:00
tonihei
d8d552af59 Fix proguard rule to also keep referenced class name
PiperOrigin-RevId: 579234050
(cherry picked from commit bce82bdc75)
2024-01-08 14:54:17 +00:00
tonihei
40094273ea Fix access to stale ByteBuffer in FfmpegAudioDecoder
The native code can now reallocate the buffer if it needs to grow
its size, so we have to reacquire a reference in the Java code to
avoid accessing a stale instance.

This fixes a bug introduced by 8750ed8de6.

PiperOrigin-RevId: 578799862
(cherry picked from commit ae6f83d298)
2024-01-08 14:51:05 +00:00
ibaker
2f4d475b5c Split media1/media3 conversion methods out of MediaUtils
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
(cherry picked from commit 72b7019578)
2024-01-08 14:51:05 +00:00
ibaker
07258aa373 Add warning log if DASH manifest contains incomplete ClearKey info
Unfortunately we can't fail any more obviously at this point, because
manifests often contain config for multiple DRM schemes, and when
parsing the manifest we don't know which scheme is going to be used for
playback. It would be unreasonable to fail playback due to incomplete
ClearKey config if playback was otherwise going to succeed using e.g.
Widevine.

* Issue: androidx/media#777
* Issue: androidx/media#563
* Issue: google/ExoPlayer#9169

#minor-release

PiperOrigin-RevId: 578491484
(cherry picked from commit d42c23706b)
2024-01-08 14:51:05 +00:00
tianyifeng
2237f4902d Put the custom keys in MediaMetadataCompat to MediaMetadata.extras
PiperOrigin-RevId: 578473874
(cherry picked from commit 84022eacc5)
2024-01-08 14:51:05 +00:00
ibaker
fe8bbcaa12 Remove stray parentheses from release notes
PiperOrigin-RevId: 577809964
(cherry picked from commit db1ab1dcf3)
2024-01-08 14:50:26 +00:00
ibaker
a017080353 Bump okhttp dependency to 4.12
Issue: androidx/media#768
PiperOrigin-RevId: 577208115
(cherry picked from commit e8cca688ad)
2024-01-08 13:56:59 +00:00
michaelkatz
79ce4f1c73 Fallback to legacy sizerate check for H264 if CDD PerfPoint check fails
Some devices supporting Performance Points for decoder coverage are missing coverage over the CDD requirements for H264. For these cases ExoPlayer should fall back to legacy resolution and frame rate support checks. If there is an H264 stream evaluated as a `PerformancePointCoverageResult` of `COVERAGE_RESULT_NO`, then ExoPlayer checks for coverage of the [720p CDD requirement](https://source.android.com/docs/compatibility/10/android-10-cdd#5_3_4_h_264).

Issue: google/ExoPlayer#10898

Issue: androidx/media#693
PiperOrigin-RevId: 575768836
(cherry picked from commit 4515a0c3f2)
2024-01-08 13:56:42 +00:00
ibaker
77f311917f Play clear samples in DRM content without keys by default
This behavior was previously available as opt-in via
`MediaItem.DrmConfiguration.Builder.setPlayClearContentWithoutKey` and
`DefaultDrmSessionManager.Builder.setPlayClearSamplesWithoutKeys`. This
change flips the default of both these properties to true.

This should speed up the time for playback to start when playing DRM
content with a 'clear lead' of unencrypted samples at the start.
Previously playback would wait until the keys for the later encrypted
samples were ready. The new behaviour could result in mid-playback
stalls/rebuffers if the keys are not ready yet by the transition from
clear to encrypted samples, but this is not really a regression since
previously playback wouldn't have started at all at this point.

PiperOrigin-RevId: 595992727
2024-01-05 07:46:25 -08:00
ibaker
62f6c64a91 Rename test.mp3 test asset to test-cbr-info-header.mp3
This file is CBR encoded with LAME, so it has an `Info` header (the CBR
equivalent to `Xing`).

A follow-up change will use this file in `Mp3ExtractorTest`.

Issue: androidx/media#878
PiperOrigin-RevId: 595938327
2024-01-05 02:31:20 -08:00
ibaker
95e742948c Clarify docs on Player.setMediaItem(s) and replaceMediaItem(s)
These methods sound similar, but have different behaviour. This change
tries to make the distinction clearer, and sign-post from one to the
other.

#minor-release

Issue: androidx/media#910
PiperOrigin-RevId: 595701540
2024-01-04 07:41:34 -08:00
bachinger
5c50b27e8f Return null if media notification controller Future is not done
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
2024-01-04 07:35:54 -08:00
ibaker
1cb6865884 Remove CEA-6/708 support from DefaultSubtitleParserFactory
`Cea608Parser` and `Cea708Parser` don't currently work correctly on
their own without the re-ordering of input buffers implemented in
`CeaDecoder`, and it's not clear how we can properly do this re-ordering
during extraction. This change ensures that if 'parse subtitles
during extraction' is enabled, CEA-6/708 subs will be passed through
without transcoding and can then be decoded during rendering by
`Cea6/708Decoder`.

PiperOrigin-RevId: 595658628
2024-01-04 03:48:41 -08:00
Copybara-Service
8eda9f2ed2 Merge pull request #369 from Tolriq:fix_invalid_frames
PiperOrigin-RevId: 595650068
2024-01-04 03:02:29 -08:00
rohks
5970d2d586 Document and remove check for C.TIME_UNSET when consuming data in TS
PiperOrigin-RevId: 595647795
2024-01-04 02:50:04 -08:00
Ian Baker
0b482ef58c Remove columnLock, columnCount (unimplemented) and rowLock (always true)
Also add a release note and simplify the test by removing the garbage
prefix and suffix.
2024-01-03 17:49:35 +00:00
Ian Baker
04751a1cdb Format with google-java-format 2024-01-03 17:36:55 +00:00
datdoantelus
a58ddcfa23 Update test comment. 2024-01-03 17:36:55 +00:00
datdoantelus
28eb55c077 Use skipBits(2) instead of readBits for ignored bits.
Add singleServiceAndWindowDefinition_ignoreRowLock test to Cea708ParserTest
2024-01-03 17:36:55 +00:00
datdoantelus
8b39f7e287 Ignore rowLock and columnLock values as specified by ANSI/CTA-708-E S-2023 document (section 8.4.7) 2024-01-03 17:36:55 +00:00
Ian Baker
f935f59eaa Improve logging by including full stack trace, and add release note 2024-01-03 16:14:37 +00:00
Ian Baker
820278c564 Format with google-java-format 2024-01-03 15:49:43 +00:00
Tolriq
de772cfbf0 Catch errors and OOM when decoding ID3 frames.
Invalid frames have no impact on ExoPlayer ability to play the media and should not fail on errors.
Some tools can add 100Mb images in the tags that will trigger recoverable OOM with this fix.
2024-01-03 15:49:43 +00:00
samrobinson
c230414bd3 Set the default audio encoder bitrate in DefaultEncoderFactory.
Matches the approach for video frame rate.

PiperOrigin-RevId: 595385930
2024-01-03 06:37:16 -08:00
sheenachhabra
3ecf8732ba Add comments for skipping input files in Mp4Muxer tests
PiperOrigin-RevId: 595356012
2024-01-03 03:50:46 -08:00
bachinger
b11c0c19b0 Declare demo service as MediaLibraryService
The `PlaybackService` of the demo app is declared
as `androidx.media3.session.MediaSessionService` instead
of `androidx.media3.session.MediaLibraryService`. While
this technically works, its confusing to do that in the
demo app.

Generally, apps that declare the legacy
`android.media.browse.MediaBrowserService` should also
declare `androidx.media3.session.MediaLibraryService`
and the demo app should reflect this common case.

Issue: androidx/media#672
PiperOrigin-RevId: 595320994
2024-01-03 00:51:17 -08:00
ibaker
258ffa68b5 Add tests with out-of-order CEA-608 input buffers
The `Cea608DecoderTest` added here fails if re-ordering is removed from
`CeaDecoder`.

The `Cea608ParserTest` is added with `@Ignore` because there's currently
no re-ordering support in this part of the subtitle handling pipeline
(partly because there's no concept of 'current playback time', meaning
it's hard to know **when** to re-order).

PiperOrigin-RevId: 595320205
2024-01-03 00:45:31 -08:00
ibaker
7b450f0d0a Fix limit calculation to include offset in Cea6/708Parser.parse
PiperOrigin-RevId: 595007390
2024-01-01 20:22:27 -08:00
sheenachhabra
5149cc60ac Skip Mp4Muxer tests for unwanted input files
PiperOrigin-RevId: 594478028
2023-12-29 11:10:26 -08:00
bachinger
426bc94090 Don't set negative values to setWhen()
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
2023-12-29 06:56:02 -08:00
sheenachhabra
846ace16aa Allow creating fragmented MP4 file via demo app
PiperOrigin-RevId: 594435072
2023-12-29 04:39:04 -08:00
sheenachhabra
27ae6d974e Allow creating fragmented MP4 file via InAppMuxer
PiperOrigin-RevId: 594431665
2023-12-29 04:15:01 -08:00
sheenachhabra
e0257f403f Implement fragmented MP4 (fMP4) in the Mp4Muxer
Changes includes;
1. Public API to enable fMP4 and to pass fragment duration.
2. Added `FragmentedMp4Writer`.
3. Added logic to create fragments based on given fragment duration.
4. Write "moov" box only once in the beginning.
3. Add all the required boxes for current implementation.
4. Unit tests for all the new boxes.
5. E2E test for generating fMP4.

Note: The output file is un seek-able with this first implementation.
PiperOrigin-RevId: 594426486
2023-12-29 03:39:38 -08:00
sheenachhabra
b0e00a7d28 Fix ByteBuffer.array() warning
PiperOrigin-RevId: 594274620
2023-12-28 10:07:47 -08:00
sheenachhabra
1609928242 Throw exception when B-frames are written to Mp4Muxer
Mp4Muxer does not support out of order B-frames. Currently it
silently writes out of order B-frames, producing an invalid file (with
negative sample durations).

Although `Mp4Extractor` is somehow able to process this invalid file and
`Exoplayer` is able to play it but that is unexpected.

The `sample.mp4` test file contains B frames. Other test files does not
contain `H264 video + AAC audio` format hence created a new test file by
running `sample.mp4` via `Transformer` after applying some effects.

PiperOrigin-RevId: 594016144
2023-12-27 08:32:36 -08:00
tofunmi
0ab7bafa87 Migrate Gaussian Blur Effect to media3.
PiperOrigin-RevId: 593164068
2023-12-22 14:13:19 -08:00
tofunmi
e3056dacac Rename Mp4MetadataInfo to mp4Info
PiperOrigin-RevId: 593143940
2023-12-22 11:10:30 -08:00
tofunmi
4fc11a98a1 ignore dropSamplesBeforeFirstVideoSample in audio-only streams
PiperOrigin-RevId: 593126632
2023-12-22 08:54:29 -08:00
ibaker
64231ee079 Tweak SubtitleTranscodingTrackOutput.ensureSampleDataCapacity
This more closely matches the intended, documented behaviour of this
method. The previous implementation was incorrectly checking
`sampleDataEnd + newSampleSize`, but it's more correct to compare
`existingSampleDataLength + newSampleSize`, in order to handle the
case of non-zero `sampleDataStart`. We've already checked above whether
`newSampleSize` fits after `sampleDataEnd` without growing or
reshuffling the array, so no need to basically repeat that check.

In the case of handling one sample at a time, the previous
implementation resulted in `sampleData` growing by `sampleSize`
**every time** the pointers reached the end. With the new check for
`sampleDataStart == sampleDataEnd`, this is avoided by always writing
each new sample at the start of the array (because the previous sample
has already been consumed), meaning `sampleData` remains equal to
`sampleSize` without growing.

PiperOrigin-RevId: 593119927
2023-12-22 08:06:30 -08:00
tofunmi
7e12b9e15f Add rough progress updates in trim optimization
PiperOrigin-RevId: 593116025
2023-12-22 07:37:23 -08:00
tofunmi
1632f37d70 Transformer: Add api to drop audio samples before the first video frame
fix for Issue: androidx/media#829

Manual Testing: Viewed the transformer output file of previously problematic case in Exoplayer, Chrome, VLC, Quicktime and Safari and all showed the issue not to occur anymore. The newly produced output file can be found at https://github.com/androidx/media/assets/42352357/fdf105c1-9550-422f-b088-7900f655ac78

PiperOrigin-RevId: 593104752
2023-12-22 06:18:07 -08:00
ibaker
a496bbd777 Add parentheses to fix UnexpectedLoaderException message logic
These were missing in 5211ff0dc1

Without these, the `": null"` is still logged (but the `"Unexpected
IllegalStateException"` bit is not), because the **whole** string
concatenation is compared to null as the boolean condition of the
ternary, and this condition is always false (the result of a string
concatentation is never `null`) i.e. (with excess parentheses for
clarity):

```
(("Unexpected " + cause.getClass().getSimpleName() + cause.getMessage()) != null)
    ? ": " + cause.getMessage()
    : ""
```

Also add a test because obviously this isn't as simple as I'd thought.

PiperOrigin-RevId: 593079975
2023-12-22 03:42:42 -08:00
simakova
09bde8053d Update method description for setEffects in Composition
PiperOrigin-RevId: 593071081
2023-12-22 02:51:52 -08:00
andrewlewis
ef7842dd88 Fix typo
PiperOrigin-RevId: 593061829
2023-12-22 02:04:30 -08:00
andrewlewis
1845a4ae69 Expand operating rate workaround to T612 chipset
PiperOrigin-RevId: 592916187
2023-12-21 11:52:35 -08:00
ibaker
5211ff0dc1 Only append non-null exception messages in UnexpectedLoaderException
The previous code led me to misread this stack trace as a null pointer
exception, but it's really an index out of bounds exception:

```
Caused by: androidx.media3.exoplayer.upstream.Loader$UnexpectedLoaderException: Unexpected IllegalArgumentException: null
  at androidx.media3.exoplayer.upstream.Loader$LoadTask.run(Loader.java:435)
  at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145)
  at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:644)
  at java.lang.Thread.run(Thread.java:1012)
Caused by: java.lang.IllegalArgumentException
  at androidx.media3.common.util.Assertions.checkArgument(Assertions.java:40)
  at androidx.media3.common.util.ParsableByteArray.setPosition(ParsableByteArray.java:164)
  at androidx.media3.extractor.text.cea.Cea608Parser.parse(Cea608Parser.java:440)
```

PiperOrigin-RevId: 592876546
2023-12-21 09:09:41 -08:00
huangdarwin
0ed19937d3 Test: Remove setInputColorInfo from VFP test runner.
Instead, for input videos, use the colorInfo provided by the extractor. Similarly, for input images, use sRGB, the only color currently in use.

Textures do still need the input ColorInfo provided though.

PiperOrigin-RevId: 592875967
2023-12-21 09:06:55 -08:00
tofunmi
57d00fcca0 Rename crow_emulator_transformer_output
PiperOrigin-RevId: 592873355
2023-12-21 08:56:48 -08:00
Copybara-Service
966b5178b6 Merge pull request #914 from cemrich:366-forward-time-wrong
PiperOrigin-RevId: 592871532
2023-12-21 08:48:24 -08:00
andrewlewis
7d11ee7538 Optionally notify codec init in default decoder factory
Replace the event for notifying fallback to cover codec initialization in
general (but keeping the list of errors).

Add a flag to control whether to try non-primary codecs, with the same
documentation as the similar flag in ExoPlayer's renderer.

Make the class final as it shouldn't be necessary to subclass it.

PiperOrigin-RevId: 592869868
2023-12-21 08:42:44 -08:00
tofunmi
3081ceb179 Remove the matchInitializationData option from TransformerInternal
Essentially a manual revert of ba0724ca78

PiperOrigin-RevId: 592869049
2023-12-21 08:38:58 -08:00
ibaker
f36ab87b38 Fix DASH CEA-608 parsing during extraction
This is similar to the HLS fix in 770ca66fbc

Similar to HLS, the original problem here was **not** modifying the
`Format` for caption tracks
embedded into the video stream. I tried just updating the format in
both places, but that caused new failures because the new
('transcoded') format was then fed into `FragmentedMp4Extractor` as
part of `closedCaptionFormats`, which resulted in the CEA-608 data
being emitted from `FragmentedMp4Extractor` with the incorrect
`application/x-media3-cues` MIME type (but the bytes were actually
CEA-608), meaning the transcoding wrapper passed it through without
transcoding and decoding failed (because obviously CEA-608 bytes can't
be decoded by `CueDecoder` which is expecting a `Bundle` from
`CuesWithTiming.toBundle`.

To resolve this we keep track of the 'original' caption formats inside
`TrackGroupInfo`, so we can feed them into `FragmentedMp4Extractor`.
For all other usages in `DashMediaPeriod` we use the 'transcoded'
caption formats.

PiperOrigin-RevId: 592866262
2023-12-21 08:25:03 -08:00
sheenachhabra
60c8273521 Split Mp4Writer into an abstract class and DefaultMp4Writer
With fMP4 implementation there will be two writers `DefaultMp4Writer`
and `FragmentedMp4Writer`.

Changes includes:
1. Make Mp4Writer as an abstract class and keep only common functionality
into it.
2. Create a DefaultMp4Writer which contains existing logic to write MP4.
3. The fMP4 logic needs to access `pending sample buffer info` at various
places, so did refactoring to split List<Pair<BufferInfo, ByteBuffer>>
into two separate lists.

PiperOrigin-RevId: 592861398
2023-12-21 08:02:01 -08:00
Marc Baechinger
5be190ce4a Update release notes 2023-12-21 16:44:13 +01:00
huangdarwin
4774fa1a60 Test: Update tone mapping capabilities check output format.
Checking the output format's mime type may skip tests more often than we'd like,
because we may desire using a lower-spec output mimetype than what's passed in, if
based on the input's HDR mimetype value.

Therefore, update this output format to null, for tone-mapping tests

PiperOrigin-RevId: 592855713
2023-12-21 07:30:07 -08:00
Christine Coenen
793b27af3b Fix forward and rewind button texts cut off with material theme applied 2023-12-21 16:28:38 +01:00
rohks
639d380762 Fix the check for clang complier in FFmpeg build file
Also updated the `README` file to accurately specify the use of NDK r23c and the default setting `ANDROID_ABI=21` for NDK r26b.

PiperOrigin-RevId: 592845796
2023-12-21 06:35:37 -08:00
sheenachhabra
0b88e09a82 Improve durationsVuForStts method implementation
Issues with the current implementation
1. The implementation is unnecessarily complicated and can be
easily simplified.To make all the tracks start from the same time,
its only the first sample that require some timestamp adjustments
but the current implementation shifts all the timestamps. Since method
calculates the `sample duration`, shifting all the timestamps has no effect
as such.
2. The implementation always forced first sample to start at 0. But when we
want to use same method for `Fragmented MP4` then it will look inaccurate
as we will call this method for different `fragments` and each `fragment`
will not start from 0 presentation time. Although the output will be same
since this method returns `duration` and not the `timestamps`.
3. As per previous implementation if there is just one sample then
its duration is made equals to its presentation time, which looks incorrect.
With new changes, if a single sample is passed then its duration will always
be 0 irrespective of specified last sample duration behaviour.

PiperOrigin-RevId: 592826612
2023-12-21 04:45:43 -08:00
okunhardt
250fc80419 Move HttpEngineDataSource to the DataSource library.
Since HttpEngineDataSource does not have any external dependencies, it does not need to be in its own package.

PiperOrigin-RevId: 592623750
2023-12-20 12:10:36 -08:00
Googler
e25e497227 Make DefaultDecoderFactory try multiple formats before giving up
PiperOrigin-RevId: 592622544
2023-12-20 12:07:19 -08:00
tonihei
98519931e7 Split creation of AudioCapabilitiesReceiver from instance access
getAudioCapabilities currently creates the receiver and returns
the current capabilities. This is error-prone because the
capabilities are also available as a class field.

This can made cleaner by letting the method just create the receiver
and all access to the capabilities can be made via class field.

PiperOrigin-RevId: 592591590
2023-12-20 10:12:27 -08:00
ibaker
770ca66fbc Fix HLS CEA-608 when parsing during extraction
HLS distinguishes between 'subtitles' (WebVTT or TTML distributed in
separate files with their own playlist) and 'captions' (CEA-608 or 708,
distributed muxed into the video file).

The format transformation added in 7b762642db
only applies to subtitles and not captions. This change makes the same
transformation for caption formats.

This resolves an error like:

```
SampleQueueMappingException: Unable to bind a sample queue to TrackGroup with MIME type application/cea-608.
```

Also add two playback tests for HLS CEA-608, one that parses during
decoding (old way) and one during extraction (new way). Adding these
tests is what alerted me to this issue.

PiperOrigin-RevId: 592571284
2023-12-20 08:52:39 -08:00
tofunmi
4ce47ccdd3 MuxerWrapper: remove unnecessary volatiles
PiperOrigin-RevId: 592569012
2023-12-20 08:37:03 -08:00
tonihei
59f01388a6 Use platform constants for PCM 24/32 bit encoding
These constants are used when setting up the AudioTrack
and should match the definition in the platform.

PiperOrigin-RevId: 592564644
2023-12-20 08:16:35 -08:00
ibaker
8b9bf5e7cd Add DASH CEA-608 playback test
This was generated by combining the existing `ts/bbb_2500ms.ts` test
asset and a temporary `.srt` file using
https://cloud.google.com/transcoder/docs/how-to/captions-and-subtitles

This doesn't directly reproduce the problem fixed by
7ca26f898d,
because the CEA-608 subs are structured differently to the stream I
discovered the problem with (from Issue: androidx/media#887). However this test
does fail if that fix is reverted after
486230fbd7.

I'm also not able to repro the character duplication reported in
Issue: androidx/media#887 by just changing the manifest in this CL. I'm not yet
sure on the exact differences between the stream provided on GitHub
and this stream.

This stream does provide some regression protection, because it
currently fails with 'new' subtitle parsing
(`DashMediaSource.Factory.experimentalParseSubtitlesDuringExtraction(true)`),
though I'm not sure on the exact reason for that yet.

PiperOrigin-RevId: 592476328
2023-12-20 01:13:21 -08:00
bachinger
36b7a49d52 Use factory to create media period holders in the queue
This is a refactoring that allows the `MediaPeriodQueue` to
create media period holders without all the collaborators
being passes in to `enqueueNextMediaPeriodHolder(...)`.

The factory is presumably also helpful in unit test to
know whether and when exactly a holder is created in
the preloading process.

PiperOrigin-RevId: 592301400
2023-12-19 11:55:13 -08:00
ibaker
486230fbd7 Throw a clear error from Cea608/708Parser.parseToLegacySubtitle
This would have immediately exposed the mistakes fixed by
7ca26f898d

Issue: androidx/media#904
PiperOrigin-RevId: 592244943
2023-12-19 08:34:37 -08:00
bachinger
8940900c69 Optimize short form content demo app
PiperOrigin-RevId: 592225900
2023-12-19 07:08:27 -08:00
ibaker
7ca26f898d Fix 'legacy' CEA-608 and CEA-708 to use the Decoder impls
We deliberately left `Cea608Decoder` and `Cea708Decoder` intact when
creating the respective `SubtitleParser` implementations (in
27caeb8038
and
94e45eb4ad
respectively).

However we didn't correctly change the behaviour of
`SubtitleDecoderFactory.DEFAULT` in order to use these 'legacy'
implementations. We firstly left the `Cea608Decoder` instantiation
**after** the `DefaultSubtitleParserFactory.supportsFormat()` check,
meaning that code would never be reached (since `supportsFormat` now
returns true for CEA-608). Then in the second change (which was supposed
to only be about CEA-708) we removed all instantiations of **both**
`Cea608Decoder` and `Cea708Decoder`. This change puts the decoder
instantiations back and moves them above the
`DefaultSubtitleParserFactory.supportsFormat` check, meaning they will
be used in preference to `DelegatingSubtitleDecoder`.

This resolves the immediately-disappearing subtitles tracked by
Issue: androidx/media#904.
PiperOrigin-RevId: 592217937
2023-12-19 06:32:36 -08:00
tonihei
e10f96d6a6 Make some DefaultRenderersFactory methods final
These methods are just setters and not meant to be overridden.

PiperOrigin-RevId: 592193857
2023-12-19 04:38:57 -08:00
ibaker
6853ffccae Add container to Format.toLogString
While investigating Issue: androidx/media#887 I naively assumed the CEA-608
captions were in a TS file, but they're actually in an MP4 (which is
possibly obvious given DASH only supports MP4). This change includes
container info in the `EventLogger` `tracks` output.

PiperOrigin-RevId: 592192752
2023-12-19 04:33:58 -08:00
ibaker
0b8a9a2ca4 Add Widevine license renewal example to demo app
PiperOrigin-RevId: 592182371
2023-12-19 03:49:43 -08:00
christosts
3bb233a911 Misc clean-ups in ImageRenderer
Add some missing empty lines and use checkStateNotNull() everywhere.

PiperOrigin-RevId: 592173300
2023-12-19 03:06:29 -08:00
tofunmi
087c07e596 Rename OptimizationResult options
Rename options to be more accurate of what they capture

PiperOrigin-RevId: 592155563
2023-12-19 01:50:40 -08:00
tonihei
e5aa69237e Use CRYPTO_ASYNC mode for video from API 34
This allows us to remove the additional thread we create
for asynchronous buffer queuing and use a synchronized
queueing approach again.

This API looks strictly beneficial on all tested devices,
but since this code path in MediaCodec has not been used
widely, we leave an opt-out flag for now.

PiperOrigin-RevId: 591867472
2023-12-18 05:32:40 -08:00
sheenachhabra
bb7aa2fb19 Update updateMetadataEntries() method javadoc
PiperOrigin-RevId: 591858840
2023-12-18 04:45:35 -08:00
tonihei
b7c3d83e51 Forward setParameters to AsynchronousMediaCodecBufferEnqueuer
The parameters may change the decoding behavior of the
following samples and it's suprising/wrong to apply them
from another thread where we can't guarantee from which
sample they apply.

PiperOrigin-RevId: 591808760
2023-12-18 00:37:21 -08:00
huangdarwin
236bad5597 Add access control modifier to variable.
PiperOrigin-RevId: 591302601
2023-12-15 10:57:53 -08:00
huangdarwin
bde56b6b43 Effect: Move inputColorInfo javadoc to registerInputStream.
Oops, I forgot to move these in the earlier change, http://<unknown commit>.

PiperOrigin-RevId: 591300964
2023-12-15 10:52:22 -08:00
sheenachhabra
1303bfbc7c Set language field when creating MediaFormat from a Format
Currently Transformer simply omits the language field from the input
media file when writing data to the output file.

PiperOrigin-RevId: 591287481
2023-12-15 10:06:38 -08:00
huangdarwin
7579693739 Effect: Move VideoFrameProcessor inputColorInfo interface to FrameInfo.
Move `inputColorInfo` from `VideoFrameProcessor`'s `Factory.create` to `FrameInfo`,
input via `registerInputStream`.

Also, manually tested on exoplayer demo that setVideoEffects still works.

PiperOrigin-RevId: 591273545
2023-12-15 09:17:39 -08:00
tonihei
f47c4e33ec Remove experimental synchronization on async buffer queuing
PiperOrigin-RevId: 591273508
2023-12-15 09:14:52 -08:00
bachinger
29d7dd1ec9 Keep selections for preloaded adaptive sample streams
When an adaptive source has been preloaded, the track selection
of the player should possibly not override the preloaded selection
to avoid discarding preloaded data.

PiperOrigin-RevId: 591256334
2023-12-15 08:09:22 -08:00
lpribanic
1096ae9145 Write empty image byte arrays to sample queue
The number of empty image byte arrays written is one less than the
total number of tiles in the image. The empty byte arrays act as
placeholders for individual tiles inside ImageRenderer.

PiperOrigin-RevId: 591231432
2023-12-15 06:18:54 -08:00
claincly
7e65cce967 Fix first frame not force rendered
This is because currently

1. Player sets a surfaceView to render to
2. Player intializes the renderer
3. MCVR initializes the VideoSinkProvider, by extension VideoGraph

But when 1 happens, MCVR doesn't set the surfaceView on the VideoGraph because
it's not initialized. Consequently after VideoGraph is initialized, it doesn't
have a surface to render to, and thus dropping the first a few frames.

Also adds a test for first frame to verify the correct first frame is rendered.

PiperOrigin-RevId: 591228174
2023-12-15 06:01:12 -08:00
christosts
7df3e9e779 Integrate ImageRenderer with composition preview
PiperOrigin-RevId: 591218013
2023-12-15 05:01:50 -08:00
rohks
7f6596bab2 Fix sending negative bufferedDurationUs to CmcdData.Factory
When track is changed during playback, `playbackPositionUs` may be in middle of a chunk and `loadPositionUs` should be the start of that chunk. In this situation `loadPositionUs` can be less than the current `playbackPositionUs`, resulting into negative `bufferedDurationUs`. It translates to having no buffer and hence we should send `0` for `bufferedDurationUs` when creating new instances of `CmcdData.Factory`.

Issue: androidx/media#888

#minor-release

PiperOrigin-RevId: 591099785
2023-12-14 17:39:41 -08:00
huangdarwin
0baf777c96 Effect: Release FinalShaderProgramWrapper when releasing DVFP.
Otherwise, there's a memory leak of ~30MB, as this is never released.

This likely used to be considered released as part of what now became
`intermediateGlShaderPrograms`, but its release was missed after we split
`finalShaderProgramWrapper` out from the larger glShaderProgram list.

PiperOrigin-RevId: 590954785
2023-12-14 08:59:38 -08:00
ibaker
7399b7c5ce Remove @Beta comments that should have been removed in 0a016b59f7
PiperOrigin-RevId: 590940876
2023-12-14 08:04:23 -08:00
huangdarwin
97e9ed3f7b Effect: Move inputColorInfo usage to registerInputStream.
To prepare to move `inputColorInfo` from `VFP.Factory.create` to
`VFP.registerInputStream`, move all usage of `inputColorInfo` to be *after*
`registerInputStream`.

To do this, defer creation of `externalShaderProgram` instances, which require
`inputColorInfo`. However, we must still initialize `InputSwitcher` and OpenGL
ES 3.0 contexts in the VFP create, to create and request the input surface from
ExternalTextureManager.

PiperOrigin-RevId: 590937251
2023-12-14 07:50:04 -08:00
tonihei
01578780a6 Use different wraparound assumptions for duration readers
The timestamp adjuster also estimates the number of wraparounds
of the 90Khz TS timestamp. It does that by assuming that a new
timestamp is always close to the previous one (in either direction).

This logic doesn't always work for duration estimates because the
timestamp at the end of the media is not close to the one at the
beginning and it may also never be less than the one at the beginning.

This can be fixed by introducing a new estimation model that assumes
the new timestamp is strictly greater than the previous one without
making the assumption that it has to be close to it.

Issue: androidx/media#855

#minor-release

PiperOrigin-RevId: 590936953
2023-12-14 07:47:11 -08:00
bachinger
4974f960e7 Fix broadcasting notifyChildrenChanged for legacy controllers
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
2023-12-14 05:20:39 -08:00
samrobinson
84471813b6 Update TODO internal bug number.
PiperOrigin-RevId: 590884408
2023-12-14 03:43:16 -08:00
Copybara-Service
ab296ef686 Merge pull request #753 from stevemayhew:p-fix-issue-9347
PiperOrigin-RevId: 590862514
2023-12-14 02:05:35 -08:00
lpribanic
d52772dff8 Set image tile counts to what the manifest says
Vertical and horizontal tile counts inside Format used by ImageRenderer
used to be required to equal 1 and were set to 1 regardless of what
the manifest said.

This change removes the above requirement and sets the tile counts to
the values from the manifest.

PiperOrigin-RevId: 590608353
2023-12-13 08:37:06 -08:00
lpribanic
b1d65f6d00 Amend javadocs for ImageOutput methods
PiperOrigin-RevId: 590607537
2023-12-13 08:33:55 -08:00
ibaker
9a766161ee Combine 'matching' versions in media3 bug template
#minor-release

PiperOrigin-RevId: 590586491
2023-12-13 07:14:21 -08:00
tonihei
7a702870f6 Add test and release notes 2023-12-13 14:48:35 +00:00
Steve Mayhew
64840159d6 Fixes issue #9347 - jump to live on seek to 0
Using 0 as the unset prepare position is the root cause of a number of issues,
as outliine in the ExoPlayer issue https://github.com/google/ExoPlayer/issues/7975

The premise of this fix is that once the prepare override is used (the initial call
to `selectTracks()`) it is never needed again, so simply invalidate it after use.
2023-12-13 14:48:35 +00:00
huangdarwin
a15dfd75be GL: Request OpenGL ES 3.0 context on API 29+, with fallback to 2.0.
Despite GL 3.0 not being required on API 29+, it is experimentally
determined to always be supported on our testing devices, on API 29+.

That said, still fall back to OpenGL 2.0 if 3.0 is not supported,
just in case.

PiperOrigin-RevId: 590569772
2023-12-13 06:01:08 -08:00
tofunmi
2fa5430417 Update OptimizationResult to specify different reasons for abandonment
PiperOrigin-RevId: 590530694
2023-12-13 03:22:55 -08:00
ibaker
f6fe90f30b Clean-up multi-line strings in YAML issue templates
* If we don't want any newlines in the result, it's better to use `>`
* If we want newlines (e.g. for markdown) then we should ensure the
  string **only** contains the newlines we want, because GitHub (unlike
  other markdown renderers) preserves single newlines in the output,
  leading to ugly newlines dictated by the source.

Also remove a markdown-style link that isn't renderered as markdown.

PiperOrigin-RevId: 590309749
(cherry picked from commit 6aeaad26ad)
2023-12-13 09:49:13 +00:00
ibaker
6aeaad26ad Clean-up multi-line strings in YAML issue templates
* If we don't want any newlines in the result, it's better to use `>`
* If we want newlines (e.g. for markdown) then we should ensure the
  string **only** contains the newlines we want, because GitHub (unlike
  other markdown renderers) preserves single newlines in the output,
  leading to ugly newlines dictated by the source.

Also remove a markdown-style link that isn't renderered as markdown.

PiperOrigin-RevId: 590309749
2023-12-12 13:11:51 -08:00
tofunmi
37def3679f Trim optimization: fallback on format mismatches
Manual testing: tested manually with pixel 4a

PiperOrigin-RevId: 590284361
2023-12-12 11:53:43 -08:00
sheenachhabra
ee1147ffe1 Remove unused method from TrackMetadataProvider interface
PiperOrigin-RevId: 590242668
2023-12-12 10:01:46 -08:00
Copybara-Service
f465efeefd Merge pull request #864 from v-novaltd:dsparano-exo129_2
PiperOrigin-RevId: 590234505
2023-12-12 09:37:41 -08:00
ibaker
5580b78b13 Fix VorbisComment.populateMediaMetadata key comparison to ignore case
Issue: androidx/media#876

#minor-release

PiperOrigin-RevId: 590215918
2023-12-12 08:43:02 -08:00
tonihei
8e33fbd536 Deprecate RAW_RESOURCE_SCHEME and util method
It's better to use the generic Android resource scheme which
is at least as powerful as our own one.

Issue: androidx/media#868
PiperOrigin-RevId: 590168919
2023-12-12 05:34:09 -08:00
Copybara-Service
27f437b65a Merge pull request #867 from equeim:ndk-r26
PiperOrigin-RevId: 590142275
2023-12-12 03:48:08 -08:00
sheenachhabra
0660b55ceb Move doInterleave() call to Mp4Writer
`Mp4Writer` receives all the tracks/samples and then it adds them to
corresponding `Track` object. As the `Track` object is primarily to hold
track specific data and `Mp4Writer` is responsible for interleaving related
logic, the call to `doInterleave` should be with `Mp4Writer`. The `Track`
object should just act like a data holding class.
This will also help in reusing `Track` class for fragmented MP4 implementation.

PiperOrigin-RevId: 590138002
2023-12-12 03:32:18 -08:00
tonihei
ce67b4d723 Add release notes 2023-12-12 10:42:35 +00:00
Alexey Rochev
38b5b03ebb Fix error with NDK r26 2023-12-12 10:40:27 +00:00
Alexey Rochev
6874cc80cf ffmpeg: add support of specifying Android ABI version when building FFmpeg
Also add proper error message when using NDK that doesn't support requested ABI version.
2023-12-12 10:40:27 +00:00
samrobinson
90a0cbdf3d Fix handling of repeated EOS in SilenceSkippingAudioProcessor.
Issue: androidx/media#712
PiperOrigin-RevId: 589882412
2023-12-11 11:17:14 -08:00
ibaker
d356d88c4f Improve test dump output for role and selection flags
PiperOrigin-RevId: 589878576
2023-12-11 11:05:40 -08:00
bachinger
7f9b02080a Make the media notification controller marker key visible
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
2023-12-11 10:57:00 -08:00
ibaker
3e5ef51594 Remove empty container/src/androidTest directory
PiperOrigin-RevId: 589870662
2023-12-11 10:41:51 -08:00
ibaker
5266c71b3a Fix handling of multiple HEVC tracks in JPEG motion photos
The MP4 data in JPEG motion photos can contain multiple `video/hevc` tracks, but only the first is at a playable frame rate while the others are low-fps, high-res tracks designed for specific use-cases (not direct video playback).

ExoPlayer currently selects the unplayable track by default, because it
has a higher resolution. This change introduces a flag to
`Mp4Extractor` that results in the first video track being marked as
`ROLE_FLAG_MAIN`, and all subsequent video tracks `ROLE_FLAG_ALTERNATE`
- this then results in the playable lower-res track being selected by
default.

PiperOrigin-RevId: 589832072
2023-12-11 08:31:13 -08:00
christosts
4c4c5f6a90 CompositionVideoSinkProvider: apply rotation effects per video
There is a bug in CompositionVideoSinkProvider where the rotation
effect is applied only on the first video and the same effect
is applied on subsequent videos without checking if the next
items in the playlist must be rotated.

The bug applies only on devices with API < 21.

PiperOrigin-RevId: 589823797
2023-12-11 07:56:50 -08:00
tonihei
eb2092bc8b Formatting fixes and release notes 2023-12-11 15:12:50 +00:00
Daniele Sparano
6f5187a34b Format to wake up PR 2023-12-11 14:28:11 +00:00
Daniele Sparano
4a17ca7600 Add basic h264 sample unit test to ensure correct sample flags, including key frames 2023-12-11 14:28:11 +00:00
Daniele Sparano
d4af13803a Fix H264 reader key frame detection 2023-12-11 14:28:11 +00:00
ibaker
379cb3ba54 Tighten the handling of validDataChannelTimeoutMs in Cea608Parser
This matches the documented requirements for this parameter.

PiperOrigin-RevId: 589799256
2023-12-11 06:05:53 -08:00
tonihei
00c7a9bcbb Keep playback thread blocked until next action with playUntilPosition
We currently pause playback to prevent further progress while the
app thread runs assertion and triggers additional actions. This is
not ideal because we do not actually want to pause playback in
almost all cases where this method used.

This can be improved by keeping the playback thread blocked and only
unblock it the next time the app thread waits for the player (either
via RobolectricUtil methods or by blocking the thread itself). To
add this automatic handling, this change introduces a new util class
for the tests that can keep the list of waiting threads statically
(because the access to this logic is spread across multiple independent
classes).

PiperOrigin-RevId: 589784204
2023-12-11 04:45:31 -08:00
tofunmi
00d5b6ec99 TransformerEndToEndTest: replace /*testId=*/ with variable
PiperOrigin-RevId: 589765715
2023-12-11 03:14:34 -08:00
huangdarwin
1ebe099685 Test: Make a method scope private.
For clarity.

PiperOrigin-RevId: 589758781
2023-12-11 02:43:25 -08:00
tianyifeng
b2a673d521 Move preload components to androidx.media3.exoplayer.source.preload
PiperOrigin-RevId: 589455479
2023-12-09 13:41:55 -08:00
ibaker
224dad3988 Remove AnalyticsListener as a public super-type of ExoHostedTest
Move the `AnalyticsListener` implementation to a private inner class.

This avoids polluting the public API of `ExoHostedTest`, especially as
it's designed to be extended.

PiperOrigin-RevId: 589188113
2023-12-08 11:13:18 -08:00
sheenachhabra
ac67f739d4 Specify which input file has B-frames in Transformer demo app
For out of order B-frames, the samples comes out of order and hence
presentation timestamps are not strictly increasing.
This can be verified by adding following assertion in `writeSampleData()` API
either in `MuxerWrapper` or in `Muxer API`.
```
checkArgument(
          bufferInfo.presentationTimeUs > lastSamplePresentationTimeUs,
          "Out of order B-frames are not supported");
```

PiperOrigin-RevId: 589152093
2023-12-08 09:23:42 -08:00
samrobinson
1471528176 Change AudioGraph #release to #reset, resetting internal state.
PiperOrigin-RevId: 589113634
2023-12-08 06:36:32 -08:00
tofunmi
c5c8e988e8 Abandon trim optimization when transcoding effects are set
PiperOrigin-RevId: 588839072
2023-12-07 10:39:38 -08:00
samrobinson
ab798659d9 Request specific AudioFormat from AudioGraphInputs on creation.
Also adds an alternate way to configure the AudioGraph.

Apps should no longer need to ensure that inputs have the same sample
rate.

PiperOrigin-RevId: 588747431
2023-12-07 04:42:03 -08:00
andrewlewis
c014ba9d5f Use API 33 constants for DV levels
PiperOrigin-RevId: 588740855
2023-12-07 04:15:19 -08:00
tofunmi
be5b29d92d Update ExportResult.OptimizationResult options
Added a new ABANDONED option so one can tell the difference between when the optimization has been requested but not applied vs not requested at all. also changed the ordering do better represent the hierarchy of failure modes

PiperOrigin-RevId: 588720513
2023-12-07 02:52:16 -08:00
tofunmi
cd346ca14d Transformer: Add support for transmuxing audio in trim optimization
PiperOrigin-RevId: 588711597
2023-12-07 02:18:21 -08:00
christosts
faeff17a4c Fix bug in CompositingVideoSinkProvider.isInitialized()
Fix a bug where CompositingVideoSinkProvider.isInitialized() returns
true even after releasing the CompositingVideoSinkProvider.

PiperOrigin-RevId: 588481744
2023-12-06 11:01:45 -08:00
christosts
073ee8a1d0 Move instantiation of CompositingVideoSinkProvider
This change moves the instantiation of the CompositingVideoSinkProvider
out of MediaCodecVideoRenderer so that the composition preview player can
re-use the CompositingVideoSinkProvider instance for driving the rendering of
images.

The main point of the change is the ownership of the
VideoFrameReleaseControl, which decides when a frame should be rendered
and so far was owned by the MediaCodecVideoRenderer. With this change,
in the context of composition preview, the VideoFrameReleaseControl
is no longer owned by MediaCodecVideoRenderer, but provided to it.

This way, the CompositingVideoSinkProvider instance, hence the
VideoFrameReleaseControl can be re-used to funnel images into the
video pipeline and render the pipeline from elsewhere (and not
MediaCodecVideoRenderer).

PiperOrigin-RevId: 588459007
2023-12-06 09:52:43 -08:00
ibaker
bd19953ac9 Split Cue.toBundle into serializable and binder-based variants
The serializable form is used when we need to serialize the result into
bytes in the sample queue. The binder-based (ultimately
filedescriptor-based) form is used for
session/controller IPC, in order to avoid sending the bitmap bytes over
the IPC.

Issue: androidx/media#836

#minor-release

PiperOrigin-RevId: 588420836
2023-12-06 07:35:34 -08:00
huangdarwin
a98052b3fc Test: Mention expected bitmap in assertion message.
This helped me debug which bitmap was actually failing. Otherwise, you need to clear all bitmaps on the device relating to this test, then adb pull all bitmaps and see the last uploaded one to see, which is much more confusing.

PiperOrigin-RevId: 588374081
2023-12-06 04:17:37 -08:00
samrobinson
757585ce6d Release MuxerWrapper in every test (in an @After block).
PiperOrigin-RevId: 588110566
2023-12-05 10:13:27 -08:00
ibaker
6360082b87 Add extractor and playback tests for Pixel JPEG motion photo
This image has two video tracks in the MP4 data, one is a 'real' video
which we want to play by default, and the other is a low-fps video track
which isn't intended to be directly played, it's encoded in HEVC for
compression and decoding efficiency.

This test demonstrates ExoPlayer's current behaviour default extraction
and playback, which results in selecting the high-res, low-fps track
(actually single sample in this example), instead of playing the actual
video.

PiperOrigin-RevId: 588068908
2023-12-05 07:46:19 -08:00
ibaker
d4fe3fe318 Add Robolectric e2e test support for HEVC content
PiperOrigin-RevId: 588055594
2023-12-05 06:52:39 -08:00
Googler
e0f1783a54 Fix nullability issue in MediaControllerImplLegacy
PiperOrigin-RevId: 588035411
2023-12-05 05:24:57 -08:00
tofunmi
b0e2fd78af Use getter for presentationDurationUs
Delays failures to when the field is used in preview code, so that exports in the demo app can continue succeed

PiperOrigin-RevId: 588022569
2023-12-05 04:43:57 -08:00
michaelkatz
d1e38abf93 Limit processing Opus decode-only frames by seek-preroll in offload
As Opus decoders skip some bytes prior to playback during a seek, the renderer for bypass playback should send samples to the decoder even if they would be decode-only. However, the renderer should not send samples with time preceding that range. This change adds that constraint.

#minor-release

PiperOrigin-RevId: 588014983
2023-12-05 03:44:37 -08:00
tonihei
b1541b096f Map VORBIS channel layout to Android layout
Both the extension OPUS decoder and the OMX/C2 MediaCodec
implementations for OPUS and VORBIS decode into the channel
layout defined by VORBIS. See
https://www.xiph.org/vorbis/doc/Vorbis_I_spec.html#x1-140001.2.3

While this is technically correct for a stand-alone OPUS or VORBIS
decoder, it doesn't match the channel layout expected by Android.
See https://developer.android.com/reference/android/media/AudioFormat#channelMask

The fix is to apply the channel mapping after decoding if needed.
Also add e2e tests with audio dumps for the extension renderer,
including a new 5.1 channel test file.

Issue: google/ExoPlayer#8396

#minor-release

PiperOrigin-RevId: 588004832
2023-12-05 03:01:32 -08:00
ibaker
913f6da083 MCR: Ensure mediaCrypto and codec are atomically non-null
`mediaCrypto` is initialized before `codec` in
`maybeInitCodecOrBypass`. Before this change, it was possible for
`maybeInitCodecOrBypass` to complete with `mediaCrypto != null` and
`codec == null`, in particular if it was run as part of clearing the
player surface (since in that case, no video codec is initialized).
This inconsistent state then causes issues during a later invocation of
`maybeInitCodecOrBypass`, when `mediaCrypto` is still non-null, and
`mediaCryptoRequiresSecureDecoder = true`, but the
content has been changed to unencrypted with no associated DRM session.
This results in a playback error, because a secure decoder is
initialized but there's no DRM session available to work with it.

This change ensures that when `maybeInitCodecOrBypass` completes,
either both `mediaCrypto != null` and `codec != null` (i.e. codec
initialization was completed) or `mediaCrypto == null` and
`codec == null` (i.e. codec initialization was not completed). We also
ensure that when nulling out `mediaCrypto` we also set
`maybeInitCodecOrBypass = false`. A later change should be able to
demote `maybeInitCodecOrBypass` from a field to a local in order to
remove any risk of that part of state becoming out of sync. This
resolves the issue, because during the second invocation of
`maybeInitCodecOrBypass` an insecure decoder is now (correctly)
initialized and the unencrypted content is successfully played.

#minor-release

PiperOrigin-RevId: 587713911
2023-12-04 07:32:52 -08:00
tianyifeng
f32bdf86bc Set playerId when preloading to make the PreloadMediaSource reusable
We set the `playerId` only in the constructor currently. But in the case of this source doesn't have `preload` called, the player's release of this source will set the playerId to `null`, which makes this source un-reusable with a null `playerId`.

PiperOrigin-RevId: 587698214
2023-12-04 06:31:11 -08:00
tofunmi
88b15e73b2 fix: update TransformerPauseResumeTest to use isRunningOnEmulator
#minor-release

PiperOrigin-RevId: 586964536
2023-12-01 04:01:52 -08:00
samrobinson
fe272d3c49 Follow practices/guidance in Muxer tests around:
* @Before and @After usage. [1].
* static fields before non-static. [2].

@Before method should typically be paired with an @After method,
focused on ensuring that the component is released regardless of what
the test does.

In tests, inlining final class variables is preferrable [1]. In general
things like the file path should be part of the test (the @Rule means
we don't need before/after) if only used once.

Statically importing values and using them directly is preferable to
having a variable declared as non-final that's effectively final,
because from a readability perspective someone can see (the caps) that
the value is final static and immutable, so doesn't have to check if
it's changed/reassigned.

PiperOrigin-RevId: 586697887
2023-11-30 09:29:18 -08:00
tofunmi
5b3491082b fix: make BitmapOverlay constructor public
So developers can subclass it
#minor-release

PiperOrigin-RevId: 586638134
2023-11-30 04:54:06 -08:00
huangdarwin
a2a4ef5f40 Effect: Fix overlay alpha handling.
Before, a translucent overlay over an opaque video would result in a
translucent output. This is not consistent with physical properties of light
(if putting a translucent object in front of an opaque object, you can't see
behind the opaque object).

Using the mixing properties from DefaultVideoCompositor.

PiperOrigin-RevId: 586636275
2023-11-30 04:43:21 -08:00
ibaker
28c210686f Don't include null text or bitmaps in Cue.toBundle()
`fromBundle` doesn't distinguish between `FIELD_BITMAP` and `FIELD_TEXT`
being present with a null value, or being absent, so we might as well
avoid including them when the value is null.

I've separated this from a later change to add
`Cue.toSerializableBundle` which will also skip setting a bitmap value
into the `Bundle` if `this.bitmap == null`. This is partly because it
results in changes to a lot of extractor test dump files, and it's
easier to review that as a separate change.

PiperOrigin-RevId: 586626141
2023-11-30 03:58:33 -08:00
jbibik
03564fdbc6 Promote method to control subtitle parsing to MediaSource.Factory
PiperOrigin-RevId: 586361222
2023-11-29 09:12:04 -08:00
jbibik
8a8b875c72 Add experimental opt-in to parse SS subtitles during extraction
PiperOrigin-RevId: 586331888
2023-11-29 07:14:14 -08:00
huangdarwin
9add30e582 Effect: Use Bitmap generation ID to detect changes.
This is much simpler than using protected methods that signal updates in
bitmaps.

PiperOrigin-RevId: 586295312
2023-11-29 04:29:49 -08:00
christosts
3d1d8f4439 Exit early progressive loads if the load task is canceled
Add an check when loading progressive media in case the load
is canceled. If the player is released very early, the progressive
media period may carry on with the initial loading unnecessarily.

PiperOrigin-RevId: 586288385
2023-11-29 04:01:06 -08:00
andrewlewis
3204313f13 Remove debug logging
This case is expected and we aren't trying to gather information about it
currently, so we shouldn't log.

PiperOrigin-RevId: 586015969
2023-11-28 10:01:37 -08:00
huangdarwin
e5ef31b277 Effect: Avoid allocating bitmaps and textures in Overlays.
In `TextOverlay` and `DrawableOverlay`, treat `Bitmap` as a buffer, where we
allocate it rarely and reuse it as long as possible before making a new one.

In `BitmapOverlay`, avoid allocating GL textures too often as well.

Strongly reduces allocations and memory usage growth (saving ~100-150 MB on 4k60fps
at high end), at the cost of more code complexity and low-end using 70MB more, on
1/1 comparisons.

PiperOrigin-RevId: 585990602
2023-11-28 08:44:30 -08:00
huangdarwin
eb01c3f440 Add exception message for MediaCodecRenderer exception.
Otherwise, it's difficult to differentiate between different sources of ERROR_CODE_DECODING_FORMAT_UNSUPPORTED.

PiperOrigin-RevId: 585966636
2023-11-28 07:15:52 -08:00
andrewlewis
b8c1e22389 Clarify threading-related comments in texture manager
In `ExternalTextureManager` fields are accessed from the GL thread and the class needs to be constructed on the GL thread.

Also visibly document threading requirement in the parent class.

PiperOrigin-RevId: 585941284
2023-11-28 05:30:15 -08:00
andrewlewis
7bbf72c202 Use JsonWriter to convert to JSON
Before the change the output was JSON-like but not valid because it had commas
after objects/arrays.

PiperOrigin-RevId: 585929345
2023-11-28 04:39:50 -08:00
tofunmi
b598c96c2f Update emulator device names
PiperOrigin-RevId: 585682881
2023-11-27 10:02:02 -08:00
andrewlewis
1c7c06999e Turn off debug trace logging by default
The issue that motivated adding this (frames unexpectedly being dropped by the
decoder) has been addressed, so we can turn off the logging to reduce
unnecessary allocations during transformation. We can easily turn on debug
logging in future as needed by setting `DebugTraceUtil.DEBUG = true`.

Also avoid allocations for string building at logging call sites by passing a
format string for extra info. Formatting the string now only happens when
debugging is turned on.

Tested manually by running transformations in the new state (DEBUG = false) and
with debugging turned on.

PiperOrigin-RevId: 585666349
2023-11-27 08:57:30 -08:00
ibaker
63062a9c10 Make CueSerializationTest more realistic
Serializing bitmap cues is currently broken, but this test is
incorrectly passing. This change makes two changes to introduce the same
failure (both changes are necessary, each one alone still passes):

1. Move from Robolectric to an instrumentation test.
2. Trigger the `Bitmap` to be serialized using a file descriptor, either
   by calling `Bitmap.asShared` in the test when constructing the `Cue`,
   or constructing the `Bitmap` from a 'real' image byte array instead a
   1x1 token image.

Issue: androidx/media#836
PiperOrigin-RevId: 585643486
2023-11-27 07:16:19 -08:00
Copybara-Service
5f27b18210 Merge pull request #837 from superjohan:fix/android-14-clearkey
PiperOrigin-RevId: 585639025
2023-11-27 06:56:45 -08:00
andrewlewis
e84a13fb54 Restrict operating rate workaround to SM8550
PiperOrigin-RevId: 585613041
2023-11-27 04:42:42 -08:00
andrewlewis
8b38b34b9f Work around codec frame rate issues in Redmi Note 9 Pro
The decoder and encoder won't accept high values for frame rate, so avoid
setting the key when configuring the decoder, and set a default value for the
encoder (where the key is required).

Also skip SSIM calculation for 4k, where the device lacks concurrent decoding
support.

PiperOrigin-RevId: 585604976
2023-11-27 04:05:44 -08:00
huangdarwin
c650f05234 Document TimestampWrapper not working with previewing.
Mentioned in https://github.com/androidx/media/issues/821

PiperOrigin-RevId: 585595948
2023-11-27 03:25:31 -08:00
Ian Baker
8e4ffe7d57 Add release note for clearkey workaround change 2023-11-27 10:41:47 +00:00
Johan Halin
ad7b12e56f Apply workaround for Android 13 and newer
At least some Android 14 devices still have the same invalid URL issue
when using ClearKey DRM, so might as well apply the check to newer
versions of Android as well.
2023-11-27 10:41:47 +00:00
andrewlewis
ad40db4489 Avoid value close to overflow for KEY_OPERATING_RATE
Using `Integer.MAX_VALUE` risks causing arithmetic overflow in the codec
implementation.

Issue: androidx/media#810

#minor-release

PiperOrigin-RevId: 585104621
2023-11-24 08:57:59 -08:00
siroberts
bc36553e81 Expose isTrusted property of ControllerInfo.
PiperOrigin-RevId: 585052580
2023-11-24 03:37:33 -08:00
jbibik
c0ef5f6de4 Serialize media3 custom Spans for Cue encoding/decoding
PiperOrigin-RevId: 585028521
2023-11-24 01:32:40 -08:00
ibaker
479344d74e Fix typo in DashManifestParser
PiperOrigin-RevId: 585017285
2023-11-24 00:32:26 -08:00
tonihei
85a54e2e19 Remove redundant ) in Javadoc
PiperOrigin-RevId: 584910697
2023-11-23 09:58:45 -08:00
Copybara-Service
45b51d8c97 Merge pull request #707 from equeim:ffmpeg-6.0
PiperOrigin-RevId: 584893190
2023-11-23 08:06:04 -08:00
samrobinson
aef2fcb900 Plumb EditedMediaItem for audio preview.
PiperOrigin-RevId: 584865962
2023-11-23 05:13:32 -08:00
tonihei
e766666482 Instruct MediaCodec to drop buffers before start time in tunneling mode
We don't get the buffer back after decoding to make a proper decision
about whether dropping the buffer is needed, so we do the next best
thing and tell the codec to drop the buffer if its input timestamp is
less than the intended start time.

PiperOrigin-RevId: 584863144
2023-11-23 04:56:57 -08:00
christosts
2a74cb7ef2 Move VideoFrameProcessor reflective loading code
Move the reflective loading of VideoFrameProcessor from
MediaCodecVideoRenderer to the CompositingVideoSinkProvider. This is so
that all reflective code lives in one place. The
CompositingVideoSinkProvider already has reflective code to load the
default PreviewingVideoGraph.Factory.

PiperOrigin-RevId: 584852547
2023-11-23 03:54:18 -08:00
samrobinson
1524d12634 Avoid using unneeded double ended queue.
These usages have no need for the double ended input functionality. All
other usages across media3 are ConcurrentLinkedQueue.

PiperOrigin-RevId: 584841104
2023-11-23 02:51:20 -08:00
huangdarwin
0f040e6c6e Use static import for Util.formatInvariant.
In OverlayShaderProgram, this method is used quite a lot, and is the only method from Util.java in this file. Marginally reduce complexity by using a static import instead.

PiperOrigin-RevId: 584828455
2023-11-23 01:45:19 -08:00
huangdarwin
dc037b22cd Effect: Flip texture in OpenGL instead of allocating a Bitmap.
Reduce short-lived allocations of potentially large objects, like Bitmap.

Unfortunately, this does make the TextureOverlay interface more messy though, requiring a way to signal whether the texture should be flipped vertically.

PiperOrigin-RevId: 584661400
2023-11-22 10:17:10 -08:00
Rohit Singh
7c939593fe Add change to RELEASENOTES 2023-11-22 16:25:44 +00:00
Alexey Rochev
6332693ce4 Use swr_alloc_set_opts2 function to set SwrContext options 2023-11-22 16:14:47 +00:00
Alexey Rochev
815d93cfa2 Migrate to FFmpeg 6.0
These changes are also compatible with FFmpeg 5.1, which is now minimum supported version.

Also set -Wl,-Bsymbolic flag via target_link_options command which is more correct.
2023-11-22 16:14:47 +00:00
tofunmi
2d77e4d22c Implement trim optimization in Transformer
PiperOrigin-RevId: 584622392
2023-11-22 07:28:34 -08:00
christosts
6435ddb89e Create VideoFrameRenderControl
Split CompositingVideoSinkProvider.VideoSinkImpl in two classes:
- VideoSinkImpl now only receives input from MediaCodecVideoRenderer and
  forwards frames to its connected VideoFrameProcessor
- VideoFrameRenderControl takes composited frames out of the VideoGraph
  and schedules the rendering of those.
- CompositingVideoSinkProvider connects VideoSinkImpl with
  VideoFramesRenderer.

PiperOrigin-RevId: 584605078
2023-11-22 06:05:04 -08:00
bachinger
a063d137b4 Add session extras to the state of the controller
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
2023-11-21 14:32:33 -08:00
rohks
1d61c48266 Rollback of 1360548649
PiperOrigin-RevId: 584358604
2023-11-21 10:12:47 -08:00
rohks
1360548649 Handle unsupported format xHE-AAC in FfmpegAudioRenderer
Issue: androidx/media#803
PiperOrigin-RevId: 584333812
2023-11-21 08:34:25 -08:00
huangdarwin
0b22a7a0d8 GL: Move private helper method next to the method that uses it.
In addition to being more readable, this will help future CLs that modify
these methods...

PiperOrigin-RevId: 584323686
2023-11-21 07:52:24 -08:00
huangdarwin
6c68146efa GL demo: Use setColor instead of setARGB
setColor is a bit more readable

PiperOrigin-RevId: 584322875
2023-11-21 07:45:32 -08:00
christosts
ec08db458e MidiExtractor: mark only the first sample as key-frame
This change fixes a bug with seeking forward in MIDI. When seeking forward,
the progressive media period attempts to seek within the sample queue, if a
key-frame exists before the seeking position. With MIDI, however, we can
only skip Note-On and Note-Off samples and all other samples must be sent
to the MIDI decoder.

When seeking outside the sample queue, the MidiExtractor already
instructs the player to start from the beginning of the MIDI input. With
this change, only the first output sample is a key-frame, thus the
progressive media period can no longer seek within the sample queue and
is forced to seek from the MIDI input start always.

Issue: androidx/media#704

#minor-release

PiperOrigin-RevId: 584321443
2023-11-21 07:39:46 -08:00
samrobinson
79fd3365fa Use VolumeScalingAudioProcessor in audio effect preview test.
Dump files changes are easier to understand with a processor that keeps
buffer sizes the same.

PiperOrigin-RevId: 584320606
2023-11-21 07:35:01 -08:00
tonihei
af0282b9db Avoid clipping live offset override to min/max offsets
The live offset override is used to replace the media-defined
live offset after user seeks to ensure the live adjustment adjusts
to the new user-provided live offset and doesn't go back to the
original one.

However, the code currently clips the override to the min/max
live offsets defined in LiveConfiguration. This is useful to
clip the default value (in case of inconsistent values in the media),
but the clipping shouldn't be applied to user overrides as
the player will then adjust the position back to the min/max
and doesn't stay at the desired user position.

See 2416d99857 (r132871601)

#minor-release

PiperOrigin-RevId: 584311004
2023-11-21 06:49:19 -08:00
Copybara-Service
fde142d66e Merge pull request #793 from androidx:mpegh_extractor_changes
PiperOrigin-RevId: 584291984
2023-11-21 05:07:27 -08:00
bachinger
fd81d2a1b2 Use a better sample video for testing
The replaced one had barely no movement and audio in
the first second.

PiperOrigin-RevId: 584283388
2023-11-21 04:21:07 -08:00
Rohit Singh
4c3ca9b6f4 update mhm1 mp4 samples and corresponding extractor dumps 2023-11-21 12:12:23 +00:00
bachinger
ec478138ba Add test case to test position conversion when POSITION_UNKNOWN
PiperOrigin-RevId: 584261559
2023-11-21 02:24:30 -08:00
bachinger
167f50a9ca Return empty timeline when media info is null
Issue: androidx/media#708
PiperOrigin-RevId: 584054624
2023-11-20 09:55:36 -08:00
ibaker
4bcb60d31d Add Cea708Decoder/ParserTest with a single, simple example
PiperOrigin-RevId: 584042033
2023-11-20 09:06:03 -08:00
tianyifeng
89bedf0fb5 Emit onPositionDiscontinuity event when silence is skipped
Issue: androidx/media#765
PiperOrigin-RevId: 584024654
2023-11-20 07:50:13 -08:00
tonihei
5eb6a889a7 Adjust Javadoc
PiperOrigin-RevId: 583965332
2023-11-20 02:54:57 -08:00
rohks
ffbaa090aa Use .test top level domain for test URI
PiperOrigin-RevId: 583951327
2023-11-20 02:00:30 -08:00
rohks
6df240877c Populate MediaMetadata.extras to MediaMetadataCompat
Ensures backward compatibility.

Issue: androidx/media#802
PiperOrigin-RevId: 583425114
2023-11-17 10:25:10 -08:00
claincly
ad96ca3b30 Make vararg APIs more robust
Composition and EditedMediaItemSequence don't allow empty lists in their main
constructors, so shouldn't the vararg API. This is more inline with Effective
Java item 53.

PiperOrigin-RevId: 583415124
2023-11-17 09:51:39 -08:00
Ian Baker
4f5038bc07 Merge branch 'release' into release-1.2.0 2023-11-17 16:13:40 +00:00
andrewlewis
7b9aa87344 Allow allocating more buffers when transmuxing
When transmuxing, the `EncodedSampleExporter` maintains a queue of input
buffers that get filled with encoded data by the asset loader. The number of
buffers was limited to avoid using more and more memory if producer (asset
loader) gets far ahead of the consumer (exporter).

Previously this limit was fixed at 10 buffers, but increasing the number of
buffers can make some transmux operations much faster. Allow allocating between
a min and max number of buffers, and also set a target allocation size beyond
which new buffers can't be allocated. This allows audio formats which require
many small buffers to be processed more quickly, while preventing allocating
too much memory for hypothetical very high bitrate formats.

'Remove video' edits on local videos in particular get much faster, because
audio buffers are very short and there are lots of them. With a sample 10
minute video, a 'remove video' edit took 2 seconds (36 seconds before this
change).  With a sample 1 minute removing video took 0.25 seconds after this
change (2.5 seconds before).

The speed improvement is smaller for other types of edits that retain the video
track. Transmuxing a 10 minute video retaining the video track took 26 seconds
(40 seconds before).

PiperOrigin-RevId: 583390284
2023-11-17 08:11:25 -08:00
ibaker
2cc8afecc6 Remove recommendation to pin annotation-experimental to version 1.2.0
This was intended to avoid bringing in a transitive dependency on the
Kotlin standard library, but Gradle no longer flags lint errors on
`@RequiresOptIn` violations with `annotation-experimental:1.2.0` (1.3.0
is needed), making this recommendation dangerous. See also
https://issuetracker.google.com/310651921.

PiperOrigin-RevId: 582276430
(cherry picked from commit aa1ec981a3)
2023-11-17 10:07:23 +00:00
ibaker
1b83c59759 Add @OptIn to fields in demo PlayerActivity now this is supported
This is possible now we use `annotation-experimental:1.3.1`.

#minor-release

PiperOrigin-RevId: 582315579
(cherry picked from commit 8d83d491f1)
2023-11-17 10:07:23 +00:00
jbibik
f90726a78d Merge release notes for media3 1.2.0 stable release
PiperOrigin-RevId: 580923121
(cherry picked from commit 7ee07a5ff5)
2023-11-17 10:07:20 +00:00
ibaker
66c162dabd Fix examples in MediaLibraryInfo javadoc to be realistic
Bugfix releases don't have pre-release cycles.

PiperOrigin-RevId: 583295158
2023-11-17 00:52:10 -08:00
christosts
7dc0654c69 Rollback of eafe2e35f0
PiperOrigin-RevId: 583045154
2023-11-16 08:01:24 -08:00
jbibik
b750ad50f9 Add subtitle parsing support in HLS for TS files
PiperOrigin-RevId: 582714493
2023-11-15 10:00:03 -08:00
samrobinson
d5fbf0007b Migrate to Util.durationUsToSampleCount in transformer audio.
PiperOrigin-RevId: 582700443
2023-11-15 09:15:10 -08:00
lpribanic
64d2210b79 Add DashPlayback test for loading thumbnail grids
This test instantiates an image renderer, selects an image track and
plays a thumbnail grid.

PiperOrigin-RevId: 582696009
2023-11-15 09:03:19 -08:00
jbibik
a667ceb6f9 Test DASH playback with TTML subs muxed into MP4
PiperOrigin-RevId: 582685662
2023-11-15 08:31:31 -08:00
tonihei
310e2edcca Workaround layout problems with Material Design
In some contexts (e.g. BottomSheetDialogFrament), Material Design
themes will override the default of singleLine=false to true. This
causes layout problems because the forward/rewind buttons are no
longer visible with singleLine=true.

This problem can be avoided by explicitly requesting the default
value of false in our layout files.

Issue: androidx/media#511

#minor-release

PiperOrigin-RevId: 582604131
2023-11-15 02:57:03 -08:00
ibaker
bd7615c0b8 Update recommended way to suppress @UnstableApi errors in lint.xml
#minor-release

PiperOrigin-RevId: 582599098
2023-11-15 02:34:40 -08:00
jbibik
94e45eb4ad Migrate CEA-708 logic to a SubtitleParser implementation
This change is similar to 27caeb8038 (CEA-608), but is currently lacking unit tests.

PiperOrigin-RevId: 582585457
2023-11-15 01:38:56 -08:00
jbibik
b23b1bb693 Add HLS support for parsing TTML subs muxed into MP4 during extraction
This removes the flakiness of the HLS playback test as well.

Previously, this flow only worked for standalone WebVTT subtitles (7b762642db)

PiperOrigin-RevId: 582359383
2023-11-14 10:10:44 -08:00
jbibik
67f770a786 Add HLS playback test with TTML subtitles muxed into MP4
The test is hidden behind the `@Ignore` annotation due to some
flakiness. However, it will be removed when the subtitle parsing is
moved to a pre-sample-queue architecture.

The test media was created with:

```shell
$ cp ../../dash/standalone-ttml/sample.xml sample.ttml
$ MP4Box -add sample.ttml sample.text.mp4
$ MP4Box -frag 10000 sample.text.mp4
$ rm sample.ttml
```

PiperOrigin-RevId: 582347113
2023-11-14 09:31:09 -08:00
tonihei
9bf1852069 Set MIME type from IMA SDK on ads MediaItem
This helps to play ads where the file extension is not sufficient
to deduce the correct source in DefaultMediaSourceFactory.

PiperOrigin-RevId: 582340114
2023-11-14 09:12:07 -08:00
tonihei
03a23bef8f Use full MediaItem to define ad playbacks
Currently, ads are only defined by a single URL, which makes it
impossible to define additional fields needed to play ads correctly.

This can be fixed by using a full MediaItem in AdPlaybackState,
replacing the previous Uri field.

PiperOrigin-RevId: 582331588
2023-11-14 08:35:14 -08:00
huangdarwin
8f69bb0d9d HDR: Update PQ to SDR tone-mapping to renderengine.
Use renderengine's PQ to SDR tone-mapping implementation instead
of naive implementation from before.

This improves luminance on highlights, as seen in the test image.

PiperOrigin-RevId: 582318045
2023-11-14 07:43:39 -08:00
tonihei
b570c72588 Normalize MIME types when accepting user or media input
MIME types are case-insensitive, but none of the many existing
comparisons across our code base take this into account. The
code can be made more robust by normalizing all MIME types at the
moment they are first set into a class/builder and adding toLowerCase
as part of the normalization.

Most concretely, this fixes an issue with playing HLS streams via
the IMA SDK where the stream MIME type is indicated with all lower
case "application/x-mpegurl", which failed the MIME type comparison
in DefaultMediaSourceFactory.

PiperOrigin-RevId: 582317261
2023-11-14 07:40:15 -08:00
ibaker
8d83d491f1 Add @OptIn to fields in demo PlayerActivity now this is supported
This is possible now we use `annotation-experimental:1.3.1`.

#minor-release

PiperOrigin-RevId: 582315579
2023-11-14 07:33:45 -08:00
lpribanic
877d26abdc Add ImageRenderer in CapturingRenderersFactory by default
DefaultRenderersFactory now instantiates an ImageRenderer by default,
so CapturingRenderersFactory will too.

PiperOrigin-RevId: 582307243
2023-11-14 06:58:48 -08:00
huangdarwin
28c095d8d0 Effect: Clarify threading for VideoFrameProcessor methods.
All methods in VideoFrameProcessor are expected to be called by the owning thread,
as far as I understand (vs. 10 threads each queuing frames/textures/streams, which
invalidates blocking done by registerInputStream and flush)

PiperOrigin-RevId: 582295240
2023-11-14 06:07:27 -08:00
ibaker
aa1ec981a3 Remove recommendation to pin annotation-experimental to version 1.2.0
This was intended to avoid bringing in a transitive dependency on the
Kotlin standard library, but Gradle no longer flags lint errors on
`@RequiresOptIn` violations with `annotation-experimental:1.2.0` (1.3.0
is needed), making this recommendation dangerous. See also
https://issuetracker.google.com/310651921.

#minor-release

PiperOrigin-RevId: 582276430
2023-11-14 04:38:38 -08:00
lpribanic
ec7ac3f482 Create image extractors in BundledChunkExtractor
BundledChunkExtractor creates a JpegExtractor or a PngExtractor if the
chunk's MIME type is JPEG or PNG respectively.

The JpegExtractor is instantiated to load an image track.

PiperOrigin-RevId: 582005828
2023-11-13 10:20:23 -08:00
andrewlewis
1b13c87825 Refine test skipping logic
Skip wearable devices, which don't have the same CDD requirements on codecs from Android 5 (API 21).

Limit an existing skipping case to pre API 33 devices, so that we can catch failures on Android 13 (API 33) onwards, and add OnePlus 9 Pro which also times out calculating SSIM. Remove TODOs for removing test/SSIM skipping now they are restricted to API version.

PiperOrigin-RevId: 581985554
2023-11-13 09:14:41 -08:00
andrewlewis
c00161fb8f Skip export4K60 on Pixel 3
This device over-reports encoding capabilities, so skip the test.

This is a Pixel device that was upgraded to Android 12 (API 31/32) so the issue should only affect devices that didn't take OTAs.

PiperOrigin-RevId: 581981073
2023-11-13 09:02:38 -08:00
lpribanic
2fb5695a82 Instantiate an ImageRenderer
Instantiate an ImageRenderer and add it to the list returned by
DefaultRenderersFactory.buildRenderers.

Add Renderer.MessageType.MSG_SET_IMAGE_OUTPUT and
ExoPlayer.setImageOutput to enable setting a custom
ImageRenderer.imageOutput.

Add ImageRenderer.handleMessage to process messages sent to the
renderer.

PiperOrigin-RevId: 581962451
2023-11-13 07:54:47 -08:00
andrewlewis
330713f687 Expand frame drop workaround to Realme C11
Based on on-device testing, this device seems to have the same issue as Moto G (20) where frames are dropped despite configuring the decoder not to drop frames.

PiperOrigin-RevId: 581943805
2023-11-13 06:47:12 -08:00
andrewlewis
c763ed7941 Expand blocklist for export8K24 to OnePlus 9 Pro
This is failing with the same error about having insufficient resources.

PiperOrigin-RevId: 581921054
2023-11-13 05:00:15 -08:00
tianyifeng
79711ebd3f Parse "f800" as channel count of 5 for Dolby in DASH manifest
Issue: androidx/media#688
PiperOrigin-RevId: 581908905
2023-11-13 04:00:24 -08:00
jbibik
a2679fba54 Bump media3 versions to 1.2.0 (stable)
#minor-release

PiperOrigin-RevId: 580856330
(cherry picked from commit 3918d36200)
2023-11-12 20:52:00 +00:00
Googler
7014bc6bf4 Add icon URI to bundle serialization
PiperOrigin-RevId: 581333583
2023-11-10 12:19:49 -08:00
Googler
e79809616c Don't crash when receiving a bad playback state
PiperOrigin-RevId: 580942377
2023-11-09 10:01:31 -08:00
jbibik
7ee07a5ff5 Merge release notes for media3 1.2.0 stable release
PiperOrigin-RevId: 580923121
2023-11-09 08:54:44 -08:00
jbibik
3918d36200 Bump media3 versions to 1.2.0 (stable)
#minor-release

PiperOrigin-RevId: 580856330
2023-11-09 04:19:30 -08:00
claincly
f172923f0d Remove possibly retained bitmap reference
PiperOrigin-RevId: 580579054
2023-11-08 10:39:52 -08:00
jbibik
508582d56c Remove old pre-releases from the github bug template
PiperOrigin-RevId: 580554963
2023-11-08 09:19:04 -08:00
claincly
ef9a76efe2 Fix composition's duration not respecting presentation duration
PiperOrigin-RevId: 580540264
2023-11-08 08:23:54 -08:00
samrobinson
2ae22a412a Cleanup small nits in AudioGraphInput.
PiperOrigin-RevId: 580503934
2023-11-08 05:49:34 -08:00
christosts
dae3e275c4 Increase performance test upper bound threshold
PiperOrigin-RevId: 580497700
2023-11-08 05:22:43 -08:00
samrobinson
76474684f9 Plumb audio through AudioGraph for Composition preview.
The dump file diff as part of this change is because using AudioGraph
means the 2nd item is automatically edited to match the AudioFormat of
the 1st item {44.1KHz mono}, rather than {48KHz stereo}.

Manually verified that for the 2nd item, data output:
* Before: 66936 bytes (16734 frames) output = 348_625us of audio.
* After: 30750 bytes (15375 frames) output = 348_639us of audio.

The small final buffer is caused by SonicAudioProcessor outputting all
pending data when EOS queued, and is WAI.

PiperOrigin-RevId: 580494578
2023-11-08 05:13:08 -08:00
claincly
8d1663a57f Clarify GL texture creation
PiperOrigin-RevId: 580176027
2023-11-07 07:43:15 -08:00
Rohit Singh
6297e7aeae Changes based on internal review 2023-11-07 14:23:07 +00:00
andrewlewis
a7d47d4526 Add info about using SurfaceView instead of TextureView
PiperOrigin-RevId: 580145645
2023-11-07 05:35:09 -08:00
Rohit Singh
8e554c6d6a - some further changes according to review comments
- update MPEG-H test data and extractor dumps
2023-11-07 13:01:20 +00:00
tofunmi
4311cf1d6c Mp4MetadataInfo: add format and time-based I-frame timestamp extraction
PiperOrigin-RevId: 580132463
2023-11-07 04:31:25 -08:00
jbibik
089910546f Fix the asset and dump file names for the standalone Webvtt-HLS test
PiperOrigin-RevId: 580125493
2023-11-07 04:02:34 -08:00
andrewlewis
63bda3b001 Fix typo
PiperOrigin-RevId: 580113633
2023-11-07 03:02:56 -08:00
tofunmi
ba0724ca78 Pass initializationData to EncoderFactory when requested
PiperOrigin-RevId: 580098432
2023-11-07 02:04:39 -08:00
andrewlewis
14fb45626d Add missing visibility modifier
PiperOrigin-RevId: 580092052
2023-11-07 01:33:44 -08:00
sheenachhabra
5db9a66b3b Implement resume API in Transformer
Changes includes:
1. Add resume flow.
2. Change demo app code to resume export.
3. Changes in test infra to trigger resume.
4. E2E Test cases

PiperOrigin-RevId: 579895744
2023-11-06 11:01:04 -08:00
ibaker
7991838326 Rollback of a19f577976
PiperOrigin-RevId: 577139027
(cherry picked from commit dd6306e1ba)
2023-11-06 16:51:08 +00:00
claincly
414b72619b Remove unnecessary memory allocation in OpenGL
PiperOrigin-RevId: 579835031
2023-11-06 07:21:23 -08:00
Rohit Singh
6d2059080b - changes according to review comments
- add test data and dumps
2023-11-06 13:28:26 +00:00
Rohit Singh
94442291bd Extend MP4 extractor implementation with complete parsing of mhaC and mhaP boxes 2023-11-06 13:11:46 +00:00
claincly
98e9022c0e Ensure the exception thrown in the constructor is reported
PiperOrigin-RevId: 579776559
2023-11-06 02:44:22 -08:00
huangdarwin
920d588575 Effect: Clarify ExternalTextureManager thread access.
Turns out more things are accessed only on the GL thread than labelled.

PiperOrigin-RevId: 579244695
2023-11-03 11:25:16 -07:00
tonihei
bce82bdc75 Fix proguard rule to also keep referenced class name
PiperOrigin-RevId: 579234050
2023-11-03 10:53:36 -07:00
huangdarwin
229d9713a4 Flush: Add javadoc for exception when no active stream.
PiperOrigin-RevId: 579225491
2023-11-03 10:28:25 -07:00
tonihei
312203d38b Deprecate Bundleable and Bundleable.Creator
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
2023-11-03 08:27:21 -07:00
ibaker
0a016b59f7 Remove Guava @Beta API warning suppressions
These are no longer needed now we've updated to 32.1.3 in 7a10435633

PiperOrigin-RevId: 579149808
2023-11-03 05:21:49 -07:00
Googler
21a9bfe440 Add iconUri to CommandButton
PiperOrigin-RevId: 578916804
2023-11-03 05:19:56 -07:00
ibaker
901f89c456 Add @CheckReturnValue to ParsableByteArray and ParsableBitArray
This helps encourage usages of `skipXXX()` methods instead of
`readXXX()`.

PiperOrigin-RevId: 578892379
2023-11-02 10:08:26 -07:00
tofunmi
3253f1b5cd Add microsecond precision to MediaItem.ClippingConfiguration
PiperOrigin-RevId: 578881990
2023-11-02 09:40:11 -07:00
Copybara-Service
dab9eb33a4 Merge pull request #692 from haixia-meta:main
PiperOrigin-RevId: 578881745
2023-11-02 09:36:38 -07:00
microkatz
dc530289bb Changed av1c parser from a class to a method 2023-11-02 15:38:27 +00:00
microkatz
9d43cdac17 Add av1C to atom list comment in colr atom parse 2023-11-02 15:31:49 +00:00
Haixia Shi
5bca9d8a41 Use a shorter test file 2023-11-02 15:31:49 +00:00
Haixia Shi
258f45f874 Fix unit test problems with sample_with_av1c.mp4 2023-11-02 15:31:49 +00:00
microkatz
5a70bbfeec Format with google-java-format 2023-11-02 15:31:49 +00:00
Haixia Shi
834664be4f Add a unit test to Mp4ExtractorTest with a small av1 sample with color info. 2023-11-02 15:31:49 +00:00
microkatz
918079059c Format files and add release note 2023-11-02 15:31:49 +00:00
Haixia Shi
f455e843bc Address review comments on Av1BitstreamParser
* Rename method f(n) to a more helpful name.
* Move the private inner class to the bottom.
* Move public fields before private fields but below the static field.
* Make `private ParsableByteArray data` final.
* Make sure `parseSequenceHeader` can only be called once.
2023-11-02 15:31:48 +00:00
Haixia Shi
4ded7e588d Add AV1 color space parsing in MP4 atom parser
This adds av1C parsing based on the AV1 bitstream specification: https://aomediacodec.github.io/av1-spec/av1-spec.pdf

This is needed to have correct color space when using hardware AV1 decoder.
2023-11-02 15:31:48 +00:00
jbibik
c5241c028e Restore DelegatingSubtitleDecoder's visibility to package-private
PiperOrigin-RevId: 578836078
2023-11-02 06:50:23 -07:00
lpribanic
7387284c1c Add image track selection to DefaultTrackSelector
DefaultTrackSelector now has all logic necessary for selecting an
image track.

If isPrioritizeImageOverVideoEnabled is set to true, image track will
try to be selected first and a video track will only be selected if no
image track is available. If isPrioritizeImageOverVideoEnabled is set
to false, image track will be selected only if video track wasn't
selected.

PiperOrigin-RevId: 578806006
2023-11-02 04:25:05 -07:00
tonihei
ae6f83d298 Fix access to stale ByteBuffer in FfmpegAudioDecoder
The native code can now reallocate the buffer if it needs to grow
its size, so we have to reacquire a reference in the Java code to
avoid accessing a stale instance.

This fixes a bug introduced by 8750ed8de6.

PiperOrigin-RevId: 578799862
2023-11-02 03:55:44 -07:00
tonihei
d4e5ab2c4d Make BundleableUtil more generic by taking Function parameters
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
2023-11-02 03:17:17 -07:00
tofunmi
de82aa93f0 Move shouldTrancodeAudio/Video to static helper methods
PiperOrigin-RevId: 578617730
2023-11-01 13:12:56 -07:00
Googler
a671f4aede Add addAll to SessionCommands
PiperOrigin-RevId: 578588968
2023-11-01 11:47:49 -07:00
ibaker
7a10435633 Upgrade Guava dependency to 32.1.3
This is slightly out of sync with the version in AOSP (32.1.2) but the
diff is minimal, and we need 32.1.3 here as it contains the fix for
https://github.com/google/guava/issues/6657.

PiperOrigin-RevId: 578572893
2023-11-01 11:02:35 -07:00
huangdarwin
44f317693b Flush: Move TextureManager flush logic to abstract class.
This also adds flush support to texture input.

PiperOrigin-RevId: 578536040
2023-11-01 09:08:10 -07:00
jbibik
7b762642db Add experimental opt-in to parse HLS subtitles during extraction
PiperOrigin-RevId: 578524318
2023-11-01 08:25:37 -07:00
ibaker
72b7019578 Split media1/media3 conversion methods out of MediaUtils
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
2023-11-01 08:04:21 -07:00
ibaker
27caeb8038 Migrate CEA-608 logic to a SubtitleParser implementation
PiperOrigin-RevId: 578505919
2023-11-01 07:07:19 -07:00
ibaker
d42c23706b Add warning log if DASH manifest contains incomplete ClearKey info
Unfortunately we can't fail any more obviously at this point, because
manifests often contain config for multiple DRM schemes, and when
parsing the manifest we don't know which scheme is going to be used for
playback. It would be unreasonable to fail playback due to incomplete
ClearKey config if playback was otherwise going to succeed using e.g.
Widevine.

* Issue: androidx/media#777
* Issue: androidx/media#563
* Issue: google/ExoPlayer#9169

#minor-release

PiperOrigin-RevId: 578491484
2023-11-01 05:59:49 -07:00
tianyifeng
84022eacc5 Put the custom keys in MediaMetadataCompat to MediaMetadata.extras
PiperOrigin-RevId: 578473874
2023-11-01 04:30:10 -07:00
tonihei
1a09430182 Make remote process bundle method less error-prone
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
2023-11-01 03:08:43 -07:00
Copybara-Service
4f99000ba1 Merge pull request #746 from equeim:ffmpeg-output-buffer-reallocation
PiperOrigin-RevId: 578217064
2023-10-31 09:59:35 -07:00
tonihei
58d8850b21 Satisfy nullness checker correctness by using local variable 2023-10-31 12:56:32 +00:00
huangdarwin
8d87a27fb9 Remove deprecated ColorInfo constructor
This was first deprecated in a4bc0959be, submitted Dec 2022

PiperOrigin-RevId: 578152077
2023-10-31 05:46:39 -07:00
tonihei
c4c4ef9670 Add terminating newline 2023-10-31 12:39:02 +00:00
tonihei
78142d3f5e Fix typo 2023-10-31 12:32:28 +00:00
tonihei
36fb20719f Change warning suppression style 2023-10-31 12:29:23 +00:00
tonihei
8750ed8de6 Format with google-java-format
Also amended Javadoc and added assertion to grow method
2023-10-31 12:25:32 +00:00
Alexey Rochev
adee4626d3 ffmpeg: reallocate output buffer dynamically
With FFmpeg we can't determine size of output buffer ahead of time for all codecs,
so we need to reallocate it when needed instead of simply failing.
2023-10-31 12:25:32 +00:00
ibaker
3a527a888a Split openAssetFileDescriptor from RawResourceDataSource.open
This moves the invocation of `transferInitializing` slightly earlier,
but this is consistent with other `DataSource` implementations like
`OkHttpDataSource`.

PiperOrigin-RevId: 578137236
2023-10-31 04:38:57 -07:00
ibaker
88f554c74b Add cross-package support to RawResourceDataSource
This has been documented to work since this class was created, but until
now we were always trying to resolve using the current application's
`Resources.getIdentifier` method. This commit changes to resolve to the
other app's `Resources` object if the package name doesn't match the
current package.

This will only work if the current app has package-visibility to the
destination package: http://g.co/dev/packagevisibility

This is hard to test because to do so robustly requires being able to
guaranteed that another test APK will be installed with a known raw
resource inside it.

PiperOrigin-RevId: 577864992
2023-10-30 09:17:45 -07:00
ibaker
26789b56c2 Remove unecessary proguard config symlink
PiperOrigin-RevId: 577858121
2023-10-30 08:53:51 -07:00
ibaker
841cdf170b Reduce HlsMediaPeriod to package-private visibility
This type shouldn't be directly depended on from outside the HLS
package.

PiperOrigin-RevId: 577833188
2023-10-30 07:17:52 -07:00
ibaker
db1ab1dcf3 Remove stray parentheses from release notes
#minor-release

PiperOrigin-RevId: 577809964
2023-10-30 05:19:34 -07:00
ibaker
e30e43ec3f Migrate EventLogger to non-deprecated AnalyticsListener methods
Also suppress a warning about unused constructor parameters.

#minor-release

PiperOrigin-RevId: 577795245
2023-10-30 04:05:46 -07:00
jbibik
1ac6263869 Test DASH playback + standalone WebVTT parsed during extraction
This change applies to standalone WebVTT files linked directly from the manifest.

Since DASH only supports stand-alone IMSC1 (TTML) and WebVTT text files, this change concludes the support extension of text-based subtitle files to be parse during extraction.

PiperOrigin-RevId: 577468830
2023-10-28 08:44:11 -07:00
jbibik
97efa70852 Add DASH support for parsing standalone TTML files during extraction
This change applies to standalone TTML files linked directly from the manifest.

As a result, we no longer have the flakiness in the DashPlaybackTest which uses sidecar-loaded (standalone file) TTML subtitles. We experimentally opt into parsing subtitles during extraction and use SubtitleExtractor in hybrid mode.

PiperOrigin-RevId: 577457256
2023-10-28 06:59:45 -07:00
jbibik
1359b0147d Add an HLS End-to-End test with WebVtt sidecar subtitles
These subtitles are parsed using the old-flow, i.e. after decoding.

PiperOrigin-RevId: 577452579
2023-10-28 06:15:24 -07:00
ibaker
e8cca688ad Bump okhttp dependency to 4.12
Issue: androidx/media#768
PiperOrigin-RevId: 577208115
2023-10-27 08:34:19 -07:00
sheenachhabra
5b0be4e8b0 Create unique name for export output file.
With pause/resume functionality coming in, we need the output file
path to be different from the previous one.

PiperOrigin-RevId: 577175540
2023-10-27 06:12:23 -07:00
huangdarwin
fed88cf6f5 Flush: Disallow flushing when there's no active input.
Throws when calling flush when there's no active input, for example
before an input stream is registered or after all output streams have
ended.

PiperOrigin-RevId: 577165419
2023-10-27 05:23:38 -07:00
ibaker
dd6306e1ba Rollback of a19f577976
PiperOrigin-RevId: 577139027
2023-10-27 03:12:19 -07:00
huangdarwin
346b9257ba Flush: VideoFrameProcessor texture output
PiperOrigin-RevId: 576928149
2023-10-26 11:06:04 -07:00
claincly
841b4fba9a Fix GL releasing surface that doesn't need releasing
PiperOrigin-RevId: 576545767
2023-10-25 09:05:11 -07:00
sheenachhabra
1e2815cade Simplify Mp4ExtractorWrapper implementation
Changes includes:
1. Create static factory method and hide constructor.
2. Move all the fetching logic to init() method.

PiperOrigin-RevId: 576544902
2023-10-25 09:02:02 -07:00
claincly
3204da41fe Add performance test for composition previewing
PiperOrigin-RevId: 576509031
2023-10-25 06:22:16 -07:00
huangdarwin
e91ce868ad Flush: Add javadoc to mention flush limitation.
PiperOrigin-RevId: 576482193
2023-10-25 04:10:32 -07:00
sheenachhabra
fe6305931d Add moto g(20) API 30 in the allowed frame dropping list
This is a workaround to avoid frame dropping.

PiperOrigin-RevId: 576467065
2023-10-25 03:07:08 -07:00
Googler
8796b2e21e Add isPrioritizeImageOverVideoEnabled to TrackSelectionParameters
This CL adds an isPrioritizeImageOverVideoEnabled flag to
TrackSelectionParameters and an API to set the flag value.

The flag will be used by DefaultTrackSelector to determine whether
to select an image track if both an image track and a video track are available.

PiperOrigin-RevId: 576175162
2023-10-24 10:01:22 -07:00
ibaker
e7a255cfbb Add httpengine module to core_settings.gradle
PiperOrigin-RevId: 576166099
2023-10-24 09:32:10 -07:00
rohks
3d6ac7f6f4 Add com.github.philburk:jsyn to JAR list
#minor-release

PiperOrigin-RevId: 576148893
(cherry picked from commit 00943a0a73)
2023-10-24 17:07:47 +01:00
rohks
00943a0a73 Add com.github.philburk:jsyn to JAR list
#minor-release

PiperOrigin-RevId: 576148893
2023-10-24 08:32:07 -07:00
tofunmi
beed1bd76e Pass initial timestamp offset to EncodedSampleExporter
When transmuxing, we usually only need to offset the timestamp by the position of a mediaItem in a sequence.

Trim optimization introduces another type of offset: for the transmux of the second part of the video we need to offset the timestamps by the total duration already trancoded by transformer.

PiperOrigin-RevId: 576134656
2023-10-24 07:39:23 -07:00
rohks
d6b11738e2 Move HttpEngineDataSource release note to unreleased section
PiperOrigin-RevId: 576127741
2023-10-24 07:04:53 -07:00
huangdarwin
a8a590c305 Effect: Clarify flush behavior in javadoc
PiperOrigin-RevId: 576118064
2023-10-24 06:13:22 -07:00
claincly
1fc34676d9 Make sure effects are applied on the correct frame
The events happens in the following order, assuming two media items:

1. First media item is fully decoded, record the last frame's pts
  - Note frame processing is still ongoing for this media item
2. Renderer sends `onOutputFormatChanged()` to signal the second media item
3. **Block sending the frames of the second media item to the `VideoSink`**
4. Frame processing finishes on the first media item
5. The last frame of the first media item is released
6. **Reconfigure the `VideoSink` to apply new effects**
7. **Start sending the frames of the second media item to the `VideoSink`**

This CL implements the **events in bold**

PiperOrigin-RevId: 576098798
2023-10-24 04:45:05 -07:00
claincly
e8adbd9075 Require duration in EditedMediaItem in composition previewing
Adds an additional field for actual presentation duration of the
EditedMediaItem

PiperOrigin-RevId: 576090574
2023-10-24 04:09:14 -07:00
tofunmi
771d203204 ExoAssetLoaderRenderer:Drop negative timestamp buffers when transmuxing
Prevents queuing unneeded buffers when transmuxing. (we already do this when transcoding).

PiperOrigin-RevId: 576080462
2023-10-24 03:21:56 -07:00
Copybara-Service
64d93eb0d1 Merge pull request #710 from loki666:patch-2
PiperOrigin-RevId: 575817952
2023-10-23 07:58:17 -07:00
christosts
71602767ca Restructure TrackEvent.populateFrom() 2023-10-23 14:44:27 +00:00
Philippe Simons
a06430a513 Update TrackEvent.java 2023-10-23 14:32:03 +00:00
Philippe Simons
b27b65199a Update TrackEvent.java 2023-10-23 14:32:03 +00:00
Philippe Simons
fc2099dede MIDI: Ignore SysEx messages
ignore SysEx messages instead of choking
2023-10-23 14:32:03 +00:00
rohks
105bdf57d8 Reorder RELEASENOTES to move unreleased changes to correct section
#minor-release

PiperOrigin-RevId: 575807109
2023-10-23 07:06:46 -07:00
rohks
1c54c393a0 Reorder RELEASENOTES to move unreleased changes to correct section
PiperOrigin-RevId: 575807109
(cherry picked from commit 105bdf57d8)
2023-10-23 07:03:35 -07:00
simakova
1ba1998e8d Update param description in TimestampWrapper
PiperOrigin-RevId: 575806256
2023-10-23 07:02:09 -07:00
rohks
9d3d7abdc6 Bump Media3 version numbers for 1.2.0-rc01
#minor-release

PiperOrigin-RevId: 575805495
2023-10-23 06:57:55 -07:00
rohks
7a2d80d87e Bump Media3 version numbers for 1.2.0-rc01
#minor-release

PiperOrigin-RevId: 575805495
(cherry picked from commit 9d3d7abdc6)
2023-10-23 06:55:40 -07:00
rohks
7202f5d4de Update RELEASENOTES for 1.2.0-rc01 release
#minor-release

PiperOrigin-RevId: 575795800
2023-10-23 06:10:31 -07:00
rohks
c997c71258 Update RELEASENOTES for 1.2.0-rc01 release
PiperOrigin-RevId: 575795800
(cherry picked from commit 7202f5d4de)
2023-10-23 06:07:35 -07:00
michaelkatz
4515a0c3f2 Fallback to legacy sizerate check for H264 if CDD PerfPoint check fails
Some devices supporting Performance Points for decoder coverage are missing coverage over the CDD requirements for H264. For these cases ExoPlayer should fall back to legacy resolution and frame rate support checks. If there is an H264 stream evaluated as a `PerformancePointCoverageResult` of `COVERAGE_RESULT_NO`, then ExoPlayer checks for coverage of the [720p CDD requirement](https://source.android.com/docs/compatibility/10/android-10-cdd#5_3_4_h_264).

Issue: google/ExoPlayer#10898

Issue: androidx/media#693
PiperOrigin-RevId: 575768836
2023-10-23 03:49:50 -07:00
bachinger
a79d44edc5 Use MediaSessionImpl.onMediaButtonEvent() to dispatch key events
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
2023-10-20 08:55:15 -07:00
bachinger
f2cf43ccd5 Use MediaSessionImpl.onMediaButtonEvent() to dispatch key events
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
(cherry picked from commit a79d44edc5)
2023-10-20 08:52:55 -07:00
rohks
a8ab9e2c70 Update translations in the ui module
#minor-release

PiperOrigin-RevId: 575161190
2023-10-20 02:52:30 -07:00
rohks
47a451abf7 Update translations in the ui module
#minor-release

PiperOrigin-RevId: 575161190
(cherry picked from commit a8ab9e2c70)
2023-10-20 02:49:23 -07:00
simakova
beb1711d4c Remove CompositionPlayer activity from the transformer demo app
The CompositionPlayer is not ready yet.

Issue: androidx/media#741
PiperOrigin-RevId: 574859927
2023-10-19 07:19:15 -07:00
simakova
9ac6f89fd7 Remove CompositionPlayer activity from the transformer demo app
The CompositionPlayer is not ready yet.

Issue: androidx/media#741
PiperOrigin-RevId: 574859927
(cherry picked from commit beb1711d4c)
2023-10-19 07:17:02 -07:00
tonihei
bfd1a2724c Add missing command checks to playback resumption flow
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
2023-10-19 05:39:21 -07:00
tonihei
e1ad106453 Add missing command checks to playback resumption flow
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
(cherry picked from commit bfd1a2724c)
2023-10-19 05:36:49 -07:00
Copybara-Service
5f80a47081 Merge pull request #728 from lawadr:audio-capabilities-fix
PiperOrigin-RevId: 574829263
2023-10-19 05:18:21 -07:00
Copybara-Service
cb67b16cac Merge pull request #728 from lawadr:audio-capabilities-fix
PiperOrigin-RevId: 574829263
(cherry picked from commit 5f80a47081)
2023-10-19 05:18:21 -07:00
claincly
2673b64371 Ignore 8k export test on incapable devices
And add a test to cover 8k transcode to lower resolution

PiperOrigin-RevId: 574809781
2023-10-19 03:58:13 -07:00
bachinger
54d5810fc3 Do not hide System UI when app rejects connection
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
2023-10-19 03:51:19 -07:00
bachinger
a8b0bd712a Do not hide System UI when app rejects connection
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
(cherry picked from commit 54d5810fc3)
2023-10-19 03:48:16 -07:00
tonihei
8f44916e97 Add release notes 2023-10-19 09:45:28 +01:00
lawadr
580ff6759c Fix AudioCapabilities regression
Since DEFAULT_MAX_CHANNEL_COUNT was increased from 8 to 10,
getMaxSupportedChannelCountForPassthrough always throws if its loop
enters its second iteration (channelCount of 9). This is due to
Util.getAudioTrackChannelConfig returning CHANNEL_INVALID when passed a
channelCount of 9, and setting CHANNEL_INVALID as the AudioFormat's
channel mask throws an exception.

This change skips each iteration where CHANNEL_INVALID is returned.
2023-10-19 09:17:41 +01:00
tonihei
f0cab4d03e Rollback of 64bd3bcad3
PiperOrigin-RevId: 574766164
2023-10-19 01:06:08 -07:00
tonihei
2ae6b1e832 Rollback of 64bd3bcad3
PiperOrigin-RevId: 574766164
(cherry picked from commit f0cab4d03e)
2023-10-19 01:03:49 -07:00
Googler
cf3733765c Rollback of eafe2e35f0
PiperOrigin-RevId: 574755143
2023-10-19 00:21:43 -07:00
Googler
4c778edd4d Rollback of eafe2e35f0
PiperOrigin-RevId: 574755143
(cherry picked from commit cf3733765c)
2023-10-19 00:18:56 -07:00
tonihei
21cb3a6bea Rollback of 4ebe630a80
PiperOrigin-RevId: 574530273
(cherry picked from commit c0759a4e62)
2023-10-23 13:15:17 +01:00
ibaker
5d6fefe410 Add formatting to scheme list in DefaultDataSource javadoc
The current formatting makes the 'scheme' part of the list blend into
the definition, especially when the definition is multi-line.

https://developer.android.com/reference/androidx/media3/datasource/DefaultDataSource

I considered adding another level of nesting, but I think bold will
help distinguish the structure of the list without adding too much HTML
or visual whitespace.

#minor-release

PiperOrigin-RevId: 574514208
(cherry picked from commit aec6db77fa)
2023-10-23 13:15:17 +01:00
michaelkatz
111ac63695 Send decode-only Opus samples in bypass mode for seekPreRoll skip
As Opus decoders skip some bytes prior to playback during a seek, the renderer for bypass playback should send samples to the decoder even if they would be decode-only.

#minor-release

PiperOrigin-RevId: 574494666
(cherry picked from commit 00193e0304)
2023-10-23 13:15:17 +01:00
tonihei
fe60d0d7b4 Use DataSourceBitmapLoader by default
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
(cherry picked from commit db86932781)
2023-10-23 13:15:17 +01:00
christosts
5a4adc9b25 Fix MIDI decoder build.gradle
Issue: androidx/media#734

#minor-release

PiperOrigin-RevId: 574425269
(cherry picked from commit ff4ff76990)
2023-10-23 13:15:17 +01:00
Googler
9ace4855e0 Rollback of 4ebe630a80
PiperOrigin-RevId: 574308136
(cherry picked from commit ff330bd8e9)
2023-10-23 13:15:17 +01:00
Googler
fcb3315edc Rollback of 64bd3bcad3
PiperOrigin-RevId: 574290408
(cherry picked from commit 1a43aa3602)
2023-10-23 13:15:17 +01:00
christosts
ee83baf92e Publish MIDI decoder module on Maven repository
Issue: androidx/media#734

#minor-release

PiperOrigin-RevId: 574182702
(cherry picked from commit 61770f8a61)
2023-10-23 13:15:17 +01:00
Copybara-Service
29846d0167 Merge pull request #491 from v-novaltd:dsparano-exo128
PiperOrigin-RevId: 574129451
(cherry picked from commit 009d48a75e)
2023-10-23 13:15:17 +01:00
ibaker
f290d0ef86 Move DASH subtitle parsing release note to correct section
#minor-release

PiperOrigin-RevId: 574090381
(cherry picked from commit df19097e22)
2023-10-23 13:15:17 +01:00
bachinger
8e48433be3 Send media button events from service directly using MediaSessionImpl
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
(cherry picked from commit 64bd3bcad3)
2023-10-23 13:15:17 +01:00
bachinger
85167f175a Send ConnectionState as in-process bundle if possible
#minor-release

PiperOrigin-RevId: 573849858
(cherry picked from commit d5f093f43c)
2023-10-23 13:15:17 +01:00
bachinger
386d2239eb Only set the queue when COMMAND_GET_TIMELINE is available
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
(cherry picked from commit f53e1bc6f6)
2023-10-23 13:15:17 +01:00
tonihei
e46ee01c00 Expand MediaItems in session demo instead of just replacing them
When MediaItems are added from the controller, we currently completely
replace the item with the one from our database, overriding any
potential additional information the controller may have set.

Also forward the onAddMediaItems/onSetMediaItems callbacks to common
helper methods instead of redirecting them through super methods

#minor-release
Issue: androidx/media#706
PiperOrigin-RevId: 573799351
(cherry picked from commit 00425dbe80)
2023-10-23 13:15:17 +01:00
tianyifeng
2a7d85e065 Calculate HLS live playlist refresh interval accurately
Previously, we calculated the next playlist reload time by adding the target duration (or half of it, depending on whether there is a real update in the new playlist snapshot) from the last load completion time, which makes the reload interval as long as `targetDuration(or half of it) + lastLoadDuration`. While still complying to the standard that "the client MUST wait for at least the target duration before attempting to reload the Playlist file again", this could cause buffering when the playback position is close to the end of live window. This change is to calculate the reload interval accurately by not adding the term `lastLoadDuration`.

Issue: androidx/media#663

#minor-release

PiperOrigin-RevId: 573300009
(cherry picked from commit 58a63c82aa)
2023-10-23 13:15:16 +01:00
Googler
b65136e292 Remove deprecated DownloadNotificationHelper.buildProgressNotification
Use a non deprecated method that takes a `notMetRequirements` parameter
instead.

PiperOrigin-RevId: 573252909
(cherry picked from commit 8b7ebc7032)
2023-10-23 13:15:12 +01:00
ibaker
3244318d28 Test more URI forms in RawResourceDataSourceContractTest
PiperOrigin-RevId: 573220915
(cherry picked from commit 40459f7212)
2023-10-23 13:14:42 +01:00
ibaker
f77f3dfa1a Migrate SubtitleParser implementations to incremental parse()
All production and test callers of the non-incremental methods are
already migrated, so we can remove them in this change too.

#minor-release

PiperOrigin-RevId: 573207318
(cherry picked from commit ecd24646cb)
2023-10-23 13:14:42 +01:00
ibaker
74277b14c8 Remove the 'super speed' SmoothStreaming PlayReady stream from demo
This content is no longer available, the manifest is returning a 404.

Issue: google/ExoPlayer#11309

#minor-release

PiperOrigin-RevId: 573202175
(cherry picked from commit a19f577976)
2023-10-23 13:14:42 +01:00
ibaker
b77a2530af Change LegacySubtitleUtil handling of SubtitleParser.OutputOptions
If the `Subtitle` has 'active' cues at `OutputOptions.startTimeUs`, this
change ensures these are emitted in a `CuesWithTiming` with
`CuesWithTiming.startTimeUs = OutputOptions.startTimeUs`. If
`OutputOptions.outputAllCues` is also set, then another `CuesWithTiming`
is emitted at the end that covers the 'first part' of the active cues,
and  ends at `OutputOptions.startTimeUs`.

As well as adding some more tests to `LegacySubtitleUtilWebvttTest`,
this change also adds more tests for `TtmlParser` handling of
`OutputOptions`, which transitively tests the behaviour of
`LegacySubtitleUtil`.

#minor-release

PiperOrigin-RevId: 573151016
(cherry picked from commit f9ece88a25)
2023-10-23 13:14:42 +01:00
Copybara-Service
c7186c9400 Merge pull request #650 from cedricxperi:dts-lbr-buffer-underflow-fix
PiperOrigin-RevId: 572864175
(cherry picked from commit 2421ba4d8f)
2023-10-23 13:14:42 +01:00
ibaker
24c39b6a78 Migrate SubtitleParser tests to incremental parse() methods
All the production code is already calling these new incremental
methods, migrating the tests allows us to remove the old
`List`-returning methods in a follow-up change.

#minor-release

PiperOrigin-RevId: 572822828
(cherry picked from commit a12bde4f57)
2023-10-23 13:14:42 +01:00
tonihei
d7044c7b83 Avoid bundling PlayerInfo for in-process calls
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
(cherry picked from commit d1fc15f207)
2023-10-23 13:14:42 +01:00
tonihei
7d6146170f Split available command filtering and bundling
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
(cherry picked from commit 4ebe630a80)
2023-10-23 13:14:42 +01:00
bachinger
0255f3be16 Check whether a session is still managed before removing
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
(cherry picked from commit 7fdc5b22ba)
2023-10-23 13:14:42 +01:00
michaelkatz
ec21b9e634 Update release notes to mention AudioOffloadPreference class changes
Issue: androidx/media#721
PiperOrigin-RevId: 572565009
(cherry picked from commit cef85be40f)
2023-10-23 13:14:42 +01:00
ibaker
de3eb672a5 Request notification permission when starting session demo app
#minor-release

PiperOrigin-RevId: 572556101
(cherry picked from commit c7a091a973)
2023-10-23 13:14:41 +01:00
bachinger
4b85207621 Add MediaSession.Builder().setPeriodicPositionUpdateEnabled()
This allows to disable periodic position updates when building
the session.

#minor-release

PiperOrigin-RevId: 572531837
(cherry picked from commit 4dc3db4da3)
2023-10-23 13:14:41 +01:00
ibaker
03a3f77340 Add experimental opt-in to parse DASH subtitles during extraction
This currently only applies to subtitles muxed into mp4 segments, and
not standalone text files linked directly from the manifest.

Issue: androidx/media#288

#minor-release

PiperOrigin-RevId: 572263764
(cherry picked from commit 66fa591959)
2023-10-23 13:14:41 +01:00
tonihei
7254f5aca5 Do not interrupt controller thread without a good reason
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
(cherry picked from commit 846117399f)
2023-10-23 13:14:41 +01:00
ibaker
2ec24ac55f Update @UnstableApi docs to include a package-info.java example
#minor-release

PiperOrigin-RevId: 572229092
(cherry picked from commit 7009c53c79)
2023-10-23 13:14:41 +01:00
ibaker
292701ba55 Add SubtitleParser.Factory.getCueReplacementBehavior()
This gives access to the replacement behavior for a particular subtitle
format without needing to instantiate a `SubtitleParser`.

#minor-release

PiperOrigin-RevId: 572226084
(cherry picked from commit e366c3d419)
2023-10-23 13:14:41 +01:00
tonihei
d078baf435 Remove unneccessary method parameter
The value already exists as a class field.

#minor-release

PiperOrigin-RevId: 572200771
(cherry picked from commit e5fa0c2ce9)
2023-10-23 13:14:41 +01:00
tonihei
69749c59cc Align audio adaptive support checks with video
In particular:
 - Add allowAudioNonSeamlessAdaptiveness parameter (default true, same
   as video and as already implemented by default)
 - Forward mixedMimeTypeAdaptation support to AudioTrackScore
   (as for VideoTrackScore) and adapt mixed MIME type adaptive
   support accordingly
 - Check adaptive support when deciding whether a track is allowed for
   adaptation (also same check as for video). This takes the new
   parameter into account.

PiperOrigin-RevId: 572191308
(cherry picked from commit f20d18e6ca)
2023-10-23 13:14:39 +01:00
ibaker
bd24e788b3 Use package-level @OptIn for demo apps
This demonstrates that `@OptIn` can now be used at the package-level
(since [`androidx.annotation:annotation-experimental:1.3.0`](https://developer.android.com/jetpack/androidx/releases/annotation#annotation-experimental-1.3.0)).

PiperOrigin-RevId: 572187729
(cherry picked from commit d60596cfca)
2023-10-23 13:13:46 +01:00
tonihei
77bccf0dd1 Make BundleListRetriever local Binder aware
When used within the same process, we don't have to go via the
onTransact method (which includes marshalling and unmarhsalling
the data), but can directly return the list.

#minor-release

PiperOrigin-RevId: 572179846
(cherry picked from commit 0bddd06938)
2023-10-23 13:13:46 +01:00
tonihei
7d063e9aab Add missing Future cancellation checks
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
(cherry picked from commit fe7c62afe0)
2023-10-23 13:13:46 +01:00
Googler
c913237e92 Fix the resumption of playback when suitable device is connected.
With this change the playback will resume as soon as the suitable device is connected and suppression reason is cleared (within set time out).

#minor-release

PiperOrigin-RevId: 572140309
(cherry picked from commit dc859eae82)
2023-10-23 13:13:46 +01:00
Googler
f799259a14 ...Update metalava library and Reformat api.txt...
PiperOrigin-RevId: 572013340
(cherry picked from commit da49a02b44)
2023-10-23 13:13:46 +01:00
tonihei
fdaf9b47df Use more targeted listening in session PlayerActivity
The current metadata updates are triggered by item transitions,
but depending on the speed of loading the playlist, the first
metadata may only be known later via metadata-change callbacks.

Slow playlist loading also means the UI stays empty and it's
beneficial to show a placeholder to avoid the impressions the
UI hangs.

Finally, clean-up by removing unused string constants and merging
all listeners into onEvents

#minor-release

PiperOrigin-RevId: 571951529
(cherry picked from commit fd81c904e1)
2023-10-23 13:13:46 +01:00
ibaker
99ea703455 Fix the asset and dump file names for the standalone TTML DASH test
#minor-release

PiperOrigin-RevId: 571941997
(cherry picked from commit 33c151eb5b)
2023-10-23 13:13:46 +01:00
christosts
3ba8459624 Report dropped frames from the VideoSink
After 4fad529433, MediaCodecVideoRenderer does not report if frames
are dropped from the VideoSink. This commit fixes this.

#minor-release

PiperOrigin-RevId: 571905721
(cherry picked from commit 05b17b5430)
2023-10-23 13:13:46 +01:00
ibaker
1818d46077 Return true from CuesResolver.addCues if the output changed
This belongs in the resolver, because it depends on the resolution
algorithm (and therefore the logic can't live in `TextRenderer`).

This also fixes a bug in `TextRenderer` where we were doing arithmetic
with `cues.durationUs` without checking if it was `TIME_UNSET` first.

#minor-release

PiperOrigin-RevId: 571332750
(cherry picked from commit 272428734b)
2023-10-23 13:13:46 +01:00
ibaker
6ad54d72ad Update TextRenderer to handle CuesWithTiming instances directly
The existing `Subtitle` handling code is left intact to support the
legacy post-`SampleQueue` decoding path for now.

This also includes full support for merging overlapping `CuesWithTiming`
instances, which explains the test dump file changes, and which should
resolve the following issues (if used with the
decoder-before-`SampleQueue` subtitle logic added in
5d453fcf37):

* Issue: google/ExoPlayer#10295
* Issue: google/ExoPlayer#4794

It should also help resolve Issue: androidx/media#288, but that will also require
some changes in the DASH module to enable pre-`SampleQueue` subtitle
parsing (which should happen soon).

PiperOrigin-RevId: 571021417
(cherry picked from commit 002ee0555d)
2023-10-23 13:13:42 +01:00
okunhardt
fa8dc4f49a Implement HttpEngineDataSource, a HttpDataSource using the [HttpEngine](https://developer.android.com/reference/android/net/http/HttpEngine) API.
HttpEngine was added in Android SDK 34. This DataSource is preferable to the DefaultHttpDataSource if supported as it offers better performance and more modern features.

PiperOrigin-RevId: 574594553
2023-10-18 14:17:56 -07:00
tonihei
c0759a4e62 Rollback of 4ebe630a80
PiperOrigin-RevId: 574530273
2023-10-18 11:05:49 -07:00
ibaker
aec6db77fa Add formatting to scheme list in DefaultDataSource javadoc
The current formatting makes the 'scheme' part of the list blend into
the definition, especially when the definition is multi-line.

https://developer.android.com/reference/androidx/media3/datasource/DefaultDataSource

I considered adding another level of nesting, but I think bold will
help distinguish the structure of the list without adding too much HTML
or visual whitespace.

#minor-release

PiperOrigin-RevId: 574514208
2023-10-18 10:17:58 -07:00
michaelkatz
00193e0304 Send decode-only Opus samples in bypass mode for seekPreRoll skip
As Opus decoders skip some bytes prior to playback during a seek, the renderer for bypass playback should send samples to the decoder even if they would be decode-only.

#minor-release

PiperOrigin-RevId: 574494666
2023-10-18 09:11:27 -07:00
tonihei
db86932781 Use DataSourceBitmapLoader by default
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
2023-10-18 06:18:32 -07:00
tianyifeng
43e6882fb4 Add PreloadMediaSource and PreloadMediaPeriod
The `PreloadMediaSource` has below two new public methods that suppose to be called by the app:

* `preload(long)` allows the apps to preload the source at the passed start position before playback. The preload efforts include preparing the source for a `Timeline`, creating and caching a `MediaPeriod`, preparing the period, selecting tracks on the period and continuing loading the data on the period.
* `releasePreloadMediaSource()` allows the apps to release the preloaded progress.

The `PreloadMediaPeriod` is designed to facilitate the `PreloadMediaSource` for the preloading work. It has a new package-private method `selectTracksForPreloading` which will cache the `SampleStream` that corresponds to the track selection made during the preloading, and when the `PreloadMediaPeriod.selectTracks` is called for playback, it will uses the preloaded streams if the new selection is equal to the selection made during the preloading.

Also add a shortform demo module to demo the usage of `PreloadMediaSource` with the short-form content use case.

PiperOrigin-RevId: 574439529
2023-10-18 04:57:06 -07:00
christosts
ff4ff76990 Fix MIDI decoder build.gradle
Issue: androidx/media#734

#minor-release

PiperOrigin-RevId: 574425269
2023-10-18 03:42:47 -07:00
christosts
eafe2e35f0 Move video frame release logic to VideoFrameReleaseControl
This change moves the release timestamp adjustment logic out of
MediaCodecVideoRenderer and into a standalone component, the
VideoFrameReleaseControl. The plan for VideoFrameReleaseControl is to use
it:
- from MediaCodecVideoRenderer, when ExoPlayer plays video in standalone
  mode.
- from the CompositionPlayer's DefaultVideoSink, when CompositionPlayer
  supports multiple sequences.
- (temporarily) from the CompositionPlayer's custom ImageRenderer while
  we are implementing single-sequence preview, which is an intermediate
  milestone for composition preview.
PiperOrigin-RevId: 574420427
2023-10-18 03:17:03 -07:00
Googler
ff330bd8e9 Rollback of 4ebe630a80
PiperOrigin-RevId: 574308136
2023-10-17 17:16:01 -07:00
Googler
1a43aa3602 Rollback of 64bd3bcad3
PiperOrigin-RevId: 574290408
2023-10-17 16:01:10 -07:00
christosts
61770f8a61 Publish MIDI decoder module on Maven repository
Issue: androidx/media#734

#minor-release

PiperOrigin-RevId: 574182702
2023-10-17 09:59:44 -07:00
andrewlewis
680eed52f3 Add support for flattening SEF files with H.265
PiperOrigin-RevId: 574173120
2023-10-17 09:26:14 -07:00
jbibik
c16accb816 Update RELEASENOTES.md for 1.2.0-beta01 release
PiperOrigin-RevId: 571941830
(cherry picked from commit 62ad1dfdf5)
2023-10-17 15:57:14 +01:00
Copybara-Service
009d48a75e Merge pull request #491 from v-novaltd:dsparano-exo128
PiperOrigin-RevId: 574129451
2023-10-17 06:35:19 -07:00
microkatz
716240776e Updated golden file tests and readded constructor 2023-10-17 11:42:33 +00:00
microkatz
e28288f9c5 Updated golden file tests and removed deprecated ColorInfo constructor usage 2023-10-17 11:42:33 +00:00
microkatz
212e138bcf Removed deprecated ColorInfo constructor call and fixed formatting 2023-10-17 11:42:33 +00:00
microkatz
d206be74ef Updated to use ColorInfo.Builder() and formatting issues 2023-10-17 11:42:33 +00:00
microkatz
bbcf37dc9e Format with google-java-format 2023-10-17 11:42:33 +00:00
Daniele Sparano
f14732873f Change isColorValid with isDataSpaceValid 2023-10-17 11:42:33 +00:00
Daniele Sparano
1fe9c3303e Resume toLogString() in ColorInfo; revert DebugTextViewHelper 2023-10-17 11:42:33 +00:00
microkatz
c72ec74e11 Format with google-java-format 2023-10-17 11:42:33 +00:00
microkatz
ee1b1500e2 Format with google-java-format 2023-10-17 11:42:33 +00:00
Daniele Sparano
f8d98861ea Move luma and chroma bitdepths to ColorInfo class 2023-10-17 11:42:33 +00:00
Daniele Sparano
59ff0dbb85 Improve isobmff atom parsing changes 2023-10-17 11:42:33 +00:00
Daniele Sparano
d454bd0601 Set luma and chroma bit depths in Format from Rtsp 2023-10-17 11:42:33 +00:00
Daniele Sparano
fc61d96d5c Replace literal with constant variable 2023-10-17 11:42:32 +00:00
Daniele Sparano
c7fe0662ce Set bitdepths in test Format 2023-10-17 11:42:32 +00:00
Daniele Sparano
e71ca5a740 Add luma and chroma bit depths to Format, set them as signalled in containers and parameter sets 2023-10-17 11:42:32 +00:00
claincly
dc0bee9307 Perform case insensitive comparison in tests
The model is "Redmi 6A" on the device

PiperOrigin-RevId: 574103629
2023-10-17 04:37:21 -07:00
ibaker
df19097e22 Move DASH subtitle parsing release note to correct section
#minor-release

PiperOrigin-RevId: 574090381
2023-10-17 03:42:04 -07:00
bachinger
64bd3bcad3 Send media button events from service directly using MediaSessionImpl
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
2023-10-16 13:52:30 -07:00
bachinger
d5f093f43c Send ConnectionState as in-process bundle if possible
#minor-release

PiperOrigin-RevId: 573849858
2023-10-16 10:15:34 -07:00
ibaker
681eadeb85 Test overriding resource type in RawResourceDataSource
I couldn't work out a good way to set up a test environment with
an asset in a different package, so I'm not adding a test for the
package overriding.

PiperOrigin-RevId: 573843326
2023-10-16 09:58:00 -07:00
samrobinson
fe1144487a Parse metadata from srfr atom in SMTA.
PiperOrigin-RevId: 573829216
2023-10-16 09:11:53 -07:00
bachinger
f53e1bc6f6 Only set the queue when COMMAND_GET_TIMELINE is available
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
2023-10-16 08:14:38 -07:00
tonihei
00425dbe80 Expand MediaItems in session demo instead of just replacing them
When MediaItems are added from the controller, we currently completely
replace the item with the one from our database, overriding any
potential additional information the controller may have set.

Also forward the onAddMediaItems/onSetMediaItems callbacks to common
helper methods instead of redirecting them through super methods

#minor-release
Issue: androidx/media#706
PiperOrigin-RevId: 573799351
2023-10-16 07:05:28 -07:00
claincly
37c86f3c15 Enable per-mediaItem effect in CompositionPlayer
Currently the effects are applied one frame too early. This will be fixed in
a later CL.

PiperOrigin-RevId: 573773074
2023-10-16 04:41:22 -07:00
ibaker
35121a2d3d Add RawResourceDataSource test for android.resource:///id URI
This is the documented format of this URI. The previous test was
exercising an undocumented format. Support for the previous format is
kept (and documented) because it seems to be relatively common (despite
the package name not being needed or used).

PiperOrigin-RevId: 573756190
2023-10-16 03:06:25 -07:00
tianyifeng
58a63c82aa Calculate HLS live playlist refresh interval accurately
Previously, we calculated the next playlist reload time by adding the target duration (or half of it, depending on whether there is a real update in the new playlist snapshot) from the last load completion time, which makes the reload interval as long as `targetDuration(or half of it) + lastLoadDuration`. While still complying to the standard that "the client MUST wait for at least the target duration before attempting to reload the Playlist file again", this could cause buffering when the playback position is close to the end of live window. This change is to calculate the reload interval accurately by not adding the term `lastLoadDuration`.

Issue: androidx/media#663

#minor-release

PiperOrigin-RevId: 573300009
2023-10-13 13:06:46 -07:00
Googler
8b7ebc7032 Remove deprecated DownloadNotificationHelper.buildProgressNotification
Use a non deprecated method that takes a `notMetRequirements` parameter
instead.

#minor-release

PiperOrigin-RevId: 573252909
2023-10-13 10:17:57 -07:00
ibaker
40459f7212 Test more URI forms in RawResourceDataSourceContractTest
PiperOrigin-RevId: 573220915
2023-10-13 07:57:58 -07:00
ibaker
ecd24646cb Migrate SubtitleParser implementations to incremental parse()
All production and test callers of the non-incremental methods are
already migrated, so we can remove them in this change too.

#minor-release

PiperOrigin-RevId: 573207318
2023-10-13 06:52:40 -07:00
ibaker
a19f577976 Remove the 'super speed' SmoothStreaming PlayReady stream from demo
This content is no longer available, the manifest is returning a 404.

Issue: google/ExoPlayer#11309

#minor-release

PiperOrigin-RevId: 573202175
2023-10-13 06:31:39 -07:00
ibaker
f9ece88a25 Change LegacySubtitleUtil handling of SubtitleParser.OutputOptions
If the `Subtitle` has 'active' cues at `OutputOptions.startTimeUs`, this
change ensures these are emitted in a `CuesWithTiming` with
`CuesWithTiming.startTimeUs = OutputOptions.startTimeUs`. If
`OutputOptions.outputAllCues` is also set, then another `CuesWithTiming`
is emitted at the end that covers the 'first part' of the active cues,
and  ends at `OutputOptions.startTimeUs`.

As well as adding some more tests to `LegacySubtitleUtilWebvttTest`,
this change also adds more tests for `TtmlParser` handling of
`OutputOptions`, which transitively tests the behaviour of
`LegacySubtitleUtil`.

#minor-release

PiperOrigin-RevId: 573151016
2023-10-13 02:21:22 -07:00
Copybara-Service
2421ba4d8f Merge pull request #650 from cedricxperi:dts-lbr-buffer-underflow-fix
PiperOrigin-RevId: 572864175
2023-10-12 04:50:32 -07:00
Tianyi Feng
492048c00b Modify the comment lines 2023-10-12 09:56:28 +00:00
Tianyi Feng
834b61d1b7 Update the year in the copyright 2023-10-12 09:56:28 +00:00
Tianyi Feng
49f45c45d1 Rebase and resolve conflict in the release notes 2023-10-12 09:56:28 +00:00
Tianyi Feng
215f663019 Format with google-java-format 2023-10-12 09:56:28 +00:00
Cedric T
0f200ba5d1 Update nits 2023-10-12 09:56:28 +00:00
Cedric T
24d03b0625 Rename DTSE to DTSHD 2023-10-12 09:56:28 +00:00
Cedric T
7edfe58283 Remove current mimetype state and add DTSHD test cases 2023-10-12 09:56:28 +00:00
Cedric T
25acaa1c81 Fix DTS Express Audio Buffer Underflow Issue. 2023-10-12 09:56:28 +00:00
ibaker
a12bde4f57 Migrate SubtitleParser tests to incremental parse() methods
All the production code is already calling these new incremental
methods, migrating the tests allows us to remove the old
`List`-returning methods in a follow-up change.

#minor-release

PiperOrigin-RevId: 572822828
2023-10-12 01:42:28 -07:00
tonihei
d1fc15f207 Avoid bundling PlayerInfo for in-process calls
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
2023-10-12 01:16:27 -07:00
tonihei
4ebe630a80 Split available command filtering and bundling
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
2023-10-11 09:09:11 -07:00
bachinger
7fdc5b22ba Check whether a session is still managed before removing
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
2023-10-11 07:27:50 -07:00
michaelkatz
cef85be40f Update release notes to mention AudioOffloadPreference class changes
Issue: androidx/media#721
PiperOrigin-RevId: 572565009
2023-10-11 07:12:37 -07:00
ibaker
c7a091a973 Request notification permission when starting session demo app
#minor-release

PiperOrigin-RevId: 572556101
2023-10-11 06:27:59 -07:00
bachinger
4dc3db4da3 Add MediaSession.Builder().setPeriodicPositionUpdateEnabled()
This allows to disable periodic position updates when building
the session.

#minor-release

PiperOrigin-RevId: 572531837
2023-10-11 04:10:03 -07:00
ibaker
164e658839 Test that DefaultSubtitleParserFactory format support is consistent
Looping through all MIME types is a bit hacky, but seems like a nice way
to check "all" MIME types (or at least more than a random selection).

PiperOrigin-RevId: 572508027
2023-10-11 02:10:30 -07:00
tofunmi
8f2161c43d Support customized loading in ExternallyLoadedMediaSource
PiperOrigin-RevId: 572299971
2023-10-10 10:44:08 -07:00
ibaker
66fa591959 Add experimental opt-in to parse DASH subtitles during extraction
This currently only applies to subtitles muxed into mp4 segments, and
not standalone text files linked directly from the manifest.

Issue: androidx/media#288

#minor-release

PiperOrigin-RevId: 572263764
2023-10-10 08:53:42 -07:00
tonihei
846117399f Do not interrupt controller thread without a good reason
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
2023-10-10 08:36:40 -07:00
ibaker
7009c53c79 Update @UnstableApi docs to include a package-info.java example
#minor-release

PiperOrigin-RevId: 572229092
2023-10-10 06:35:24 -07:00
ibaker
e366c3d419 Add SubtitleParser.Factory.getCueReplacementBehavior()
This gives access to the replacement behavior for a particular subtitle
format without needing to instantiate a `SubtitleParser`.

#minor-release

PiperOrigin-RevId: 572226084
2023-10-10 06:20:08 -07:00
tonihei
e5fa0c2ce9 Remove unneccessary method parameter
The value already exists as a class field.

#minor-release

PiperOrigin-RevId: 572200771
2023-10-10 04:09:15 -07:00
tonihei
f20d18e6ca Align audio adaptive support checks with video
In particular:
 - Add allowAudioNonSeamlessAdaptiveness parameter (default true, same
   as video and as already implemented by default)
 - Forward mixedMimeTypeAdaptation support to AudioTrackScore
   (as for VideoTrackScore) and adapt mixed MIME type adaptive
   support accordingly
 - Check adaptive support when deciding whether a track is allowed for
   adaptation (also same check as for video). This takes the new
   parameter into account.

#minor-release

PiperOrigin-RevId: 572191308
2023-10-10 03:18:22 -07:00
ibaker
d60596cfca Use package-level @OptIn for demo apps
This demonstrates that `@OptIn` can now be used at the package-level
(since [`androidx.annotation:annotation-experimental:1.3.0`](https://developer.android.com/jetpack/androidx/releases/annotation#annotation-experimental-1.3.0)).

PiperOrigin-RevId: 572187729
2023-10-10 03:02:25 -07:00
tonihei
0bddd06938 Make BundleListRetriever local Binder aware
When used within the same process, we don't have to go via the
onTransact method (which includes marshalling and unmarhsalling
the data), but can directly return the list.

#minor-release

PiperOrigin-RevId: 572179846
2023-10-10 02:22:56 -07:00
tonihei
fe7c62afe0 Add missing Future cancellation checks
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
2023-10-10 02:14:24 -07:00
Googler
dc859eae82 Fix the resumption of playback when suitable device is connected.
With this change the playback will resume as soon as the suitable device is connected and suppression reason is cleared (within set time out).

#minor-release

PiperOrigin-RevId: 572140309
2023-10-09 22:52:16 -07:00
jbibik
ef013c04ab Bump Media3 version numbers for 1.2.0-beta01 release
#minor-release

PiperOrigin-RevId: 572003628
(cherry picked from commit 97645a200d)
2023-10-09 22:47:37 +01:00
Googler
da49a02b44 ...Update metalava library and Reformat api.txt...
PiperOrigin-RevId: 572013340
2023-10-09 12:43:43 -07:00
jbibik
97645a200d Bump Media3 version numbers for 1.2.0-beta01 release
#minor-release

PiperOrigin-RevId: 572003628
2023-10-09 12:06:00 -07:00
tonihei
fd81c904e1 Use more targeted listening in session PlayerActivity
The current metadata updates are triggered by item transitions,
but depending on the speed of loading the playlist, the first
metadata may only be known later via metadata-change callbacks.

Slow playlist loading also means the UI stays empty and it's
beneficial to show a placeholder to avoid the impressions the
UI hangs.

Finally, clean-up by removing unused string constants and merging
all listeners into onEvents

#minor-release

PiperOrigin-RevId: 571951529
2023-10-09 09:01:14 -07:00
ibaker
33c151eb5b Fix the asset and dump file names for the standalone TTML DASH test
#minor-release

PiperOrigin-RevId: 571941997
2023-10-09 08:19:05 -07:00
jbibik
62ad1dfdf5 Update RELEASENOTES.md for 1.2.0-beta01 release
PiperOrigin-RevId: 571941830
2023-10-09 08:16:47 -07:00
simakova
67e10e9362 Cleanup layout files in Transformer demo
* Update AOSP copywright headers in all xml files in the Transformer demo app
* Use "end/start" instead of "right/left" to ensure correct behavior in right-to-left locales
* Simplify contrast_options and trim_options layout

PiperOrigin-RevId: 571933637
2023-10-09 07:38:33 -07:00
christosts
05b17b5430 Report dropped frames from the VideoSink
After 4fad529433, MediaCodecVideoRenderer does not report if frames
are dropped from the VideoSink. This commit fixes this.

#minor-release

PiperOrigin-RevId: 571905721
2023-10-09 05:04:51 -07:00
ibaker
3ed7e561bb Set Format.cueReplacementBehavior in SubtitleExtractor
This is more correct, though in reality all text-based subtitles handled
by `SubtitleExtractor` are implemented with MERGE behavior in media3.

PiperOrigin-RevId: 571888573
2023-10-09 03:31:40 -07:00
michaelkatz
f776021dcc Deflake RTSP keep-alive monitor test
Alters RTSP KeepAlive monitor test to just make sure that keep-alive message is sent.

The test was added in 42c1846984

#minor-release

PiperOrigin-RevId: 571349013
(cherry picked from commit 417970f713)
2023-10-06 19:20:13 +01:00
jbibik
efb8c70a4b Add multidex Gradle dependency to test-session-current
#minor-release

PiperOrigin-RevId: 571347856
(cherry picked from commit e63be0317f)
2023-10-06 19:20:13 +01:00
michaelkatz
f43d0f187a Update cached playbackHeadPosition when pausing after AudioTrack.stop()
In some streaming scenarios, like offload, the sink may finish writing buffers a bit before playback reaches the end of the track. In this case a player may pause while in this 'stopping' state.

The AudioTrackPositionTracker needs to update the cached values it uses to calculate position in the `PLAYSTATE_STOPPED`/`PLAYSTATE_STOPPING` states if pause/play are called during this period.

PiperOrigin-RevId: 571345914
(cherry picked from commit a789db5b41)
2023-10-06 19:20:13 +01:00
michaelkatz
5d0d30a280 Allow pause if in offload mode after writing all buffers
In offload mode, `AudioTrack#stop()` will put the track in `PLAYSTATE_STOPPING` rather than `PLAYSTATE_STOPPED`. The difference in state means that `AudioTrack` can be paused and played during this 'stopping' period.

Currently, if `AudioTrackPositionTracker#handleEndOfStream()` has been called then `DefaultAudioSink` in `pause()` won't call `AudioTrack#pause()`. `AudioTrack#pause()` should be called in this case if in offload mode.

#minor-release

PiperOrigin-RevId: 571335108
(cherry picked from commit ab42d64d6d)
2023-10-06 19:20:12 +01:00
michaelkatz
417970f713 Deflake RTSP keep-alive monitor test
Alters RTSP KeepAlive monitor test to just make sure that keep-alive message is sent.

The test was added in 42c1846984

#minor-release

PiperOrigin-RevId: 571349013
2023-10-06 08:51:27 -07:00
jbibik
e63be0317f Add multidex Gradle dependency to test-session-current
#minor-release

PiperOrigin-RevId: 571347856
2023-10-06 08:46:11 -07:00
michaelkatz
a789db5b41 Update cached playbackHeadPosition when pausing after AudioTrack.stop()
In some streaming scenarios, like offload, the sink may finish writing buffers a bit before playback reaches the end of the track. In this case a player may pause while in this 'stopping' state.

The AudioTrackPositionTracker needs to update the cached values it uses to calculate position in the `PLAYSTATE_STOPPED`/`PLAYSTATE_STOPPING` states if pause/play are called during this period.

PiperOrigin-RevId: 571345914
2023-10-06 08:37:24 -07:00
bachinger
da5a743175 Add MEDIA_PLAY_FROM_SEARCH to manifest of session demo app
This is required to make GMS send voice commands to the app.

#minor-release

PiperOrigin-RevId: 571326122
(cherry picked from commit 78f403aa7b)
2023-10-06 15:57:25 +01:00
tonihei
7e9ca0bf74 Deprecate decode-only flag.
The flag is no longer used by our components and only set and checked
in a few places to guarantee compatiblity with existing renderers and
decoders that still use it.

The flag will be removed in the future due to its design limitations.

#minor-release

PiperOrigin-RevId: 571291168
(cherry picked from commit 89d01981bc)
2023-10-06 15:57:25 +01:00
tonihei
03008b966d Remove release notes lines added by merge conflict
#minor-release

PiperOrigin-RevId: 571005643
(cherry picked from commit 49b1e0bbc2)
2023-10-06 15:57:25 +01:00
ibaker
dad362b414 Add tests for CuesWithTiming.endTimeUs
#minor-release

PiperOrigin-RevId: 570988195
(cherry picked from commit 6057b59723)
2023-10-06 15:57:25 +01:00
tofunmi
a4582be2c1 Change equalTo check in ImagePlaybackTest to atLeast
The aim of this test is to make sure the image is onscreen for the right amount of time, so to drive down flakes from the decoder taking too long, change this to an atLeast check

#minor-release

PiperOrigin-RevId: 570988044
(cherry picked from commit 9cc75ca52e)
2023-10-06 15:57:25 +01:00
tonihei
3c414fcde4 Update documentation wrongly referencing the decode-only flag
#minor-release

PiperOrigin-RevId: 570973457
(cherry picked from commit 87f1b4252e)
2023-10-06 15:57:25 +01:00
samrobinson
fbb64e2db2 Remove experimental keepAudioTrackOnSeek.
PiperOrigin-RevId: 570966027
(cherry picked from commit 068d420ba2)
2023-10-06 15:57:25 +01:00
michaelkatz
21c714d8d4 Use RTSP Setup response timeout value in KeepAliveMonitor intervalMs
Set KeepAliveMonitor to send a keep-alive message at half the timeout value, if provided, by the RTSP Setup response.

Issue: androidx/media#662
PiperOrigin-RevId: 570946237
(cherry picked from commit 42c1846984)
2023-10-06 15:57:25 +01:00
ibaker
1a0000db1d Add CuesWithTiming.endTimeUs
In most cases this is more useful than `durationUs`.

We will keep `durationUs`, and the constructor will continue to take
`startTimeUs` and `durationUs`, to allow for use-cases where we don't
know the start time but still want to indicate a duration (this will be
used to implement CEA-608 timeout).

#minor-release

PiperOrigin-RevId: 570944449
(cherry picked from commit bf7b91e57e)
2023-10-06 15:57:25 +01:00
tonihei
df85a996ba Add Decoder.setOutputStartTimeUs and use it in extension decoders
This gets rid of the reliance on the decode only flag that is still
set on input buffers to the decoder if they are less than the start
time.

We still need to set and check the decode-only flag in SimpleDecoder
to ensure compatbility with custom decoders that use the flag while
it's not fully removed.

PiperOrigin-RevId: 570736692
(cherry picked from commit a03e20fe6c)
2023-10-06 15:57:25 +01:00
tonihei
7bfddf9558 Remove wrong Javadoc
The corresponding logic has been removed in 796781d4c3

#minor-release

PiperOrigin-RevId: 570729509
(cherry picked from commit 64fe863f31)
2023-10-06 15:57:25 +01:00
tonihei
889739d33e Replace ENCODING_DTS_UHD_P2 value by reference to platform constant
#minor-release

PiperOrigin-RevId: 570696505
(cherry picked from commit 9ef1c20e7a)
2023-10-06 15:57:25 +01:00
tofunmi
c99c71b5a4 Update getName of BitmapFactoryImageDecoder
cleanup from 8f5835c51c

#minor-release

PiperOrigin-RevId: 570663437
(cherry picked from commit 572fb4676c)
2023-10-06 15:57:25 +01:00
tonihei
6d2bf513fb Add onAudioTrackInitialized/Released events
This is useful for analytics and understanding player behavior
during transitions.

#minor-release

PiperOrigin-RevId: 570623227
(cherry picked from commit 8e2bf21011)
2023-10-06 15:57:25 +01:00
rohks
55633658c6 Add nullness annotations to DecoderVideoRenderer
Also fixed a bug where format queue was polled with wrong timestamp value.

#fixit

PiperOrigin-RevId: 570420304
(cherry picked from commit a879bae1ee)
2023-10-06 15:57:25 +01:00
rohks
7957554442 Add nullness annotations to MediaCodecRenderer
#fixit

PiperOrigin-RevId: 570403923
(cherry picked from commit 7a91474af9)
2023-10-06 15:57:25 +01:00
tonihei
0480b70f36 Move decode-only handling out of MetadataDecoder interface logic
The interface requires the implementation to return null if the
decode-only flag is set. So instead of setting the flag and returning
null, we can simply not call the method and assume it's null.

The only reason where this wouldn't work is if the metadata format
has keyframe-like logic and requires previous metadata to decode
the next one. This is not something we came across before and it seems
ignorable. If that feature is needed in the future, we should instead
add a method to MetadataDecoder to set the first output timestamp.

#minor-release

PiperOrigin-RevId: 570399838
(cherry picked from commit 796781d4c3)
2023-10-06 15:57:25 +01:00
michaelkatz
2564c11834 Disable offload scheduling at set up for track transition
While sleeping for offload, position is estimated based on time playing. If asleep and AudioTrack is reused, then the position will keep incrementing as the subsequent item plays. That is until wakeup when playing position is updated to the timestamp of the second item. Offload scheduling should be disabled until track transitions fully.

PiperOrigin-RevId: 570397140
(cherry picked from commit da06bf057a)
2023-10-06 15:57:24 +01:00
jbibik
e4637d82b7 Add DashPlayback test with sideloaded TTML subtitles
The test is hidden behind the Ignore annotation due to some flakiness just like `webvttInMp4`. However, it will be removed when the subtitle parsing is moved to a pre-sample-queue architecture.

#minor-release

PiperOrigin-RevId: 570376275
(cherry picked from commit bd5a3920b8)
2023-10-06 15:57:24 +01:00
jbibik
484339e3e6 Add Dumper support for outputting multiline strings
PiperOrigin-RevId: 570348425
(cherry picked from commit b83f12c4ba)
2023-10-06 15:57:24 +01:00
tonihei
bc3dded868 Explicitly mark DecoderOutputBuffer as shouldBeSkipped if needed
In some cases, SimpleDecoder output needs to be skipped for rendering
because the decoder produces no data. This is one of the remaining
usages of BUFFER_FLAG_DECODE_ONLY at the moment and can be more
directly solved without using the flag. SimpleDecoder still needs to
check the flag though for backwards compatbility with custom decoders
while the flag is not completely removed.

PiperOrigin-RevId: 570345233
(cherry picked from commit c8aac24ffd)
2023-10-06 15:57:24 +01:00
samrobinson
27d6a9bcbd Deprecate experimental keepAudioTrackOnSeek methods.
#minor-release

PiperOrigin-RevId: 570340714
(cherry picked from commit 1bb501ab50)
2023-10-06 15:57:24 +01:00
ibaker
ffe65b358f Fix Util.scaleLargeValue/Timestamp to handle negative numbers
#minor-release

PiperOrigin-RevId: 570337535
(cherry picked from commit 9edbfa974a)
2023-10-06 15:57:24 +01:00
Copybara-Service
948491f665 Merge pull request #574 from hugohlln:main
PiperOrigin-RevId: 570037211
(cherry picked from commit b06d823238)
2023-10-06 15:57:24 +01:00
christosts
ecfddb9aeb MediaCodeVideoRenderer: flush video sink before codec
When seeking, we must first flush the video sink so it stops
using any SurfaceTextures before flushing MediaCodec.

#minor-release

PiperOrigin-RevId: 570015998
(cherry picked from commit 144bd72236)
2023-10-06 15:57:24 +01:00
ibaker
1c7b426ccb Mark test_session_current support app as MultiDexApplication
PiperOrigin-RevId: 570015354
(cherry picked from commit e9bf41ca04)
2023-10-06 15:57:24 +01:00
bachinger
4acce9bcae Update playlist UI when playlist is updated
When changing the playlist on Android Auto the UI of the
activity needs to be kept in sync.

PiperOrigin-RevId: 569528785
(cherry picked from commit 52d9fbff73)
2023-10-06 15:57:24 +01:00
michaelkatz
ab42d64d6d Allow pause if in offload mode after writing all buffers
In offload mode, `AudioTrack#stop()` will put the track in `PLAYSTATE_STOPPING` rather than `PLAYSTATE_STOPPED`. The difference in state means that `AudioTrack` can be paused and played during this 'stopping' period.

Currently, if `AudioTrackPositionTracker#handleEndOfStream()` has been called then `DefaultAudioSink` in `pause()` won't call `AudioTrack#pause()`. `AudioTrack#pause()` should be called in this case if in offload mode.

#minor-release

PiperOrigin-RevId: 571335108
2023-10-06 07:46:14 -07:00
ibaker
272428734b Return true from CuesResolver.addCues if the output changed
This belongs in the resolver, because it depends on the resolution
algorithm (and therefore the logic can't live in `TextRenderer`).

This also fixes a bug in `TextRenderer` where we were doing arithmetic
with `cues.durationUs` without checking if it was `TIME_UNSET` first.

#minor-release

PiperOrigin-RevId: 571332750
2023-10-06 07:33:43 -07:00
bachinger
78f403aa7b Add MEDIA_PLAY_FROM_SEARCH to manifest of session demo app
This is required to make GMS send voice commands to the app.

#minor-release

PiperOrigin-RevId: 571326122
2023-10-06 06:59:19 -07:00
tofunmi
e5010e3d71 Support updating the mediaItem in ExternallyLoadedMediaSource
PiperOrigin-RevId: 571308986
2023-10-06 05:24:35 -07:00
tofunmi
addfd3e986 Create ExternallyLoadedMediaPeriod and ExternallyLoadedMediaSource
PiperOrigin-RevId: 571292394
2023-10-06 03:54:19 -07:00
tonihei
89d01981bc Deprecate decode-only flag.
The flag is no longer used by our components and only set and checked
in a few places to guarantee compatiblity with existing renderers and
decoders that still use it.

The flag will be removed in the future due to its design limitations.

#minor-release

PiperOrigin-RevId: 571291168
2023-10-06 03:44:14 -07:00
simakova
d9cf350eb0 Add CompositionPlayer to the Transformer demo app
PiperOrigin-RevId: 571284291
2023-10-06 03:05:56 -07:00
tonihei
f8d2e362a5 Rename FfmpegVideoRenderer to ExperimentalFfmpegVideoRenderer
This makes it clearer that this class can't be used yet.

PiperOrigin-RevId: 571267898
2023-10-06 01:50:54 -07:00
ibaker
002ee0555d Update TextRenderer to handle CuesWithTiming instances directly
The existing `Subtitle` handling code is left intact to support the
legacy post-`SampleQueue` decoding path for now.

This also includes full support for merging overlapping `CuesWithTiming`
instances, which explains the test dump file changes, and which should
resolve the following issues (if used with the
decoder-before-`SampleQueue` subtitle logic added in
5d453fcf37):

* Issue: google/ExoPlayer#10295
* Issue: google/ExoPlayer#4794

It should also help resolve Issue: androidx/media#288, but that will also require
some changes in the DASH module to enable pre-`SampleQueue` subtitle
parsing (which should happen soon).

#minor-release

PiperOrigin-RevId: 571021417
2023-10-05 08:17:23 -07:00
tonihei
49b1e0bbc2 Remove release notes lines added by merge conflict
#minor-release

PiperOrigin-RevId: 571005643
2023-10-05 07:09:43 -07:00
ibaker
6057b59723 Add tests for CuesWithTiming.endTimeUs
#minor-release

PiperOrigin-RevId: 570988195
2023-10-05 05:51:54 -07:00
tofunmi
9cc75ca52e Change equalTo check in ImagePlaybackTest to atLeast
The aim of this test is to make sure the image is onscreen for the right amount of time, so to drive down flakes from the decoder taking too long, change this to an atLeast check

#minor-release

PiperOrigin-RevId: 570988044
2023-10-05 05:49:49 -07:00
tonihei
87f1b4252e Update documentation wrongly referencing the decode-only flag
#minor-release

PiperOrigin-RevId: 570973457
2023-10-05 04:32:40 -07:00
samrobinson
068d420ba2 Remove experimental keepAudioTrackOnSeek.
PiperOrigin-RevId: 570966027
2023-10-05 03:52:51 -07:00
huangdarwin
b153a271a3 Test: Ignore failing tests fixed in newer API versions.
PiperOrigin-RevId: 570954436
2023-10-05 02:53:15 -07:00
huangdarwin
40b990f5fa GL: Use only the index location returned by glGetAttribLocation
location and index are mostly equivalent, except that it's possible that location is more up-to-date than index, so we can just always use location.

PiperOrigin-RevId: 570950407
2023-10-05 02:35:11 -07:00
michaelkatz
42c1846984 Use RTSP Setup response timeout value in KeepAliveMonitor intervalMs
Set KeepAliveMonitor to send a keep-alive message at half the timeout value, if provided, by the RTSP Setup response.

Issue: androidx/media#662
PiperOrigin-RevId: 570946237
2023-10-05 02:13:54 -07:00
ibaker
bf7b91e57e Add CuesWithTiming.endTimeUs
In most cases this is more useful than `durationUs`.

We will keep `durationUs`, and the constructor will continue to take
`startTimeUs` and `durationUs`, to allow for use-cases where we don't
know the start time but still want to indicate a duration (this will be
used to implement CEA-608 timeout).

#minor-release

PiperOrigin-RevId: 570944449
2023-10-05 02:04:26 -07:00
huangdarwin
89a1bb528d Flush: VideoFrameProcessor Image Input.
Much simpler than ExternalTextureManager flushing, because
ExternalTextureManager complexity is due to decoder race condition behavior,
which we won't see for Bitmaps due to a more well-defined interface.

This is needed to test texture output flushing.

PiperOrigin-RevId: 570896363
2023-10-04 21:20:23 -07:00
tonihei
a03e20fe6c Add Decoder.setOutputStartTimeUs and use it in extension decoders
This gets rid of the reliance on the decode only flag that is still
set on input buffers to the decoder if they are less than the start
time.

We still need to set and check the decode-only flag in SimpleDecoder
to ensure compatbility with custom decoders that use the flag while
it's not fully removed.

PiperOrigin-RevId: 570736692
2023-10-04 10:37:25 -07:00
tonihei
64fe863f31 Remove wrong Javadoc
The corresponding logic has been removed in 796781d4c3

#minor-release

PiperOrigin-RevId: 570729509
2023-10-04 10:13:12 -07:00
tonihei
9ef1c20e7a Replace ENCODING_DTS_UHD_P2 value by reference to platform constant
#minor-release

PiperOrigin-RevId: 570696505
2023-10-04 08:09:04 -07:00
tofunmi
572fb4676c Update getName of BitmapFactoryImageDecoder
cleanup from 8f5835c51c

#minor-release

PiperOrigin-RevId: 570663437
2023-10-04 05:23:32 -07:00
oceanjules
12332a4afc Remove FfmpegVideoRenderer from Media3 1.2.0 release 2023-10-04 13:13:58 +01:00
tonihei
8e2bf21011 Add onAudioTrackInitialized/Released events
This is useful for analytics and understanding player behavior
during transitions.

#minor-release

PiperOrigin-RevId: 570623227
2023-10-04 01:50:15 -07:00
rohks
a879bae1ee Add nullness annotations to DecoderVideoRenderer
Also fixed a bug where format queue was polled with wrong timestamp value.

#fixit

PiperOrigin-RevId: 570420304
2023-10-03 10:06:35 -07:00
rohks
7a91474af9 Add nullness annotations to MediaCodecRenderer
#fixit

PiperOrigin-RevId: 570403923
2023-10-03 09:05:49 -07:00
tonihei
796781d4c3 Move decode-only handling out of MetadataDecoder interface logic
The interface requires the implementation to return null if the
decode-only flag is set. So instead of setting the flag and returning
null, we can simply not call the method and assume it's null.

The only reason where this wouldn't work is if the metadata format
has keyframe-like logic and requires previous metadata to decode
the next one. This is not something we came across before and it seems
ignorable. If that feature is needed in the future, we should instead
add a method to MetadataDecoder to set the first output timestamp.

#minor-release

PiperOrigin-RevId: 570399838
2023-10-03 08:49:18 -07:00
michaelkatz
da06bf057a Disable offload scheduling at set up for track transition
While sleeping for offload, position is estimated based on time playing. If asleep and AudioTrack is reused, then the position will keep incrementing as the subsequent item plays. That is until wakeup when playing position is updated to the timestamp of the second item. Offload scheduling should be disabled until track transitions fully.

PiperOrigin-RevId: 570397140
2023-10-03 08:37:31 -07:00
jbibik
bd5a3920b8 Add DashPlayback test with sideloaded TTML subtitles
The test is hidden behind the Ignore annotation due to some flakiness just like `webvttInMp4`. However, it will be removed when the subtitle parsing is moved to a pre-sample-queue architecture.

#minor-release

PiperOrigin-RevId: 570376275
2023-10-03 07:08:58 -07:00
jbibik
b83f12c4ba Add Dumper support for outputting multiline strings
PiperOrigin-RevId: 570348425
2023-10-03 04:47:31 -07:00
tonihei
c8aac24ffd Explicitly mark DecoderOutputBuffer as shouldBeSkipped if needed
In some cases, SimpleDecoder output needs to be skipped for rendering
because the decoder produces no data. This is one of the remaining
usages of BUFFER_FLAG_DECODE_ONLY at the moment and can be more
directly solved without using the flag. SimpleDecoder still needs to
check the flag though for backwards compatbility with custom decoders
while the flag is not completely removed.

PiperOrigin-RevId: 570345233
2023-10-03 04:28:21 -07:00
samrobinson
1bb501ab50 Deprecate experimental keepAudioTrackOnSeek methods.
#minor-release

PiperOrigin-RevId: 570340714
2023-10-03 04:09:49 -07:00
ibaker
9edbfa974a Fix Util.scaleLargeValue/Timestamp to handle negative numbers
#minor-release

PiperOrigin-RevId: 570337535
2023-10-03 03:52:02 -07:00
huangdarwin
fa51f8cd4d Effect: Move common statement out of switch/case
PiperOrigin-RevId: 570323141
2023-10-03 02:37:48 -07:00
huangdarwin
8953f26a5c Test: Move OpenGL tone mapping capabilities check to utility method.
PiperOrigin-RevId: 570316091
2023-10-03 02:00:55 -07:00
huangdarwin
9ca5d50b2d Test: Ignore failing tests fixed in newer API versions.
PiperOrigin-RevId: 570061196
2023-10-02 07:34:58 -07:00
Copybara-Service
b06d823238 Merge pull request #574 from hugohlln:main
PiperOrigin-RevId: 570037211
2023-10-02 05:36:28 -07:00
microkatz
f13a2e7e0f Updated method description to take into account the new void return type 2023-10-02 11:29:15 +00:00
microkatz
cd29d4637d Simplified class fields and method parameters due to using ArrayList 2023-10-02 11:29:15 +00:00
microkatz
34a0e3fa09 Updated typings to be List rather than ArrayList 2023-10-02 11:29:15 +00:00
microkatz
4b1b570c80 Added release note about DASH change 2023-10-02 11:29:15 +00:00
microkatz
8a6f4a91e9 Format with google-java-format 2023-10-02 11:29:15 +00:00
hhouillon
355484ebfb UrlTemplate uses ArrayLists instead of Arrays 2023-10-02 11:29:15 +00:00
Hugo Houillon
81e2472034 Dash UrlTemplate parses template using ArrayLists 2023-10-02 11:29:15 +00:00
hhouillon
022444e751 Edit DASH UrlTemplate identifiers parser and add UrlTemplate tests 2023-10-02 11:29:15 +00:00
hhouillon
eb5cbd902b DASH UrlTemplate parses template if it contains more than one time each identifier 2023-10-02 11:29:15 +00:00
christosts
144bd72236 MediaCodeVideoRenderer: flush video sink before codec
When seeking, we must first flush the video sink so it stops
using any SurfaceTextures before flushing MediaCodec.

#minor-release

PiperOrigin-RevId: 570015998
2023-10-02 04:03:23 -07:00
ibaker
e9bf41ca04 Mark test_session_current support app as MultiDexApplication
PiperOrigin-RevId: 570015354
2023-10-02 03:59:36 -07:00
bachinger
52d9fbff73 Update playlist UI when playlist is updated
When changing the playlist on Android Auto the UI of the
activity needs to be kept in sync.

PiperOrigin-RevId: 569528785
2023-09-29 10:42:58 -07:00
ibaker
8f5835c51c Rename DefaultImageDecoder to BitmapFactoryImageDecoder
This reflects the documented behaviour of this class.

#minor-release

PiperOrigin-RevId: 569475137
2023-09-29 06:27:24 -07:00
claincly
34dddfe9d5 Add previewing specific video graph.
PiperOrigin-RevId: 569473178
2023-09-29 06:16:16 -07:00
christosts
0b4638af15 ExportTest: make 8K asset and trim
Move remote 8K file to local and trim to 320ms.

Trim done with ffmpeg:

`ffmpeg -i {remote_file} -t 0.3 -c:v copy -c:a copy 8k24fps_300ms.mp4`

PiperOrigin-RevId: 569449962
2023-09-29 04:07:40 -07:00
bachinger
cbd23925d5 Add demos/session-automotive module
This change also enables Android Auto support for the
session demo.

PiperOrigin-RevId: 569448376
2023-09-29 04:00:58 -07:00
bachinger
a3b1661513 Bump Media3 version numbers for 1.2.0-alpha02
PiperOrigin-RevId: 569269992
2023-09-28 13:15:46 -07:00
ibaker
d50f662b10 Mark DefaultImageDecoder.BitmapDecoder as @VisibleForTesting
It seems likely we will define a new "image decoder" interface that
returns `ListenableFuture<Bitmap>`, and naming that will be
hard/annoying if we need to keep this interface working too.

It's also not really clear what a non-test implementation of this
interface would be expected to do, since `DefaultImageDecoder` is
documented to always decode using `BitmapFactory`.

#minor-release

PiperOrigin-RevId: 569206325
2023-09-28 09:33:59 -07:00
Copybara-Service
6d77838a6b Merge pull request #675 from shanujshekhar:shanujs/add-new-apis-exomediadrm
PiperOrigin-RevId: 569205163
2023-09-28 09:31:14 -07:00
claincly
cd6f8a42a5 Move Single/MultiVideoGraph impl to effect
PiperOrigin-RevId: 569188658
2023-09-28 08:27:06 -07:00
Ian Baker
a1767d349a Fix review comments 2023-09-28 15:57:13 +01:00
ibaker
d716de02aa Suppress lint in PlayerControlView and TrackSelectionDialogBuilder
PiperOrigin-RevId: 569165562
2023-09-28 06:48:54 -07:00
bachinger
db26b378f8 Update release notes for 1.2.0-alpha02
PiperOrigin-RevId: 569161165
2023-09-28 06:29:42 -07:00
bachinger
2debf0187a Split demo service into its own module for reuse
To support Automotive with the session demo, we need a separate app module.
To do this we need to split the service into its own module and make it
usable from different modules.

PiperOrigin-RevId: 568975271
2023-09-27 15:21:23 -07:00
bachinger
0b0d02c3e4 Add isAutomotiveController and isAutoCompanionController
Issue: androidx/media#561
Issue: androidx/media#644
Issue: androidx/media#645
PiperOrigin-RevId: 568948230
2023-09-27 13:45:17 -07:00
bachinger
99086b4007 Add default implementation of Callback.onSubscribe
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
2023-09-27 12:19:34 -07:00
huangdarwin
1df2210cf4 Test: Update HDR GL tone-map fallback string.
PiperOrigin-RevId: 568920716
2023-09-27 12:05:30 -07:00
tonihei
77ba0292ad Add position interpolation to MediaControllerImplLegacy
Without this, the position won't udpate until the session sends
a new playback state.

PiperOrigin-RevId: 568889286
2023-09-27 10:23:27 -07:00
ibaker
b4771e07b5 Mark HEIF decoding as only supported on API 26+
https://developer.android.com/guide/topics/media/platform/supported-formats#image-formats

#minor-release

PiperOrigin-RevId: 568864219
2023-09-27 08:56:06 -07:00
samrobinson
4e10c41bcc Throw Exception if posting to application handler fails.
PiperOrigin-RevId: 568799683
2023-09-27 03:30:30 -07:00
michaelkatz
c12fb67468 Update dumpfile tests to only print ColorInfo fields that are set
PiperOrigin-RevId: 568789489
2023-09-27 02:34:29 -07:00
samrobinson
c03a0fb66b Limit SequenceAssetLoader variable scope.
All usages of these variables are within the SampleConsumerWrapper,
so limit them to that scope.

PiperOrigin-RevId: 568582645
2023-09-26 10:38:07 -07:00
jbibik
8b71712edc Change the DASH playback dump for webvtt in mp4 to include subtitles
#minor-release

PiperOrigin-RevId: 568567703
2023-09-26 09:48:52 -07:00
Ian Baker
8e6d3e7541 Reformat some javadoc and use Guava empty list 2023-09-26 16:07:38 +01:00
Shanuj Shekhar
aba15b6952 Add new APIs to ExoMediaDrm
Changes
---
- Added `removeOfflineLicense(byte[])` and `getOfflineLicenseKeySetIds` and consumed them in their implementations

Background
---
- These APIs will help in addressing an increasing amount of `java.lang.IllegalArgumentException: Failed to restore keys: BAD_VALUE` which is our top playback error in our app
	- Based on our discussion with Widevine team and [this exoplayer issue](https://github.com/google/ExoPlayer/issues/11202#issuecomment-1708792594)
		- TL;DR: The failure occurs on startup if the user has 200+ offline licenses, we would like to add the functionality to remove offline licenses

**Note: Why we want these APIs in ExoMediaDrm and not in OfflineLicenseHelper**
	- As per the issue above, we would like to access these 2 public APIs in MediaDrm that don’t exist in `OfflineLicenseHelper` or `ExoMediaDrm`
		- APIs interested in:
			- [MediaDrm#removeOfflineLicense()](https://developer.android.com/reference/android/media/MediaDrm#removeOfflineLicense(byte%5B%5D)): To remove offline license
			- [MediaDrm#getOfflineLicenseKeySetIds()](https://developer.android.com/reference/android/media/MediaDrm#getOfflineLicenseKeySetIds()): To see number of offline licenses on startup

		- We use `OfflineLicenseHelper` to download license for L1 and we don't interact with `ExoMediaDrm` directly. But for the alternate Widevine integration, we directly depend on `ExoMediaDrm` APIs to override and call CDM Native APIs.
		- We would like to have the functionality of removing offline licenses for both integration which would need access to above APIs in `ExoMediaDrm`.

Links
---
- https://github.com/androidx/media/issues/659
2023-09-26 10:05:36 -04:00
samrobinson
0b62d37425 Verify a thread is alive before sending a message to it.
PiperOrigin-RevId: 568515736
2023-09-26 06:09:19 -07:00
tonihei
69ffac28bb Set SurfaceView lifecycle to follow attachment in PlayerView
This avoids destroying the surface if PlayerView is hidden in the
view hierarchy.

PiperOrigin-RevId: 568501459
2023-09-26 04:58:11 -07:00
tonihei
212f1f8ea8 Update decode-only flag logic in non-MediaCodec-renderers
MediaCodecRenderer has already been updated to not rely on the
input stream to mark its samples as decode-only and instead use
a simple time-based comparison to achieve the same effect.

This change makes the same update for all other renderers that
either use the flag directly or forward to a "decoder" instance.

PiperOrigin-RevId: 568232212
2023-09-25 08:53:19 -07:00
claincly
884b3de69a Update VideoSink queueBitmap() to match VideoFrameProcessor
PiperOrigin-RevId: 568226567
2023-09-25 08:31:35 -07:00
bachinger
ffd7bb5639 Resolve and dispatch media button events within Media3
Before this change, media button events are routed from `onStartCommand`
of the `MediaSessionService` to  the `MediaSessionCompat`, resolved by
the legacy library to a session command called on
`MediaSessionCompat.Callback` from where the command is delegated back
to the Media3 session.

With this change the keycode is resolved directly to a Media3 command
that is sent to the session through the media notification controller
of the session.

After this change, a playback or custom command sent to the session
from a notification, either as a pending intent (before API 33) or as
a legacy session command, look the same and the caller is the
media notification controller on all API levels.

PiperOrigin-RevId: 568224123
2023-09-25 08:19:33 -07:00
bachinger
5e05e2ec22 Pass down ControllerInfo from service to session when connecting
With this change, the `ControllerInfo` passed to
`MediaSessionService.onGetSession(ControllerInfo)`
is the same instance that is passed later to all
callback methods of `MediaSession.Callback`.

PiperOrigin-RevId: 568216855
2023-09-25 07:50:12 -07:00
ibaker
d965516dc9 Fix 'unused return value' error in SubtitleViewUtilsTest
PiperOrigin-RevId: 568170342
2023-09-25 03:50:30 -07:00
michaelkatz
916b4b0ad7 Allow custom methods in Rtsp Options response public header
ExoPlayer will not fail playback if an RTSP server responds to the Options request with an unknown RTSP method request type. ExoPlayer will parse the response and just not call methods it does not know how to use.

Issue: androidx/media#613
PiperOrigin-RevId: 568152076
2023-09-25 02:15:42 -07:00
ibaker
1f86a4e48d Remove static initializer block from MediaSessionKeyEventTest
PiperOrigin-RevId: 568149422
2023-09-25 02:02:05 -07:00
huangdarwin
444cb3fb3a Test: Rename getBitmap to getBitmapAtPresentationTimeUs
PiperOrigin-RevId: 567683139
2023-09-22 12:06:57 -07:00
huangdarwin
8a40952e1b Test: Use timestamp iterator in texture output test.
Simplify tests, before we add some similar tests.

PiperOrigin-RevId: 567666340
2023-09-22 11:02:58 -07:00
huangdarwin
ba8c85a277 Compositor: Add VideoCompositorSettings to Composition.
This allows apps using Transformer to customize how a Composition is used.

PiperOrigin-RevId: 567633129
2023-09-22 08:51:35 -07:00
claincly
42d9879d47 Add missing VideoGraph javadoc param
PiperOrigin-RevId: 567621861
2023-09-22 07:58:55 -07:00
bachinger
742410d517 Use proxy controller to maintain platform session and notification
With this change, the notification controller that is connected by
`MediaNotificationManager`, is used as a proxy controller of the
System UI controller. An app can use the proxy at connection time
and during the lifetime of the session for configuration of the
platform session and the media notification on all API levels.

This includes using custom layout and available player and session
commands of the proxy to maintain the platform session (actions,
custom actions, session extras) and the `MediaNotification.Provider`.

The legacy System UI controller is hidden from the public API,
instead the app interacts with the Media3 proxy:

- System UI is hidden from `MediaSession.getConnectedControllers()`.
- Calls from System UI to methods of `MediaSession.Callback`/
  `MediaLibrarySession.Callback` are mapped to the `ControllerInfo`
  of the proxy controller.
- When `getControllerForCurrentRequest()` is called during an operation of
  System UI the proxy `ControllerInfo` is returned.

PiperOrigin-RevId: 567606117
2023-09-22 06:36:22 -07:00
tonihei
4f4335943c Cross-reference per-stream volume methods from device volume methods
The per-stream methods are generally preferred and having a reference
to them from the device-wide methods may help with discoverability.

Issue: google/ExoPlayer#11295
PiperOrigin-RevId: 567604785
2023-09-22 06:30:56 -07:00
claincly
d9563b133e Split VideoGraph interface and move VideoGraph to common
PiperOrigin-RevId: 567599249
2023-09-22 06:01:01 -07:00
tonihei
b2016cc484 Adjust externally loaded image URI MIME type definition
Adjust the Javadoc to highlight that data of this MIME type just contains a URI, not the actual image content.

And also remove the superfluous "key" part of the MIME type string that doesn't
really add information (and it's also really just an URI, not an URI key).

PiperOrigin-RevId: 567560238
2023-09-22 02:12:53 -07:00
huangdarwin
190fd7abc6 Compositor: Clarify javadoc, to mention VideoCompositorSettings.
Clarify that we use OverlaySettings to place frames over one another,
as passed in via VideoCompositorSettings

PiperOrigin-RevId: 567321828
2023-09-21 09:01:32 -07:00
ibaker
fc91ee1d7b Session tests: Add missing CountdownLatch.await()
This helps deflake this test.

PiperOrigin-RevId: 567288892
2023-09-21 06:30:24 -07:00
rohks
b4d03a9515 Bump IMA SDK version to 3.31.0
#minor-change

PiperOrigin-RevId: 567282094
2023-09-21 05:54:13 -07:00
huangdarwin
0675e48685 HDR: Update HdrMode fallback to use OpenGL tone-mapping.
OpenGL tone-mapping is more reliable and widely supported than
MediaCodec tone-mapping.

PiperOrigin-RevId: 567267389
2023-09-21 04:33:09 -07:00
christosts
603d36726f Move DefaultImageDecoderTest in tests
Move DefaultImageDecoderTest in tests since we can decode images with
Robolectric's native graphics mode.

PiperOrigin-RevId: 567259458
2023-09-21 03:53:42 -07:00
Googler
2052be0f51 Add new setIntsUniform for setting ivec uniforms in shaders.
PiperOrigin-RevId: 567102956
2023-09-20 15:50:43 -07:00
Googler
bfd4b6a188 Move GlProgram.loadAsset to Util and make it public.
PiperOrigin-RevId: 567025091
2023-09-20 11:21:55 -07:00
christosts
7b580d3cf8 Add performance playback test for video effects
PiperOrigin-RevId: 567000714
2023-09-20 10:11:08 -07:00
claincly
5ae21b453a Extract the VideoSinkProvider interface
PiperOrigin-RevId: 566972998
2023-09-20 08:31:13 -07:00
claincly
67900c3e81 Fix not setting videoEffect in CompositingVSP
The current code only set the videoEffects when CVSP is initialized, which
happens after `player.prepare()`. But it's valid that videoEffects are set
before calling `prepare()`.

PiperOrigin-RevId: 566941216
2023-09-20 06:11:32 -07:00
tofunmi
234f7525f0 Add MimeTypes.EXTERNALLY_LOADED_IMAGE
PiperOrigin-RevId: 566915171
2023-09-20 03:55:36 -07:00
ibaker
134f53bdb2 TTML: Remove unused CellResolution.columns and collapse to int rows
PiperOrigin-RevId: 566908824
2023-09-20 03:22:21 -07:00
michaelkatz
3cf9c08dca Create AudioOffloadPreferences class
Move audio offload mode related interfaces and definitions from `TrackSelectionParameters` to a new `AudioOffloadModePreferences` class.

PiperOrigin-RevId: 566905017
2023-09-20 03:02:51 -07:00
claincly
08c72b927d Use a longer timeout for running Transformer on emulators
PiperOrigin-RevId: 566688502
2023-09-19 11:19:13 -07:00
ibaker
db7c33b01c Deprecate Util.getAudioContentTypeForStreamType
This method isn't used by the library (since <unknown commit>).

It doesn't really work well (e.g. arbitrarily defaults to `MUSIC` when
`UNKNOWN` would be a better default). There's no suggested replacement.

PiperOrigin-RevId: 566676744
2023-09-19 10:42:49 -07:00
ibaker
694d040d7e Re-land: TtmlParser implementation - moved from TtmlDecoder
This change uses the new incremental overloads of `SubtitleParser` to
avoid introducing the performance regression caused by the original
change requiring all cues to be fully parsed before the first could be
shown on screen.

`TtmlDecoder` which used to be `SimpleSubtitleDecoder` will now be
called `TtmlParser` and implement `SubtitleParser` interface. For
backwards compatibility, we will have the same functionality provided
by `DelegatingSubtitleDecoder` backed-up by a new `TtmlParser`
instance.

PiperOrigin-RevId: 566671398
2023-09-19 10:25:48 -07:00
ibaker
e357d9f218 Don't call MediaSession.Callback.onPostConnect if connecting failed
I spotted that this looked wrong while investigating test various
session test failures. However, changing this logic doesn't seem to
affect the tests so I don't know if the change is an improvement or not.

PiperOrigin-RevId: 566655318
2023-09-19 09:29:40 -07:00
claincly
3cad5ed726 Remove using Consumer of ExportException in VideoGraphs
PiperOrigin-RevId: 566651267
2023-09-19 09:14:33 -07:00
ibaker
5661794a8f Update external/guava/METADATA link from master to main branch
PiperOrigin-RevId: 566645434
2023-09-19 08:55:48 -07:00
tianyifeng
ceac1f458f Add two helpful methods to FakeMediaSource for testing
PiperOrigin-RevId: 566636545
2023-09-19 08:14:19 -07:00
jbibik
39c1ac7f3a Move setAudioAttributes from ExoPlayer to Player
PiperOrigin-RevId: 566607528
2023-09-19 06:08:37 -07:00
ibaker
f35e7bdc6a Switch WebvttParserTest to use partial-output method
PiperOrigin-RevId: 566598735
2023-09-19 05:19:07 -07:00
ibaker
92a3f3a8cd Update WebvttParser to implement new partial-output method
This requires adapting the 'to `CuesWithTiming` list' logic to work with
the new partial-output API, and that needs a private method so it's no
longer a good fit for a default method on `Subtitle` - hence moving it
to a new utility class.

Also update the implementation to never return `UNSET` duration (this is
an equivalent change to the `SsaParser` change in 9631923440).

PiperOrigin-RevId: 566598094
2023-09-19 05:15:08 -07:00
claincly
24e700c216 Decouple output size listener and setting output surface
This is because `onOutputSizeChanged()` should in theory be called on the
listener executor.

PiperOrigin-RevId: 566591784
2023-09-19 04:43:18 -07:00
jbibik
0c918d2c47 Fix ErrorProne lint actionable items
PiperOrigin-RevId: 566571653
2023-09-19 03:01:20 -07:00
huangdarwin
93d06180ef Compositor: Remove obsolete TODO
PiperOrigin-RevId: 566327798
2023-09-18 09:39:29 -07:00
rohks
fe199455e7 Add QuickTime (Classic) support to Mp4Extractor
PiperOrigin-RevId: 566272132
2023-09-18 05:29:29 -07:00
ibaker
2c0d9ba4c3 Rollback of d58f5fdf7d
PiperOrigin-RevId: 566258299
2023-09-18 04:12:21 -07:00
tonihei
f89053dbb0 Change UI module documentation link
PiperOrigin-RevId: 566257915
2023-09-18 04:09:46 -07:00
samrobinson
c4fb755283 Open progress conditionVariable when quitting internal thread.
If getProgress is blocking whilst the internal thread calls endInternal
(for error or success), the condition is never opened. Related to this,
onCompleted and onError are therefore never surfaced to the app.

progressState is accessed from application and internal threads, so
should be marked volatile to prevent a thread caching the value.

PiperOrigin-RevId: 565720184
2023-09-15 10:50:07 -07:00
claincly
fef16b05d9 Fix flaky test becasue ExtTexMgr is not using emulator settings
When running on emulators, ExternalTextureManager needs a longer timeout for
forcing EOS, but we didn't catch a device name running on blaze: `generic_x86`

PiperOrigin-RevId: 565513152
2023-09-14 16:45:38 -07:00
huangdarwin
c77b8c8479 Compositor: Split out OpenGL drawing logic into inner class.
Organize logic a bit by splitting logic about how we draw using OpenGL onto a
texture, out from the larger class, which has lots of logic discussing how we select
frames and streams.

No functional change intended, but a few method calls are shuffled around to
simplify things.

PiperOrigin-RevId: 565426225
2023-09-14 11:26:14 -07:00
tofunmi
16b0ea850f Support multiple streams in the ImageRenderer
PiperOrigin-RevId: 565410924
2023-09-14 10:37:58 -07:00
huangdarwin
5ef5d46708 Compositor: Move Settings to DefaultVideoCompositor.
This previously was in the VideoCompositor class, but wasn't
referenced at all from that interface.

PiperOrigin-RevId: 565409646
2023-09-14 10:33:25 -07:00
sheenachhabra
03b793e2ee Read muxedPartialVideo only in MUXER_MODE_MUX_PARTIAL_VIDEO mode
When we switch from MUXER_MODE_MUX_PARTIAL_VIDEO to MUXER_MODE_APPEND_VIDEO
`muxedPartialVideo` will already be `true` so `endTrack` method will pass
through this `if(muxedPartialVideo)` check which is incorrect.

PiperOrigin-RevId: 565398117
2023-09-14 09:54:25 -07:00
ibaker
d58f5fdf7d Upgrade Guava dependency to 32.1.2
Android's version of Guava was upgraded in http://r.android.com/2731599

PiperOrigin-RevId: 565396612
2023-09-14 09:50:10 -07:00
sheenachhabra
dc865e6e98 Return TIME_UNSET for last sync sample if there is no video track
PiperOrigin-RevId: 565395263
2023-09-14 09:44:42 -07:00
huangdarwin
98009d396a Compositor: Document VideoCompositor interface thread safety.
PiperOrigin-RevId: 565388982
2023-09-14 09:22:08 -07:00
christosts
c0e11e0edd Move bitmap loader tests in test
These tests were under androidTest because we needed a functional
BitmapFactory. Robolectric now supports decoding bitmaps so moving them
under tests.

PiperOrigin-RevId: 565181239
2023-09-13 15:40:55 -07:00
claincly
bf25b3e89d Move listener methods into private method for readability
The logic that handles components' boundaries are grouped together in private
methods, like handling VideoCompositor's output textures.

PiperOrigin-RevId: 565131579
2023-09-13 12:45:40 -07:00
claincly
1d8135e563 Add test for MultiInputVideoGraph
This test composites the first frame from two video inputs.

PiperOrigin-RevId: 565090338
2023-09-13 10:28:07 -07:00
claincly
5106f2f45a Rollback of e2882c051b
PiperOrigin-RevId: 565069442
2023-09-13 09:15:35 -07:00
ibaker
56fbf7377e Add javadoc to SubtitleParser.OutputOptions
PiperOrigin-RevId: 565066243
2023-09-13 09:04:27 -07:00
ibaker
f8b23da7af Add overflow tests for sample count to duration conversion methods
These methods were updated to use the new overflow-resistant
`scaleLargeValue` method in 885ddb167e.

PiperOrigin-RevId: 565059609
2023-09-13 08:38:14 -07:00
ibaker
d111976125 Change SubtitleParser interface to support incremental output
This change introduces two new types of method to `SubtitleParser`:
1. `parse()` methods that take a `Consumer<CuesWithTiming>` and return `void`
2. `parseToLegacySubtitle` method that returns `Subtitle`

(1) ensures that in the new 'parse before SampleQueue' world we can
write cues to the `SampleQueue` as soon as they're ready - this is
especially important when parsing monolithic text files, e.g. for a
whole movie.

(2) ensures that during the transition, the legacy 'parse after
SampleQueue' behaviour doesn't see any regressions in 'time to first
cue being shown'. Previously we had a single implementation to convert
from `List<CuesWithTiming>` to `Subtitle`, but this relies on the
complete list of cues being available, which can take a long time for
large files in some formats (with ExoPlayer's current parsing logic).
By allowing implementations to customise the way they create a
`Subtitle`, we can directly re-use the existing logic, so that the
'time to first cue being shown' should stay the same.

This change migrates all **usages** to the new methods, but doesn't
migrate any **implementations**. I will migrate the implementations in
follow-up CLs before deleting the old list-returning `parse()` methods.

PiperOrigin-RevId: 565057945
2023-09-13 08:33:29 -07:00
huangdarwin
e0de405e68 Compositor: Move input source javadoc to class-level.
As discussed offline, this is important for users of the class, and not all users may choose to read method javadoc, so best to make sure it's visible by leaving it at the class-level.

PiperOrigin-RevId: 565057677
2023-09-13 08:30:15 -07:00
ibaker
fdfec60f6e Remove some debugging lines in AtomParsers
These were accidentally added in 885ddb167e

PiperOrigin-RevId: 565035337
2023-09-13 06:49:25 -07:00
michaelkatz
85c944b955 Enable offload scheduling by default for audio-only offload playback
Removed `ExoPlayer.experimentalSetOffloadSchedulingEnabled` as scheduling will be enabled by default when offload is enabled for audio-only playback.

In addition, the `experimental` key word was taken out of the following
method signatures:
* `ExoPlayer.experimentalIsSleepingForOffload`
* `AudioOffloadListener.onExperimentalSleepingForOffloadChanged`
* `AudioOffloadListener.onExperimentalOffloadedPlayback`

PiperOrigin-RevId: 565035289
2023-09-13 06:46:50 -07:00
ibaker
abaf3e7aa1 Add Format.cueReplacementBehavior
Previously any `CuesWithTiming.durationUs` could be `TIME_UNSET`,
meaning it should be replaced by the next `CuesWithTiming` instance
(instead of being merged if the durations overlap, which is currently
the expected behavior for all `CuesWithTiming` with a 'real' duration).

This technically allowed a single subtitle track to include a mixture of
`CuesWithTiming` that should be merged, and some that should be
replaced. This is not actually needed for any of the subtitle formats
currently supported by ExoPlayer - in all cases a format expects either
all cues to be merged, or each cue to replace the previous one.

Supporting this mixture of merging and replacing in `TextRenderer` ended
up being very complicated, and it seemed a bit pointless since it's not
actually needed. This change means a given subtitle track either merges
**all** cues (meaning `CuesWithTiming.durationUs = C.TIME_UNSET` is not
allowed), or **every** cue is replaced by the next one (meaning
`CuesWithTiming.durationUs` may be set (to allow for cues to 'time out',
needed for CEA-608), or may be `TIME_UNSET`).

This value will be used in a subsequent change that adds cue-merging
support to `TextRenderer`.

PiperOrigin-RevId: 565028066
2023-09-13 06:09:45 -07:00
Googler
282171cb6f Rollback of e2882c051b
PiperOrigin-RevId: 564802194
2023-09-12 12:40:57 -07:00
ibaker
885ddb167e Add general-purpose overflow-resistant divide+multiply util method
This is equivalent to the existing `scaleLargeTimestamp` method with the
following changes/improvements:
* No longer specific to timestamps (there was nothing inherently
  time-specific about the logic in `scaleLargeTimestamp`, but the name
  and docs suggested it shouldn't be used for non-timestamp use-cases).
* Additional 'perfect division' checks between `value` and `divisor`.
* The caller can now provide a `RoundingMode`.
* Robust against `multiplier == 0`.
* Some extra branches before falling through to (potentially lossy)
  floating-point math, including trying to simplify the fraction with
  greatest common divisor to reduce the chance of overflowing `long`.

This was discussed during review of 6e91f0d4c5

This change also includes some golden test file updates - these
represent a bug fix where floating-point maths had previously resulted
in a timestamp being incorrectly rounded down to the previous
microsecond. These changes are due to the 'some more branches' mentioned
above.

PiperOrigin-RevId: 564760748
2023-09-12 10:22:57 -07:00
ibaker
320a45f7d6 Session tests: Log when no controllers are connected
While debugging various session tests failure I found that sometimes
this list was empty (e.g. when a controller had failed to connect, or
hadn't finished connecting yet) - resulting in these methods being
silent no-ops. I think it's basically never expected for there to be no
controllers connected when these methods are invoked, so this logs at
ERROR level to give a clue of what happened when looking at the test
logcat.

PiperOrigin-RevId: 564750969
2023-09-12 09:52:21 -07:00
claincly
e2882c051b Implement MultipleInputVideoGraph
Also adds DebugTraceUtil category to track MultipleInputVideoGraph events.

PiperOrigin-RevId: 564749202
2023-09-12 09:45:23 -07:00
sheenachhabra
b042943102 Add different modes in MuxerWrapper
For pause and resume feature we need to use same `MuxerWrapper`
for `remuxing processed video` and then to `process remaining video`.
In order to use same `MuxerWrapper` across `different Exports`
we need to preserve its state.

PiperOrigin-RevId: 564728396
2023-09-12 08:28:35 -07:00
ibaker
fe10f5ae18 Add tests for Util.scaleLargeTimestamp
This ensures we don't regress this behaviour when introducing
`scaleLargeValue`.

PiperOrigin-RevId: 564708566
2023-09-12 07:00:22 -07:00
ibaker
624eb1d7cb Add missing this.session null check in MockMediaLibraryService.
This aligns the equivalent implementation in `MockMediaSessionService`,
and it looks more correct to me - but the tests seem to pass both with
and without this change (and it doesn't seem to affect flakiness
either).

PiperOrigin-RevId: 564689493
2023-09-12 05:33:24 -07:00
ibaker
cf15463b1f Fix parameter comments in MediaBrowser tests
The parameter name was changed in 782a69e38c

PiperOrigin-RevId: 564688136
2023-09-12 05:25:22 -07:00
michaelkatz
3742f6b1f5 Allow renderer recovery with disabling offload if failed at first write
If offload fails at first write with [ERROR_DEAD_OBJECT](https://developer.android.com/reference/android/media/AudioTrack#ERROR_DEAD_OBJECT), then try disabling offload mode and try again. This allows recovery in a state where AudioTrack succeeds init in offload mode but writing is failing.

Issue: androidx/media#627
PiperOrigin-RevId: 564402181
2023-09-11 09:04:17 -07:00
ibaker
d77c707cd3 Use ISE instead of AssertionError in MockMediaLibraryService
Also pass the full cause instead of just the message.

PiperOrigin-RevId: 564313917
2023-09-11 02:28:38 -07:00
tofunmi
23665090ed Support Jpeg image track extraction in exoplayer
PiperOrigin-RevId: 563818198
2023-09-08 12:15:10 -07:00
tofunmi
be5fa6d130 Support image track extraction for JPEG
PiperOrigin-RevId: 563746945
2023-09-08 07:32:10 -07:00
tonihei
f285334a15 Deprecate multi-window time bar mode
It's much better to merge the windows at source level to reflect the
same state everywhere (e.g. notifications, player state, etc). This
can be done with ConcatenatingMediaSource2.

PiperOrigin-RevId: 563715718
2023-09-08 04:46:43 -07:00
christosts
4afecc9099 Rollback of 51fd06482b
PiperOrigin-RevId: 563714392
2023-09-08 04:39:51 -07:00
tonihei
6cff4a2638 Deprecate ConcatenatingMediaSource
There is no known use case left that needs to be solved by this
class. All other use cases are better solved by alternative
approaches (Player playlist methods or ConcatenatingMediaSource2).

PiperOrigin-RevId: 563713384
2023-09-08 04:36:01 -07:00
samrobinson
866d62dd34 Improve CompositionExportTest assertions by using dump files.
PiperOrigin-RevId: 563708666
2023-09-08 04:09:21 -07:00
Googler
007b7dbbf1 Make sure the mdat box is not extended by more than 1 GB at a time.
PiperOrigin-RevId: 563708468
2023-09-08 04:07:13 -07:00
tonihei
5a1322c9f9 Remove restriction from ConcatenatingMediaSource2
The class currently disallows offsets of periods in their windows
except for the very first window. This is not necessary because
we can use TimeOffsetMediaPeriod to eliminate the offset if needed.
This makes the class more useful for many use cases, in particular
for using it with ClippingMediaSource.

Issue: google/ExoPlayer#11226
PiperOrigin-RevId: 563702120
2023-09-08 03:31:17 -07:00
samrobinson
763dddfbd4 Dump with C.TrackType as key, rather than muxer track index.
Modifying dumping to not required "released" to be called.

Track index is an arbitrary value based on the order of addTrack calls.
Samples are dumped by track (rather than as soon as they are written),
so it's preferable to use a value that provides more context.

By using the track type as a key, dump files will be more deterministic
and will have more similarities when branched.

PiperOrigin-RevId: 563700982
2023-09-08 03:25:13 -07:00
tonihei
0c2aba9ce1 Add MediaPeriodId to CompositeMediaSource.getMediaTimeForChildMediaTime
This callback asks to correct the media time in a composition, but doesn't
provide the MediaPeriodId as the necessary context to do this.

PiperOrigin-RevId: 563699344
2023-09-08 03:17:55 -07:00
tonihei
dd2a373636 Add missing synchronization in ExperimentalBandwidthMeter
Issue: androidx/media#612
PiperOrigin-RevId: 563690229
2023-09-08 02:27:20 -07:00
tonihei
f2b1d0cfa3 Move TimeOffsetMediaPeriod to its own class
This makes it reusable for other MediaSource/Periods in the same
package.

Issue: google/ExoPlayer#11226
PiperOrigin-RevId: 563687935
2023-09-08 02:13:39 -07:00
tianyifeng
2ab5841ac2 Add setPlayerId(PlayerId) and prepareSourceCalled to BaseMediaSource
Also add getLastCreatedSource to FakeMediaSourceFactory which will be helpful in testing.

PiperOrigin-RevId: 563463475
2023-09-07 09:58:42 -07:00
huangdarwin
4c792ac907 Compositor: Add API for specifying input texture ColorInfo.
That said, only SDR is supported for now, so this will always throw if
HDR is input. This will also throw if different ColorInfo values are input
because color SDR mixing (ex. between sRGB and BT709) is not yet supported.

PiperOrigin-RevId: 563457729
2023-09-07 09:38:41 -07:00
ibaker
06f5324665 Deflake MediaSessionServiceTest.addSessions_removedWhenReleased
While investigating a different test failure on a pending change I
noticed that sometimes the "testAddSessions_removedWhenClose" session
was being released before it could be fully connected - and this
results in a failure like:

```
expected not to contain: androidx.media3.session.MediaSession@50a9ef1
but was                : [androidx.media3.session.MediaSession@50a9ef1, androidx.media3.session.MediaSession@3a6bac]
	at androidx.media3.session.MediaSessionServiceTest.addSessions_removedWhenReleased(MediaSessionServiceTest.java:376)
```

It also shows up in the logs like:

```
MediaController future failed (so we couldn't release it)
...
Caused by: java.lang.SecurityException: Session rejected the connection request.
```

Adding some debug logging revealed that the `session.release` call
posted to the test thread was happening before the call to
`MediaSessionStub.connect` on the main thread (this is triggered deep
in prod media3 session logic).

PiperOrigin-RevId: 563431265
2023-09-07 08:00:25 -07:00
ibaker
b958f451a7 Fix raw type warning in MediaBrowserCompatWithMediaLibraryServiceTest
PiperOrigin-RevId: 563410425
2023-09-07 06:22:56 -07:00
huangdarwin
19878b0b8b Effect: Clearly state what callers must do onError.
Instead of invoking "undefined behavior" may occur when a class is used
incorrectly, which is clear but not very helpful to callers, specify what Apps
or users of a class should do when issues occur.

Apply this to Compositor as well, where this otherwise might seem unclear.

PiperOrigin-RevId: 563406219
2023-09-07 06:02:09 -07:00
sheenachhabra
3835aa5344 Build ExportResult in Transformer.java
For pause and resume feature we will need to build `ExportResult`
from multiple internal Exports. Keeping the `ExportResultBuider` in
`Transformer` class will allow using same builder across different
internal exports.

PiperOrigin-RevId: 563392443
2023-09-07 04:48:52 -07:00
tofunmi
535af35511 Add heif extractor
PiperOrigin-RevId: 563340591
2023-09-07 00:31:04 -07:00
ibaker
956f58f963 Rename session to match addSessions_removedWhenReleased test name
PiperOrigin-RevId: 563132193
2023-09-06 09:46:21 -07:00
samrobinson
cff2816da4 Add silence generation parameterized test case.
PiperOrigin-RevId: 563098931
2023-09-06 07:34:32 -07:00
samrobinson
92814b84a8 Add alternate MP4 asset with PCM audio.
Audio is Mono 44.1kHz.

Created using:
`ffmpeg -i <input> -c:v copy -c:a pcm_s16be <output>`

PiperOrigin-RevId: 563079553
2023-09-06 05:58:27 -07:00
tofunmi
88b114a997 Add bmpExtractor to DefaultExtractorsFactory
PiperOrigin-RevId: 563076972
2023-09-06 05:41:43 -07:00
samrobinson
ef45c0fe5d Add parameterized dump tests for single item exports.
PiperOrigin-RevId: 563075771
2023-09-06 05:35:51 -07:00
tofunmi
45e15d48c4 Add WebpExtractor to DefaultExtractorsFactory
PiperOrigin-RevId: 563063506
2023-09-06 04:26:53 -07:00
ibaker
100af0b2de Fix test_session_current to be consistent with other test packages
This change ensures that a different package is used for
`test_session_current/src/main:support_app` and
`test_session_current/src/androidTest:test_app` - previously they used
the same package which was unusual (and possibly led to some confusing
behaviour).

PiperOrigin-RevId: 563051818
2023-09-06 03:23:44 -07:00
rohks
8dcafa0398 Add nullness annotations to MediaCodecVideoRenderer
#fixit

PiperOrigin-RevId: 562926813
2023-09-05 16:36:04 -07:00
bachinger
8c0191d0cb Use media button broadcast receiver above Android 31
This change avoids using a framework API that is deprecated since
API 31 and works around difficulties with this deprecated API on
devices from some manufacturers on API 33/34.

Manually tested with BT headphone connected to:

- Samsung SM-G920F (API 24)
- Pixel (API 28)
- Samsung SM-A515W (API 33)
- Pixel 6 Pro (API 33)

(verified manually with devices and adb output of dumpsys)

Issue: androidx/media#167
PiperOrigin-RevId: 562890206
2023-09-05 14:24:06 -07:00
andrewlewis
b56bdd8da0 Remove unnecessary track group count assertion
When checking the color transfer, there is no reason that the file should have
exactly two tracks, and this assertion means that this method can't be used
as-is for checking video-only files, for example.

PiperOrigin-RevId: 562813111
2023-09-05 10:06:44 -07:00
tofunmi
a1be9d5a60 Add WebpExtractor
Also adds it to the DefaultExtractorsFactory for use throughout exoplayer

PiperOrigin-RevId: 562784760
2023-09-05 08:23:03 -07:00
sheenachhabra
657856dfe5 Fix/Update TODOs in Mp4Muxer tests
PiperOrigin-RevId: 562728777
2023-09-05 04:04:51 -07:00
tianyifeng
2554fe8f70 Recreate AudioTrack when ERROR_DEAD_OBJECT throws as writing PCM data
We have an existing logic for recovering the `AudioTrack` from the [ERROR_DEAD_OBJECT](https://developer.android.com/reference/android/media/AudioTrack#ERROR_DEAD_OBJECT)
throws. However, this only applies to the situation when the
`writtenEncodedFrames > 0`.

However, we have a case when `ERROR_DEAD_OBJECT` throws while writing
PCM data. When the `tunneling` is turned on, the `AudioTrack` is set the
flag `AUDIO_OUTPUT_FLAG_HW_AV_SYNC`, and further because of this flag,
it is forced the flag `AUDIO_OUTPUT_FLAG_DIRECT`. When the platform
invalidates the `AudioTrack`, the `AudioTrack` won't be restored by the
platform due to `AUDIO_OUTPUT_FLAG_DIRECT` flag, and `ERROR_DEAD_OBJECT`
is thrown.

Issue: androidx/media#431
PiperOrigin-RevId: 562582451
2023-09-04 10:41:48 -07:00
tofunmi
9b2668c0ca Add BmpExtractor
Takes single sample extraction logic out of the png extractor and puts it in a helper so it can be used for bmp as well.

PiperOrigin-RevId: 562581815
2023-09-04 10:37:28 -07:00
christosts
5b19e08ea9 Rollback of 51fd06482b
PiperOrigin-RevId: 562550636
2023-09-04 07:13:59 -07:00
christosts
51fd06482b Make Timeline and MediaPeriodId visible to Renderers
This is so CompositionPlayer can customize the Renderers and figure
out when a transition to a MediaItem is made hence it can configure the
effects pipeline with the effects that are specific to the MediaItem.

PiperOrigin-RevId: 562530774
2023-09-04 05:12:13 -07:00
michaelkatz
9d58788d86 Add AudioSink#setOffloadDelayPadding to offload play gapless Opus
Created new method `AudioSink#setOffloadDelayPadding` that will set delay and padding data onto an `AudioTrack` using `AudioTrack#setOffloadDelayPadding`. This feature adds support for offloaded, gapless Opus playback as the content requires the capability to set padding data post-`AudioSink#configure`.

PiperOrigin-RevId: 562518193
2023-09-04 04:02:44 -07:00
huangdarwin
2bdda35731 Overlay: Rename videoFrameAnchor to backgroundFrameAnchor.
Overlays may be overlaid over:
* In VideoFrameProcessor, videos or images (or texture input).
* In Compositor, other videos.

In Compositor, Overlays may consist of video, so it could be confusing
for videoFrameAnchor to contrast with overlayAnchor.

Also, rename overlayAnchor to overlayFrameAnchor, since it's modifying
the anchor in the overlay's frame, so this name seems slightly more precise.

PiperOrigin-RevId: 562004292
2023-09-01 11:28:19 -07:00
christosts
70ad637e52 Conditionally output captured data in CapturingRenderersFactory
This change makes capturing components in CapturingRenderersFactory
to dump data only they have previously captured any. This is so we can
extend the CapturingRenderersFactory with more renderers that do not
capture data in pre-existing tests and we don't have to change the
golden files.

PiperOrigin-RevId: 561973645
2023-09-01 09:26:33 -07:00
tofunmi
502504fd47 Skip runUntilComparisonFrameOrEnded checks for nexus's on API 21
verified with nexus 5 running on api 21

PiperOrigin-RevId: 561957198
2023-09-01 08:10:02 -07:00
tofunmi
e15c05fc3c Flip input buffer in the ImageRenderer
also improves tests to hash bitmap now that we know the bitmaps are decoded in roboelectic tests,
as well as some minor fixes in the DefaultImageDecoder

PiperOrigin-RevId: 561946073
2023-09-01 07:12:57 -07:00
huangdarwin
57bc215210 Compositor: Implement OverlaySettings and custom in/out size support.
Implement VideoCompositor support of:
* Different input and output sizes
* CompositorSettings, to customize output size based on input texture sizes
* OverlaySettings, to place an input frame in an arbitrary position on
  the output frame.

Also, refactor Overlay's matrix logic to make it more reusable between
Compositor and Overlays

PiperOrigin-RevId: 561931854
2023-09-01 05:54:15 -07:00
claincly
6c2713f153 Renames containsKey to contains so it's more readable
PiperOrigin-RevId: 561916837
2023-09-01 04:25:25 -07:00
tonihei
f6be4bc526 Document C.TIME_UNSET on Player.setMediaItem(.., startPositonMs)
This wasn't properly documented yet (unlike the longer setMediaItems
method that already includes this documentation).

Issue: androidx/media#607
PiperOrigin-RevId: 561910073
2023-09-01 03:44:36 -07:00
tofunmi
5944adcc78 Add image e2e test
PiperOrigin-RevId: 561887238
2023-09-01 01:31:45 -07:00
bachinger
3911c9d0c7 Add StreamEventListener for IMA SSAI source
Issue: androidx/media#555
PiperOrigin-RevId: 561711428
2023-08-31 11:29:29 -07:00
sheenachhabra
219b253731 Pass initial timestamp offset to VideoFrameProcessor
For pause and resume feature we will remux the previously processed
video in the first export and then in the second export we will resume
processing remaining video. For the second export we will have to
set initial timestamp offset so that video samples from the second
export are in continuation to the previously muxed samples.

PiperOrigin-RevId: 561689651
2023-08-31 10:17:40 -07:00
Googler
4c3ad641c0 Release StreamManager before calling AdsLoader.destroy()
PiperOrigin-RevId: 561678438
2023-08-31 09:37:27 -07:00
sheenachhabra
56acb3ee21 Move start export code into startInternal() method
For pause and resume we need to perform multiple intermediate exports.
So moved start() logic into a separate so that it can be reused from
different places with different Compositions and MuxerWrapper.

PiperOrigin-RevId: 561675472
2023-08-31 09:26:02 -07:00
ibaker
8af11a980a Remove duplication of various TestUtil methods
In most cases, the places that were trying to avoid a transitive
dependency on `lib-exoplayer` when this duplication was introduced [1]
are already depending on it again, except for `lib-container` where the
dep is added in this change.

In general it seems fine for the tests of module A to depend
(transitively or directly) on module B even where the prod code of
module A **does not** depend on module B.

[1] <unknown commit>

PiperOrigin-RevId: 561660371
2023-08-31 08:23:33 -07:00
samrobinson
6ecd3e9c2d Dump DumpableSamples list in track order.
Switch to SparseArray<List> rather than a Map<Integer, List>.

Track indices now determine sample list dumping, reducing flakiness.

PiperOrigin-RevId: 561658586
2023-08-31 08:15:41 -07:00
rohks
ab64e6f92d Fix remaining test_utils module nullness issues
#fixit

PiperOrigin-RevId: 561636758
2023-08-31 06:32:13 -07:00
Copybara-Service
bbfba27cac Merge pull request #594 from Tolriq:sink_format
PiperOrigin-RevId: 561611655
2023-08-31 04:08:54 -07:00
rohks
206a663dca Add functionality to transmit CMCD data using query parameters
Currently, we only support sending Common Media Client Data (CMCD) data through custom HTTP request headers, added capability to configure and transmit it as HTTP query parameters.

PiperOrigin-RevId: 561591246
2023-08-31 02:11:12 -07:00
ibaker
89f52dcb93 Rollback of 53b882d803
PiperOrigin-RevId: 561587445
2023-08-31 01:52:13 -07:00
rohks
3539b26e19 Add nullness annotations to SsMediaPeriod
#fixit

PiperOrigin-RevId: 561583025
2023-08-31 01:29:27 -07:00
ibaker
147cab89c3 Remove subtitle TODO from CapturingRenderersFactory
We're moving towards parsing subtitles before the `SampleQueue`, and we
already have subtitle playback assertions using `Player.Listener.onCues`
which is the most 'complete' place to assert subtitle output from. We
don't need to hook anything inside `TextRenderer`, so we can remove this
TODO.

PiperOrigin-RevId: 561418660
2023-08-30 12:38:48 -07:00
tonihei
ba4b96d2c1 Prevent forwarding of zero video size to Leanback
Leanback isn't prepared to handle these values and will throw
ArithmeticExceptions.

Issue: androidx/media#617
PiperOrigin-RevId: 561413740
2023-08-30 12:20:51 -07:00
Tolriq
4e93db4d0a Format passed to audioSink.configure is missing information.
AudioSink might require the identifying data and metadata to be able to take decisions.
2023-08-30 18:23:18 +01:00
ibaker
53b882d803 Add subsampleOffsetUs to Format.toLogString
This will help with debugging subtitle sync issues as it will show up in
track selection details emitted to logcat by `EventLogger`.

PiperOrigin-RevId: 561355836
2023-08-30 09:03:42 -07:00
ibaker
64792dfda2 Rollback of 25253698bc
PiperOrigin-RevId: 561352515
2023-08-30 08:53:49 -07:00
sheenachhabra
b37e37aa3c Pass MuxerWrapper to the TransformerInternal
For pause/resume feature, same MuxerWrapper needs to be
used across intermediate exports. So pass the MuxerWrapper
from Transformer.java
More specifically, when resume() is called
1. Create a MuxerWrapper and remux the previous
video samples (Export 1).
2. User the same MuxerWrapper and start processing
remaining video samples (Export 2).

PiperOrigin-RevId: 561325867
2023-08-30 06:45:39 -07:00
michaelkatz
cf3fd1f4dd Added condition to RtspMediaPeriod.isLoading to check RtspState
If a RtspMediaSource is used within a combining source like MergingMediaSource, then it could become stuck in a loop of calling continueLoading when the source has not actually started loading yet.

Issue: androidx/media#577
PiperOrigin-RevId: 561322900
2023-08-30 06:29:53 -07:00
ibaker
b4ee896847 Remove some spurious } from Player javadoc
Also use `@linkplain` in more places: If I was already touching a javadoc
block, I switched to `@linkplain` throughout the whole block.

PiperOrigin-RevId: 561320273
2023-08-30 06:16:37 -07:00
tofunmi
6a5d5aef92 Add limited ImageRenderer
At this stage, the image renderer is designed to be able to render one input stream containing one sample. The renderer supports seeking inside that stream, which is a no-op because the stream comprises for exactly one sample.

PiperOrigin-RevId: 561307859
2023-08-30 05:15:38 -07:00
ibaker
9ee45fc938 Add TrackOutput field in PngExtractor
Also re-jig some `checkNotNull` calls to satisfy the nullness checker
(remove an unneeded one, and add a new one).

Follow-up to discussion in bb214b19f9

PiperOrigin-RevId: 561295724
2023-08-30 04:08:56 -07:00
claincly
b466b06ace Split out VideoGraph and VideoFrameProcessingWrapper
More specifically, this CL

- Defines a VideoGraph interface
  - Adds a factory method, to hide the constructors
  - Separate out an initialize method that does the real work (following that constructor should not do real work)
  - The VideoGraph takes in a list of composition effects. For now, we only use the `Presentation`, if there is one in the list. This means we can take any number of Presentations now, but only the first one will be used.
- Moves the VideoFrameProcessingWrapper to its own file

PiperOrigin-RevId: 561059653
2023-08-29 09:54:43 -07:00
tofunmi
bb214b19f9 Sample metadata in the png extractor
PiperOrigin-RevId: 561049410
2023-08-29 09:17:05 -07:00
tianyifeng
32e367fabf Set groupKey for media notification in DefaultMediaNotificationProvider
By doing so, the media notification sent from DefaultMediaNotificationProvider won't be auto-grouped (https://developer.android.com/develop/ui/views/notifications/group#automatic-grouping) with the regular notifications sent from the other places in the app. As the result, when the customer attempts to dismiss the regular notifications (by swiping away), the media notification won't be dismissed as being in the same group.

Issue: androidx/media#549
PiperOrigin-RevId: 561047571
2023-08-29 09:10:12 -07:00
tianyifeng
5a6b88d751 De-flake MediaSessionCompatCallbackWithMediaControllerTest.onStop test
The `controller.prepare()` call can trigger the callback `onPrepare()`, however, this will count down the latch by one before the callback `onStop()` is triggered.

PiperOrigin-RevId: 560988209
2023-08-29 04:28:16 -07:00
tofunmi
667103f2bd Fix SequenceAssetLoader signalling End Of Video Input twice
PiperOrigin-RevId: 560170216
2023-08-25 12:46:50 -07:00
huangdarwin
99ae44efa4 Overlays: Create OverlayMatrixProvider.
Split this logic out from `OverlayShaderProgram`, to share logic like
this with `VideoCompositor`.

Also, remove the unused `context` parameter from `OverlayShaderProgram`

`VideoCompositor` will reuse `OverlayMatrixProvider`'s storing of the matrices,
though it may generate the matrices differently, since `OverlayShaderProgram`
applies this in the fragment shader, whereas `VideoCompositor` applies this in the
vertex shader.

PiperOrigin-RevId: 560142164
2023-08-25 11:05:03 -07:00
huangdarwin
6da70c842e Overlay: Rename alpha to alphaScale.
The actual logic scales the alpha, instead of setting it, so rename
this to what it does.

We would also prefer alpha to be scaled here, to not lose alpha information
(for example for PNGs with transparent regions).

PiperOrigin-RevId: 560121708
2023-08-25 10:00:50 -07:00
sheenachhabra
1f013afea8 Add Mp4ExtractorWrapper into Transformer module
For pause and resume feature we need to find the timestamp of
the last sync sample in an MP4 file. The Mp4ExtractorWrapper
provides an easy to use API on top of Mp4Extractor.

PiperOrigin-RevId: 560113112
2023-08-25 09:29:28 -07:00
tianyifeng
86f919e7d4 Fix flaky tests in PlaylistPlaybackTest
If the loading thread of the second media item progresses slow, then when the playback of the first item approaches to the end before the second item is prepared, the stream will be set "final" and the renderers are disabled during such transition. In this case, `AudioSink.handleDiscontinuity` never gets called, which introduces the flakiness into the `test_bypassOffThenOn`.

Similarly for `test_subtitle`, if the loading thread of extracting the subtitle is slow, then when the renderer attempts to queue the input buffer, the data hasn't been available in the stream. And when the extracting finished, the renderer already advanced to the time after the subtitle end time.

To de-flake the tests, we have to make sure that the period of the second item has fully loaded before starting the playback.

PiperOrigin-RevId: 560080119
2023-08-25 07:04:26 -07:00
huangdarwin
dccbc7e459 ExoPlayer: Remove tone-mapping workaround.
PiperOrigin-RevId: 560069496
2023-08-25 06:07:44 -07:00
huangdarwin
9810d6ae92 Overlay: Improve alpha documentation and extract reused variables
PiperOrigin-RevId: 560064663
2023-08-25 05:43:02 -07:00
huangdarwin
01689ba2ec Compositor: Queue bitmaps by timestamp.
This allows us to manage timestamps in one list, instead of both via
offsets/framerates, and a list.

PiperOrigin-RevId: 560053888
2023-08-25 04:44:48 -07:00
tonihei
7899241daf Fix period indexing for multi-period DASH DAI live streams
The period index was calculated relative to the contentTimeline
of the DAI stream, but then used with the full timeline of the
player. This means it currently only works when the stream is the
only or first item in the playlist.

Issue: androidx/media#571
PiperOrigin-RevId: 560023412
2023-08-25 02:05:46 -07:00
claincly
feae0245b9 Remove the textureReleaseCallback from textureOutputListerner
PiperOrigin-RevId: 559817280
2023-08-24 11:33:11 -07:00
sheenachhabra
d5f8487fe2 Add pause and resume button in demo app
Currently the resume button will restart the export from
the beginning.

PiperOrigin-RevId: 559787856
2023-08-24 10:05:51 -07:00
claincly
28fd43617e Factor out VideoFrameProcessor logic
PiperOrigin-RevId: 559780905
2023-08-24 09:42:21 -07:00
huangdarwin
cd0b7d9e29 Transformer: Document not supporting setTextureOutput on VFP Factory.
PiperOrigin-RevId: 559760003
2023-08-24 08:25:33 -07:00
claincly
8c1bedb483 Remove unnecessary types in lambda
PiperOrigin-RevId: 559745329
2023-08-24 07:21:52 -07:00
sheenachhabra
a6f9fefb88 Add setSequences method to Composition.Builder
For pause and resume feature, we need to buildUpon the
original composition and then set the modified sequences.

PiperOrigin-RevId: 559723694
2023-08-24 05:35:06 -07:00
ibaker
2eafa570e9 Update README with instructions for Gradle Kotlin DSL
Put the Kotlin option first, with Groovy as a a second alternative.

Issue: google/ExoPlayer#11275

#minor-release

PiperOrigin-RevId: 559714938
2023-08-24 04:47:37 -07:00
claincly
930e538aca Allow re-configuring DVFP in a (mostly) non-blocking manner
The first call to method `registerInputStream` doesn't block.

Later successive calls to the method blocks until the previous register call
finishes.

PiperOrigin-RevId: 559694490
2023-08-24 02:55:54 -07:00
rohks
80495ddf9c Add nullness annotations to Representation
#fixit

PiperOrigin-RevId: 559690973
2023-08-24 02:38:11 -07:00
sheenachhabra
5276f797e5 Add buildUpon() and setMediaItem() method in EditedMediaItem
For pause/resume feature we need to build upon original EditedMediaItem
and set a modified MediaItem to it.

PiperOrigin-RevId: 559484129
2023-08-24 09:32:09 +01:00
rohks
e2ee8ae1b0 Add nullness annotations to DefaultDashChunkSource
#fixit

PiperOrigin-RevId: 559405572
2023-08-24 09:28:36 +01:00
rohks
2ad37d2e37 Add nullness annotations to MediaPeriodQueue
#fixit

PiperOrigin-RevId: 559395027
2023-08-24 09:27:43 +01:00
tofunmi
404a259295 Remove queueInputBitmap by framerate and duration interfaces
PiperOrigin-RevId: 559384011
2023-08-24 09:25:49 +01:00
samrobinson
64c2406c1e Use TestUtil value for frame count.
PiperOrigin-RevId: 559380901
2023-08-24 09:21:32 +01:00
tonihei
25cd13b3a2 Remove unused values
PiperOrigin-RevId: 559357691
2023-08-24 09:20:33 +01:00
rohks
bfa32b3998 Add nullness annotations to MediaCodeAudioRenderer
#fixit

PiperOrigin-RevId: 559175846
2023-08-24 09:19:34 +01:00
samrobinson
ff39726368 Remove redundant "aac" tag for dump file.
PiperOrigin-RevId: 559147235
2023-08-24 09:17:32 +01:00
ibaker
9533f5cd1c RtspMediaPeriod: Use a new ExtractorOutput for each SampleQueue
This removes concurrent access from `rtspLoaderWrappers`. Previously
there was a race between the playback thread clearing & re-adding
entries to this list in `retryWithRtpTcp()`, and the loading thread
accessing the entries in `InternalListener.track()` (implemented from
`ExtractorOutput`).

This change means each `ExtractorOutputImpl` uses exactly one
`SampleQueue` for its one `TrackOutput`. When the `RtspLoaderWrapper`
instances are replaced in `retryWithRtpTcp()`, any stale instances will
only be able to access their own (also stale) `SampleQueue` instances
(vs before, where the stale `ExtractorOutput` could accidentally access
'new' `SampleQueue` instances via the `rtspLoaderWrappers` field).

As well as fixing a race condition in the prod code, this also de-flakes
`RtspPlaybackTest`.

#minor-release

PiperOrigin-RevId: 559130479
2023-08-24 09:16:36 +01:00
christosts
398809e4e2 Replace Queue<Long> with a queue for long primitives
Replace Queue<Long> with LongArrayQueue which provides queue semantics
for long primitives. LongArrayQueue is forked from IntArrayQueue which
in turn was forked from Androidx CircularIntArray.

IntArrayQueue is deleted and we now use CircularIntArray directly from
Androidx Collection.

PiperOrigin-RevId: 559129744
2023-08-24 09:14:44 +01:00
tonihei
36084eef05 Split test_session_current instrumentation tests by file
PiperOrigin-RevId: 559089467
2023-08-22 15:50:29 +01:00
tonihei
a00bef9e51 Fix MediaControllerSurfaceSizeChangeTest
There are multiple problems in the test:
 1. The controller must run on the main thread due to the Player
    interface requirement to add surfaces on the thread their
    callbacks will be called on.
 2. This test made assertions about an expected callback that
    aren't true. Setting an anonymous surface will not result in
    a size change callback because the size stays unknown.
    But clearing a surface (even if never set) ensures the returned
    size is guaranteed to be zero.

PiperOrigin-RevId: 559080905
2023-08-22 15:49:08 +01:00
samrobinson
2309fc5edb Add AudioGraph test verifying silence outputs correct amount of bytes.
PiperOrigin-RevId: 559072505
2023-08-22 15:47:54 +01:00
samrobinson
b7782b5119 Inline ProgressHolder and ArgumentCaptor test class variables.
PiperOrigin-RevId: 559069221
2023-08-22 15:46:13 +01:00
rohks
0541e1953c Add nullness annotations to SampleQueue
#fixit

PiperOrigin-RevId: 559058211
2023-08-22 15:44:50 +01:00
ibaker
e9978a94af Move release note from 1.2.0-alpha01 to 'unreleased changes'
PiperOrigin-RevId: 559023779
2023-08-22 15:43:20 +01:00
samrobinson
7346029f72 Use TemporaryFolder @Rule for automated tear down of temp files.
Reduce @Before specific logic, following java dev guide.

PiperOrigin-RevId: 558825609
2023-08-22 15:42:07 +01:00
ibaker
3ced1cbaa2 Update annotation-experimental version
This picks up a fix to ensure Android Studio puts the `@OptIn`
annotation in the correct place:
https://issuetracker.google.com/251172715

This also introduces a transitive dependency from `media3-common` on
the Kotlin standard library, so this CL also includes some updates to
the dev guide to document how apps can avoid including this dep if
they want.

PiperOrigin-RevId: 558821673
2023-08-22 15:40:46 +01:00
samrobinson
ae7667783c Split dump file directories based on input file name.
Remove old unused dump files.

PiperOrigin-RevId: 558820926
2023-08-22 15:39:28 +01:00
huangdarwin
350b394596 Compositor: Add tests for 1, 3, and 5 inputs.
With this, Compositor now handles an arbitrary number of inputs!

PiperOrigin-RevId: 558813361
2023-08-22 15:38:05 +01:00
tonihei
fddb09be20 Internal change
PiperOrigin-RevId: 558799565
2023-08-22 15:36:56 +01:00
tianyifeng
15f4ff7487 Remove asserts inside callbacks
PiperOrigin-RevId: 558791481
2023-08-22 15:35:33 +01:00
ibaker
849238a52f Stop explicitly creating a sourcesElement Gradle variant
This variant has been superceded by an equivalent
`releaseVariantReleaseRuntimePublication` variant which (I think) has
been created since d5f9cf4f19.

Before this change the `sourcesElement` variant was being created with
no `files` config, which resulted in build failures when generating
javadoc in AndroidX:

```
However we cannot choose between the following variants of androidx.media3:media3-cast:1.2.0-alpha01:
  - releaseVariantReleaseSourcePublication
  - sourcesElement
```

We can resolve this confusion by deleting the empty & unneeded
`sourcesElement` variant.

#minor-release

PiperOrigin-RevId: 558783471
2023-08-22 15:34:20 +01:00
rohks
91764baa90 Add nullness annotations to SimpleCache
#fixit

PiperOrigin-RevId: 558783228
2023-08-22 15:33:08 +01:00
christosts
4fad529433 Rollback of f5a6ecdda1
PiperOrigin-RevId: 558779068
2023-08-22 15:31:43 +01:00
huangdarwin
59744fe788 Effect: Minimize calls to configure in default impl.
In case BaseShaderProgram implementations have an expensive
configure() call, we can only call configure() when absolutely necessary,
aka when the input size changes.

To reduce scope, this doesn't reduce the amount of
configure() calls that may be made outside this class, in
DefaultFrameDroppingShaderProgram and
FinalShaderProgramWrapper.

PiperOrigin-RevId: 558754314
2023-08-22 15:30:23 +01:00
huangdarwin
153740386a Compositor: Use lists for inputs instead of instances.
This makes the code a bit more flexible for when we allow for an arbitrary
number of inputs.

PiperOrigin-RevId: 558740536
2023-08-22 15:29:04 +01:00
tofunmi
521c210fd1 Create Timestamp iterator
PiperOrigin-RevId: 558738035
2023-08-22 15:27:42 +01:00
samrobinson
352916b182 Add parameterized tests for generating silence.
Covers all permutations&combinations of:
* AV asset.
* AV asset with effects.
* AV asset with silence.
* AV asset with silence and effects.

Note that the video is not relevant (therefore transmuxed), but is
needed for silence generation.

PiperOrigin-RevId: 558734593
2023-08-22 15:26:19 +01:00
rohks
e0d3cad8bb Add fields next object request (nor) and next range request (nrr)
Added this CMCD-Request fields to Common Media Client Data (CMCD) logging.

PiperOrigin-RevId: 558317146
2023-08-22 15:25:03 +01:00
rohks
b6b16b2895 Sort Common Media Client Data keys to reduce fingerprinting surface
Based on the Common Media Client Data (CMCD) specification key-value pairs should be sequenced in alphabetical order of the key name in order to reduce the fingerprinting surface exposed by the player.

PiperOrigin-RevId: 558296264
2023-08-22 15:23:33 +01:00
rohks
afb8d6c9e2 Make custom data adhere to Common Media Client Data(CMCD) specification
Added more comprehensive Javadoc around setting custom data and verification on key format.

Changed adding custom data as a `String` to `List<String>`. This would enable us to sort all keys to reduce the fingerprinting surface.

PiperOrigin-RevId: 558291240
2023-08-22 15:22:08 +01:00
samturci
6566387f70 Add a waveform audio buffer sink.
This can be used together with TeeAudioProcessor to draw an audio waveform.

PiperOrigin-RevId: 558213516
2023-08-22 15:20:47 +01:00
samrobinson
54797d4cc5 Use @Rule and other util to simplify ParameterizedAudioExportTest.
PiperOrigin-RevId: 558168355
2023-08-22 15:19:15 +01:00
samrobinson
99ac6feeee Add varargs convenience constructors to Sequence & Composition.Builder
Improves API ease-of-use & readability and reduces verbose boilerplate.

PiperOrigin-RevId: 558163557
2023-08-22 15:17:55 +01:00
tianyifeng
7f1ee0b390 Use TrackGroup.equals when determining equality of BaseTrackSelection
PiperOrigin-RevId: 558150684
2023-08-22 15:16:38 +01:00
jbibik
271bf7a56e Clean up of RELEASENOTES
#minor-release

PiperOrigin-RevId: 558135984
2023-08-18 15:35:06 +01:00
samrobinson
2db6f0aee7 Ensure audio components check incoming data is valid.
Default PCM encoding is only set for decoders outputting raw.

Tests migrated to abide by tighter restrictions.

PiperOrigin-RevId: 558129452
2023-08-18 15:33:44 +01:00
sheenachhabra
15650c6bf3 Add buildUpon method in Composition
We will need to build upon original composition
for pause and resume feature and will have to set modified sequences.
In the next CL, will add method to set sequences on builder and will
probably remove it from the constructor parameter (to avoid providing
two APIs for same thing).

PiperOrigin-RevId: 558127334
2023-08-18 15:32:28 +01:00
huangdarwin
030d8148ba Test: Add debug info to debug test failure
I wasn't able to reproduce the error in the bug by running videoTranscoding_withTextureInput_completesWithCorrectFrameCountAndDuration
100 times, but I figured this added debug info may help the next time the
issue is seen.

PiperOrigin-RevId: 558118443
2023-08-18 15:31:00 +01:00
ibaker
107e41b387 Switch from Metalava v3 output to v2
This means we no longer need `--output-kotlin-nulls=no`, because that's
already the default behaviour at `v2`. This allows Metalava to remove
the `--output-kotlin-nulls` flag.

PiperOrigin-RevId: 558112319
2023-08-18 15:29:47 +01:00
huangdarwin
39bc92ffcf Compositor: Use multi-stage rendering and occlude background.
PiperOrigin-RevId: 558110739
2023-08-18 15:28:23 +01:00
claincly
a5903f5d3e Init the collection types to the expected size
PiperOrigin-RevId: 558102287
2023-08-18 15:27:02 +01:00
bachinger
2386b7e944 Some JavaDoc fixes in ImaServerSideAdInsertionMediaSource
Issue: androidx/media#555
PiperOrigin-RevId: 558097690
2023-08-18 15:25:41 +01:00
jbibik
13a809b5b9 Add androidx.exifinterface:exifinterface to AAR list
PiperOrigin-RevId: 558090096
2023-08-18 15:24:32 +01:00
bachinger
725e1abc76 Move release notes entry to correct section
PiperOrigin-RevId: 558087503
2023-08-18 15:23:04 +01:00
claincly
c6804e40a3 Display more accurate time in demo app
PiperOrigin-RevId: 558077709
2023-08-18 15:21:53 +01:00
huangdarwin
02b347ac66 Test: Reduce tokyo.jpg test file size.
This file decompresses to 3024*4032*4 bytes ~= 48
MB, which leads to OOM errors on some devices.

Use a lower resolution test image for tests, to
still test a portrait image but without hitting
OOM errors.

PiperOrigin-RevId: 557861063
2023-08-18 15:20:34 +01:00
ibaker
450d1cd3e9 Add MediaParserExtractorAdapter.enableConstantBitrateSeeking
PiperOrigin-RevId: 557859297
2023-08-18 15:19:20 +01:00
huangdarwin
86678b99ce Decoder: Add SM-F721 to HLG blocklist.
Not only restricted to SM-F721B, per other [Models](https://www.gsmarena.com/samsung_galaxy_z_flip4-11538.php#:~:text=SM%2DF721B%2C%20SM%2DF721B/DS%2C%20SM%2DF721N%2C%20SM%2DF721U%2C%20SM%2DF721U1%2C%20SM%2DF721W).

PiperOrigin-RevId: 557857282
2023-08-18 15:17:48 +01:00
tofunmi
dd0f88490c Add ability to queue bitmap by timestamp to the sampleConsumer
PiperOrigin-RevId: 557837922
2023-08-18 15:16:24 +01:00
tofunmi
a8944ef2f0 Add BitmapDecoder interface
PiperOrigin-RevId: 557827954
2023-08-18 15:15:14 +01:00
huangdarwin
b814404c56 Effect: Update rgba matrix reference to rgb.
The 4x4 matrix only updates the RGB channels, so it should be referred to as an rgb matrix, not an rgba matrix.

PiperOrigin-RevId: 557804613
2023-08-18 15:13:44 +01:00
claincly
3ae927525b Add error listener to InputSwitcher's sampling shader program
PiperOrigin-RevId: 557797201
2023-08-18 15:12:32 +01:00
huangdarwin
a3de5978e0 Test: Use unpremultiplied alpha for GL output.
In addition to this being how Alpha should be handled, tests do fail under
API 29 without this CL. Unfortunately while these tests do fail under API 29
without this CL, we currently only run this test on API 33 emulators, so we
didn't catch this failure earlier (until compositor tests on mh failed on all
devices under API 29 and succeeded on all at or over 29).

PiperOrigin-RevId: 557781757
2023-08-18 15:11:12 +01:00
bachinger
6bd3e53e8d Set notification foreground service behaviour starting with API 31
When the foreground service type is set to `mediaPlayiback` this shouldn't
be required. However, some reports from users say that setting the
foreground service behavor fixes some problems on some devices. Setting
it explicitely with this change makes sure users don't have to do that
workaround themselves.

Issue: androidx/media#167
PiperOrigin-RevId: 557608577
2023-08-18 15:09:59 +01:00
samrobinson
74fa0ed6bf Move FakeAssetLoader to inner class of MediaItemExportTest.
MediaItemExportTest is the only class using this FakeAssetLoader, so it
should be moved out of TestUtil.

PiperOrigin-RevId: 557546717
2023-08-16 22:03:14 +01:00
samrobinson
27bc2e6844 Add new effects helper util for unit tests.
PiperOrigin-RevId: 557515564
2023-08-16 22:01:52 +01:00
ibaker
9631923440 Update SsaParser logic to show it never returns duration=UNSET
In an upcoming change I'm going to mark SSA subtitles as 'merge
replacement behavior', which will mean that
`CuesWithTiming.durationUs=C.TIME_UNSET` will not be permitted. This CL
makes it clear that `SsaParser` obeys that invariant.

PiperOrigin-RevId: 557504633
2023-08-16 22:00:38 +01:00
ibaker
d3894e6691 Add a default no-op implementation for SubtitleParser.reset
Most implementations were already no-ops.

PiperOrigin-RevId: 557503628
2023-08-16 21:59:19 +01:00
ibaker
d42c58f152 Fix DvbParser handling of pageComposition = null
This `DvbParser` was updated to implement the new `SubtitleParser`
interface in 2261756d3a.

This method used to return a `List<Cue>`, but now it returns a
`List<CuesWithTiming>`, which is closer to `List<List<Cue>>`. The
previous method returned an empty list, meaning a single 'event' with
no cues. After the change above the method still returns an empty list,
but that now means 'no events'. In order to maintain the old behaviour,
this change updates it to return a single-item list containing an empty
list of cues.

PiperOrigin-RevId: 557502261
2023-08-16 21:57:58 +01:00
tofunmi
a801f8d3f5 Add ImageDecoder.Factory
PiperOrigin-RevId: 557498045
2023-08-16 21:56:47 +01:00
jbibik
2156f94480 Bump media3 version to 1.2.0-alpha01 and update RELEASENOTES
#minor-release

PiperOrigin-RevId: 557487465
2023-08-16 21:55:35 +01:00
tianyifeng
3f366109b7 Fix Media3 1.1.1 release notes
PiperOrigin-RevId: 556735572
(cherry picked from commit dca4f1a9db)
2023-08-14 12:05:48 +00:00
tianyifeng
9c7cf224e5 Bump version numbers to Media3 1.1.1 and ExoPlayer 2.19.1
PiperOrigin-RevId: 555987303
(cherry picked from commit 1e2a5cd06a)
2023-08-14 10:22:43 +00:00
tianyifeng
a842e62991 Update release notes for Media3 1.1.1
PiperOrigin-RevId: 555951054
(cherry picked from commit b24f7678bb)
2023-08-14 10:22:38 +00:00
jbibik
2fb3a45b6c Fix Gradle Lint with @RequiresApi and SDK version
Gradle Lint doesn't recognise `checkState` assertion and TargetApi should only ever be used for suppressing a bug in Android Lint. Hence, we keep @RequiresApi and add an if-statement explicitly. Also, fixes >26 to >=26 for the version check.

PiperOrigin-RevId: 555144577
(cherry picked from commit f7c31bd3ef)
2023-08-09 13:31:48 +00:00
rohks
4af6fcb838 Bump IMA SDK version to 3.30.3
PiperOrigin-RevId: 555130308
(cherry picked from commit 38eabdc9fc)
2023-08-09 12:16:14 +00:00
tonihei
bab04ebf2c Verify source is not released before updating ad playback state
Updates to the ad playback state are posted on the main handler,
so they may arrive after the source has already been released
(=the internal MediaSource is null). This can cause NPEs.

PiperOrigin-RevId: 555102426
(cherry picked from commit 20d2ce7ce8)
2023-08-09 09:51:56 +00:00
jbibik
136f0876d5 Fix PlayerWrapper's creation of VolumeProviderCompat
When hardware buttons are used to control the volume of the remote device, the call propagates to `MediaSessionCompat.setPlaybackToRemote(volumeProviderCompat)`. However, `volumeProviderCompat` was created incorrectly when the new device volume commands were present (COMMAND_SET_DEVICE_VOLUME_WITH_FLAGS and COMMAND_ADJUST_DEVICE_VOLUME_WITH_FLAGS), i.e. with volumeControlType = `VOLUME_CONTROL_FIXED`. This resulted in `VolumeProviderCompat` which doesn't call `onSetVolumeTo` or `onAdjustVolume` and hence doesn't propagate the calls to the `Player`. Instead, it only worked with the deprecated commands which ensured the volumeControlType was `VOLUME_CONTROL_ABSOLUTE`.

This bug was introduced in c71e4bf1ff (1.0 media 3 release) when `PlayerWrapper`'s call to `createVolumeProviderCompat` was mostly rewritten to handle the new commands, but the two if-statements were not amended. Note: this change fixes the bug only for Android 11 and below. For 12 and above, there is a tracking bug for the regression that was introduced: https://issuetracker.google.com/issues/201546605

http://Issue: androidx/media#554

PiperOrigin-RevId: 554966361
(cherry picked from commit dedccc596e)
2023-08-08 22:51:53 +00:00
Tianyi Feng
294fa261b7 Merge pull request #528 from zgzong:patch-2
PiperOrigin-RevId: 554869426
(cherry picked from commit ef54364478)
2023-08-10 12:09:43 +00:00
rohks
57c73d51da Add field object type (ot)
Added this CMCD-Object field to Common Media Client Data (CMCD) logging.

PiperOrigin-RevId: 554843305
(cherry picked from commit 3ec462d1cf)
2023-08-08 16:09:07 +00:00
ibaker
7e58fde18e Use ceiling divide logic in AudioTrackPositionTracker.hasPendingData
This fixes a bug with playing very short audio files, introduced by
fe710871aa

The existing code using floor integer division results in playback never
transitioning to `STATE_ENDED` because at the end of playback for the
short sample clip provided `currentPositionUs=189937`,
`outputSampleRate=16000` and `(189937 * 16000) / 1000000 = 3038.992`,
while `writtenFrames=3039`. This is fixed by using `Util.ceilDivide`
so we return `3039`, which means
`AudioTrackPositionTracker.hasPendingData()` returns `false` (since
`writtenFrames ==
durationUsToFrames(getCurrentPositionUs(/* sourceEnded= */ false))`).

Issue: androidx/media#538
PiperOrigin-RevId: 554481782
(cherry picked from commit 6e91f0d4c5)
2023-08-07 15:17:31 +00:00
kimvde
4b3a4b3395 Check command availability before getting tracks in PlayerView
#minor-release

PiperOrigin-RevId: 554451569
(cherry picked from commit 117b18f54c)
2023-08-07 13:01:49 +00:00
tianyifeng
c0c67dd5e6 Update translations
PiperOrigin-RevId: 554439196
(cherry picked from commit ff3902debb)
2023-08-07 11:54:19 +00:00
rohks
46c757b008 Simplify and accurately compute chunk duration
Refactored `CmcdLog` to `CmcdHeadersFactory` for improved representation of its purpose and updated implementations.

#minor-change

PiperOrigin-RevId: 552831995
2023-08-01 16:48:19 +00:00
rohks
e8a4894a31 Fix wrong documentation and add missing annotations
#minor-release

PiperOrigin-RevId: 552749407
(cherry picked from commit 267d4164a9)
2023-08-01 11:21:33 +01:00
andrewlewis
50db5207cb Fix parsing of H.265 sequence parameter sets
Fix short term reference picture list parsing. Before this change, `deltaPocS0`
was derived by adding one to the value of the syntax element
`delta_poc_s0_minus1`, but (maybe surprising) the specification actually says
that `DeltaPocS0[stRpsIdx][i]` should be assigned the negation
`-(delta_poc_s0_minus1[i] + 1)` on the first iteration, then that value added
to the previous value on previous iterations. See equations (7-67) to (7-70) in
the 2021-08 version of the H.265/HEVC specification.

Also read the number of long term reference pictures once rather than on every
loop iteration (subsection 7.3.2.2.1).

PiperOrigin-RevId: 551852999
(cherry picked from commit ddb0f86604)
2023-07-28 16:00:13 +01:00
bachinger
ab2505d1a9 Only use result.sendError where supported by legacy media library
`MediaLibraryServiceLegacyStub` handles various edge cases by calling
`result.sendError(null)` with the intention to send back an error to
the legacy browser [1].

`MediaBrowserServiceCompat` of the legacy media1 Compat library has an
inner base class `Result` that has a default implementation of
`onErrorSent` that throws an `UnsupportedOperationException` [2].
However, most anonymous inner classes for `Result` created in
`MediaBrowserServiceCompat` do not override `onErrorSent` [3].

Hence Media3 must not call `sendError` in these cases. Instead we call
`sendResult(null)` according to what the default implementation of
the callbacks in `MediaBrowserServiceCompat` do ([4] as an example).

Issue: androidx/media#78
Issue: androidx/media#334

[1] https://github.com/androidx/media/blob/release/libraries/session/src/main/java/androidx/media3/session/MediaLibraryServiceLegacyStub.java#L200
[2] https://cs.android.com/androidx/platform/frameworks/support/+/androidx-main:media/media/src/main/java/androidx/media/MediaBrowserServiceCompat.java;l=872
[3] https://cs.android.com/androidx/platform/frameworks/support/+/androidx-main:media/media/src/main/java/androidx/media/MediaBrowserServiceCompat.java;l=578-604?q=MediaBrowserServiceCompat&ss=androidx
[4] https://cs.android.com/androidx/platform/frameworks/support/+/androidx-main:media/media/src/main/java/androidx/media/MediaBrowserServiceCompat.java;l=1395

PiperOrigin-RevId: 551210137
(cherry picked from commit 17ee5277d5)
2023-07-26 16:14:39 +01:00
tonihei
ac175a9c37 Fix ms to us conversion bug in DecoderVideoRenderer
The current code multiplies the value by 1000 twice,
effectively converting to nanoseconds.

#minor-release

PiperOrigin-RevId: 551129750
(cherry picked from commit f766936140)
2023-07-26 09:43:03 +01:00
ibaker
db336d5c74 Add comment about out-of-order timestamps in AtomParsers.parseStbl
PiperOrigin-RevId: 550596173
(cherry picked from commit 449cf55523)
2023-07-24 18:05:04 +01:00
ibaker
eaf4a2b448 Tighten the demo app's handling of DrmInitData for downloads
This code is Widevine specific. `OfflineLicenseHelper.downloadLicense`
requires the passed `Format` to have a `DrmInitData.SchemeData` with
Widevine UUID and non-null `data` field. The demo app tries to check
this in advance (to avoid an exception later), but its checks are
looser than those made by `OfflineLicenseHelper`. This change tightens
the checks to match.

Issue: androidx/media#512
PiperOrigin-RevId: 549587506
(cherry picked from commit 1ccedf8414)
2023-07-20 12:03:36 +01:00
rohks
7352a1be0a Add field measured throughput (mtp)
Updated `ExoTrackSelection` to provide the most recent bitrate estimate, enabling the inclusion of measured throughput (mtp) as a CMCD-Request field in Common Media Client Data (CMCD) logging.

Additionally, made changes to the `checkArgument` methods in `CmcdLog` to prevent the use of default values in certain cases.

PiperOrigin-RevId: 549369529
(cherry picked from commit cdb174c91a)
2023-07-19 19:10:56 +01:00
rohks
6443614020 Add fields top bitrate(tb) and object duration(d)
Added these CMCD-Object fields to Common Media Client Data (CMCD) logging.

PiperOrigin-RevId: 548950296
(cherry picked from commit 1b2a2fcde0)
2023-07-18 11:24:34 +01:00
tonihei
3931c28697 Fix race condition in clipped sample streams
The streams return end-of-input if they read no samples, but know that
they are fully buffered to at least the clipped end time. This helps to
detect the end of stream even if there are no new buffers after the end
of the clip (e.g. for sparse metadata tracks).

The race condition occurs because the buffered position is evaluated
after reading the sample. So between reading "no sample" and checking
the buffered position, the source may have loaded arbitrary amounts
of data. This may lead to a situation where the source has not read
all samples, reads NOTHING_READ (because the queue is empty) and then
immediately returns end-of-stream (because the buffered position
jumped forward), causing all remaining samples in the stream to be
skipped. This can fixed by moving the buffered position check to
before reading the sample, so that it never exceeds the buffered
position at the time of reading "no sample".

#minor-release

PiperOrigin-RevId: 548646464
(cherry picked from commit c64d9fd6da)
2023-07-17 12:17:17 +01:00
tonihei
d4c66e549a Remove duplicated release note entry
Issue: androidx/media#515

#minor-release

PiperOrigin-RevId: 548111465
(cherry picked from commit 42998d6400)
2023-07-14 14:36:33 +01:00
michaelkatz
09835006f4 Prepend Ogg ID and Comment Header Pages to offloaded Opus stream
Add Ogg ID Header and Comment Header Pages to the Ogg encapsulated Opus for offload playback. This further matches the RFC 7845 spec and provides initialization data to decoders.

PiperOrigin-RevId: 548080222
(cherry picked from commit 847f6f24d3)
2023-07-14 11:41:56 +01:00
rohks
57d0c197cc Add tests for DefaultSsChunkSource
Added tests for Common Media Client Data (CMCD) logging in SmoothStreaming(SS)

PiperOrigin-RevId: 548072725
2023-07-14 11:03:05 +01:00
rohks
88e34017a3 Fix dependencies for UI module
PiperOrigin-RevId: 548063325
(cherry picked from commit 4d40f2e7dd)
2023-07-14 10:12:32 +01:00
rohks
77fb6525b1 Replace Dummy with Placeholder
`Dummy` is a non inclusive language.

PiperOrigin-RevId: 547815680
(cherry picked from commit ca10204b2d)
2023-07-13 16:55:49 +01:00
rohks
272c844abd Add fields streaming format(sf), stream type(st) and version(v)
Added these CMCD-Session fields to Common Media Client Data (CMCD) logging.

PiperOrigin-RevId: 547435498
(cherry picked from commit 0412a36564)
2023-07-12 10:25:50 +01:00
bachinger
7d35f18732 Add custom layout to the state of the MediaController
This change also marks the buttons of the custom layout as
enabled/disabled according to available commands in the controller.
Accordingly, `CommandButton.Builder.setEnabled(boolean)` is deprecated
because the value is overridden by the library.

Issue: androidx/media#38

PiperOrigin-RevId: 547272588
(cherry picked from commit ea21d27a69)
2023-07-11 20:59:01 +01:00
ibaker
996755c22b Expand @UnstableApi javadoc with how to request stable API additions
Issue: androidx/media#503

#minor-release

PiperOrigin-RevId: 547143885
(cherry picked from commit 2afcf99591)
2023-07-11 11:57:13 +01:00
ibaker
c1261aa266 Remove javadoc @link from non-javadoc comments
Also update type names to match the current names for these types.

PiperOrigin-RevId: 546884049
(cherry picked from commit eed0e42ff8)
2023-07-10 16:46:18 +01:00
ibaker
bae387651b Clarify that new ConditionVariable instances are closed
#minor-release

PiperOrigin-RevId: 546803592
(cherry picked from commit a8520bdee6)
2023-07-10 10:10:03 +01:00
andrewlewis
405e5a6e3e Fix incorrect class name for MediaPipe demo
Issue: androidx/media#500

#minor-release

PiperOrigin-RevId: 545942450
(cherry picked from commit bdbf3e29a1)
2023-07-06 12:07:21 +01:00
tonihei
9de5684d6e Change multidex dependency type to androidTestImplementation
This is only needed for instrumentation tests and should not
be included in regular builds.

Issue: androidx/media#499
PiperOrigin-RevId: 545913113
(cherry picked from commit 2250ffe6c8)
2023-07-06 09:45:11 +01:00
rohks
0c6cfea048 Replace BitArray.skipBytes() with BitArray.skipBits()
Based on the spec, ETSI TS 102 366 V1.4.1 Annex F, 6 bits should have skipped instead of 6 bytes.

This correction was pointed out in Issue: androidx/media#474.

PiperOrigin-RevId: 545658365
(cherry picked from commit 07d4e5986b)
2023-07-05 15:04:50 +01:00
ibaker
bcde7e03c2 Include timing info in some SCTE-35 toString implementations
This was helpful in investigating Issue: androidx/media#471

PiperOrigin-RevId: 545393217
(cherry picked from commit 3456382ae7)
2023-07-04 10:09:27 +00:00
michaelkatz
cb7b3862c4 Add nanoTime method to Clock to support overriding System.nanoTime()
PiperOrigin-RevId: 545237925
(cherry picked from commit de4575da28)
2023-07-03 16:29:13 +00:00
tonihei
26ee4c35f3 Replace exoplayer.dev@gmail.com with android-media-github@google.com
#minor-release

PiperOrigin-RevId: 545165879
(cherry picked from commit 5e19a33095)
2023-07-03 09:34:55 +00:00
ibaker
aa34db41f7 CEA-608: Only truncate to 32 visible characters
We introduced truncation to 32 chars in <unknown commit>
and included indent and offset in the calculation. I think this is
technically correct, but it causes problems with the content in
Issue: google/ExoPlayer#11019 and it doesn't seem a problem to only truncate actual
cue text (i.e. ignore offset and indent).

PiperOrigin-RevId: 544677965
(cherry picked from commit e8fdd83558)
2023-06-30 16:35:46 +00:00
tonihei
aefba8a565 Remove dead code in ProgressiveMediaSource.Builder
These fields cannot be set and the logic to handle them can be removed.

PiperOrigin-RevId: 544646460
(cherry picked from commit 2f113c8b82)
2023-06-30 14:05:39 +00:00
microkatz
3a66617b9e Merge pull request #487 from vishnuchilakala:allow_unsigned_int_for_adaptation_set_id
PiperOrigin-RevId: 544601945
(cherry picked from commit 9513f2c551)
2023-07-05 08:53:09 +00:00
tianyifeng
52706b2eb4 Ensure that ShuffleOrder has the same length as the current playlist
Add a fail-fast check in `ExoPlayerImpl` to ensure the equality of the lengths of `ShuffleOrder` and the current playlist. Also improve the documentation of `setShuffleOrder(ShuffleOrder)` with explicit instruction on this.

Issue: androidx/media#480

#minor-release

PiperOrigin-RevId: 544009359
(cherry picked from commit d895a46b28)
2023-06-28 10:41:49 +00:00
tonihei
f768fedaee Clarify MediaPeriod.readDiscontinuity Javadoc
It currently wrongly documents that it is only called before reading
streams (that has never been the case and all MediaPeriods already need
to handle calls after reading samples from the streams).

It was also a bit unclear what a discontinuity implies and the new
Javadoc calls out the main use case for discontinuties and the intended
meaning of returning a discontinuity.

#minor-release

PiperOrigin-RevId: 543989124
(cherry picked from commit b324b8aa72)
2023-06-28 08:55:56 +00:00
tianyifeng
7683ee254a Use different package names in DiagnosticInfo for media3 and exoplayer
Issue: androidx/media#476

#minor-release

PiperOrigin-RevId: 543460075
(cherry picked from commit 140c83ce7e)
2023-06-26 16:28:47 +00:00
tonihei
ec13c42800 Do not trim audio samples by changing their timestamp
MP4 edit lists sometimes ask to start playback between two samples.
If this happens, we currently change the timestamp of the first
sample to zero to trim it (e.g. to display the first frame for a
slightly shorter period of time). However, we can't do this to audio
samples are they have an inherent duration and trimming them this
way is not possible.

PiperOrigin-RevId: 543420218
(cherry picked from commit 2322462404)
2023-06-26 13:26:35 +00:00
Googler
bf4561c606 Removing @CallSuper from [add,remove]Listener of ForwardingListener.
PiperOrigin-RevId: 543373503
(cherry picked from commit 1fc49ce288)
2023-06-26 09:11:27 +00:00
jbibik
b220dfe73c Cleaner unified PlayerInfo update method in MediaControllerImplBase
`MediaControllerImplBase` has 2 methods for updating listeners about `PlayerInfo` changes - `updatePlayerInfo` (for masking the state) and `onPlayerInfoChanged` (when communicating with the session). There is a set number of listener callbacks related to `PlayerInfo` updates and both methods should go through the same control flow (whether we know that masking will ignore most of them or not).

A unified method `notifyPlayerInfoListenersWithReasons` encapsulates only the shared logic of 2 methods - listeners' callbacks. This ensures that both methods call them in the same order and none are missed out.

PiperOrigin-RevId: 542587879
(cherry picked from commit c2d8051662)
2023-06-22 16:49:36 +00:00
jbibik
e008e21b0f Fix missing equals sign in inline-comment parameter names
PiperOrigin-RevId: 542577676
(cherry picked from commit ea0f564c1e)
2023-06-22 16:09:57 +00:00
jbibik
b4c7e6cb86 Order MediaControllerImplBase listener callbacks as in ExoPlayerImpl
The callbacks for `PlayerInfo` changes are currently in both `MediaControllerImplBase.updatePlayerInfo` (masking) and `MediaControllerImplBase.onPlayerInfoChanged`. But the order was different between them both and `ExoPlayerImpl.updatePlaybackInfo` which they are trying to mimic.

#minor-release

PiperOrigin-RevId: 542519070
(cherry picked from commit b8ac5b4210)
2023-06-22 11:19:48 +00:00
ibaker
4f5d59b58f Switch to SVG assets hosted on developer.android.com for reference docs
#minor-release

PiperOrigin-RevId: 541970884
(cherry picked from commit 34f23451e6)
2023-06-20 17:23:37 +00:00
bachinger
f6a30f6645 Fix ArrayIndexOutOfBoundIndex when re-preparing after exception
When an app tried to re-prepare a live streeam with server side inserted
ad after a playback exception, the player tried to find the ad group by
its index in the ad playback state of the next timeline when creating
the first period.

If a source that supports server side ad, has removed the ad playback
state when the source has been removed, this causes a crash. For live
streams this is a reasonable thing to do given the exception could be
caused by an invalid ad playback state.

This change removes the ad metadata from the current period for live
streams and the timeline. In case the ad playback state is not reset
by the source, the first timeline refresh would ad the metadata again.

PiperOrigin-RevId: 541959628
(cherry picked from commit 4604f0cde6)
2023-06-20 16:55:22 +00:00
jbibik
4710b8f03a Fixed spelling across various PlayerInfo *ChangeReason fields
PiperOrigin-RevId: 541892788
(cherry picked from commit b9cc70d9e2)
2023-06-20 13:06:34 +00:00
tonihei
3561258949 Fix spurious sessions created for events after the playlist is cleared
Some events may arrive after the playlist is cleared (e.g. load
cancellation). In this case, the DefaultPlaybackSessionManager may
create a new session for the already removed item.

We already have checks in place that ignore events with old
windowSequenceNumbers, but these checks only work if the current
session is set (i.e. the playlist is non-empty). The fix is to add
the same check for empty playlists by keeping note of the last
removed window sequence number.

PiperOrigin-RevId: 541870812
(cherry picked from commit e0191ddded)
2023-06-20 12:27:23 +01:00
Marc Baechinger
7e0296fa7c Merge pull request #436 from jaeho-lee104:feature/improve_condition
PiperOrigin-RevId: 540875285
(cherry picked from commit af69d5822a)
2023-06-19 16:25:40 +01:00
rohks
f01ca9d9f1 Refactor method CmcdLog.createInstance to accept bufferedDurationUs
Instead of providing `playbackDurationUs` and `loadPositionUs` individually, which are used to calculate the buffer duration for CMCD logging, we can directly pass the pre-calculated `bufferedDurationUs` available in the `getNextChunk` method of the chunk source classes.

Issue: google/ExoPlayer#8699

#minor-release

PiperOrigin-RevId: 540630112
(cherry picked from commit be9b057dda)
2023-06-15 18:55:30 +01:00
rohks
0aede89586 Add CMCD logging when requesting initialization chunk for DASH and HLS
Additionally, two existing methods to `buildDataSpec` in `DashUtil` have been deprecated, while a new method has been added that allows the inclusion of `httpRequestHeaders`.

Issue: google/ExoPlayer#8699

#minor-release

PiperOrigin-RevId: 540594444
(cherry picked from commit 52878b2aca)
2023-06-15 16:48:55 +01:00
jbibik
2367e7a9e8 Default RepeatMode for conversion is NONE/OFF
Current behaviour causes an app to crash if it receives an unrecognized repeat mode send over the wire. In order to avoid the crash, a sensible default had to be chosen.

For `Player.RepeatMode`, it is `Player.REPEAT_MODE_OFF`, which is the same value we use as default when unbundling `PlayerInfo`.

For `PlaybackStateCompat.RepeatMode`, it is `PlaybackStateCompat.REPEAT_MODE_NONE`, which is what we use in the no-arg `LegacyPlayerInfo` constructor.

Issue: androidx/media#448

#minor-release

PiperOrigin-RevId: 540563792
(cherry picked from commit 501da109ce)
2023-06-15 14:31:59 +01:00
ibaker
3c9831fcb4 Remove = from parameter args in call to Constructor.newInstance
These comments reflect the parameter names of the constructor that
we're reflectively calling, but errorprone complains that they don't
match the parameter names of `Constructor.newInstance`.

PiperOrigin-RevId: 540348118
(cherry picked from commit 567890da9e)
2023-06-14 20:32:01 +01:00
siroberts
648e9943e5 Add missing checkNotNull to bitmapLoader.
#minor-release

PiperOrigin-RevId: 540309118
(cherry picked from commit cf21add916)
2023-06-14 18:22:13 +01:00
bachinger
3cfdd4fdc5 Implement equals/hashCode for CommandButton
#minor-release

PiperOrigin-RevId: 540274932
(cherry picked from commit 3d674fa2f3)
2023-06-14 16:13:48 +01:00
ibaker
983d9d57d7 Stop suppressing exceptions in MediaCodec.Callback during flush
Previously `AsynchronousMediaCodecCallback.mediaCodecException` was
cleared when flushing completed. This behaviour was changed in
aeff51c507
so now the exception is not cleared.

The result after that commit was that we would **only** suppress/ignore
the expression if a flush was currently pending, and we would throw it
both before and after the flush. This doesn't really make sense, so this
commit changes the behaviour to also throw the exception during the
flush.

This commit also corrects the assertion in
`flush_withPendingError_resetsError` and deflakes it so that it
consistently passes. The previous version of this test, although the
assertion was incorrect, would often pass because the
`dequeueInputBuffer` call would happen while the `flush` was still
pending, so the exception was suppressed.

#minor-release

PiperOrigin-RevId: 540237228
(cherry picked from commit 248d1d99ec)
2023-06-14 13:07:39 +01:00
tonihei
a9b78318ca Add missing @Override
PiperOrigin-RevId: 540220141
(cherry picked from commit c76680a65c)
2023-06-14 11:26:38 +01:00
jbibik
9dec0d308b Notify listeners of error changes when masking in MediaControllerImplBase
Currently, the implementation of `MediaControllerImplBase` differs from `ExoPlayerImpl`. The listeners of the former are notified of player error changes only in `onPlayerInfoChanged` and not `updatePlayerInfo` (masking method). Whereas `ExoPlayerImpl` has one unified method - `updatePlaybackInfo` - which sends the events to all the available listeners.

This change fixes the lack of 2 particular callbacks - `onPlayerErrorChanged` and `onPlayerError`, however, there might be more differences. Ideally, there should be a unified method for oldPlayerInfo/newPlayerInfo comparison-update-notify-listeners flow.

Issue: androidx/media#449

#minor-release

PiperOrigin-RevId: 539961618
(cherry picked from commit 4b5a457790)
2023-06-13 15:46:46 +01:00
ibaker
6615399861 Release ExoPlayer instances in ExoPlayerTest
This was recommended in https://github.com/robolectric/robolectric/issues/8187#issuecomment-1552060094

PiperOrigin-RevId: 539691757
(cherry picked from commit 959e974138)
2023-06-12 18:19:56 +01:00
bachinger
c3a96b2e08 Clean up HLS sample for cast demo
Issue: androidx/media#452
#minor-release
PiperOrigin-RevId: 539613535
(cherry picked from commit c2f78db87e)
2023-06-12 11:40:30 +00:00
claincly
0cf3ab31bf Factor out video decoding and fix two minor issues
1. Not treating 0 as valid buffer index
2. Not handling the case the last frame is a comparison frame

PiperOrigin-RevId: 539607482
(cherry picked from commit 4b1ac2f172)
2023-06-12 11:05:08 +00:00
ibaker
8ff61a1430 Stop setting -no-module-directories in ExoPlayer javadoc generation
This flag was introduced to fix links in javadoc search when generating
it with Java 11: <unknown commit>

The flag is no longer supported with Java 17 (which is required for
Gradle 8.0+), and seems to no longer be needed: I generated the javadoc
with it removed and the search links work OK.

PiperOrigin-RevId: 536738686
2023-08-11 15:52:04 +00:00
Tofunmi Adigun-Hameed
5328d6464a
Merge pull request #498 from androidx/release-1.1.0
Release 1.1.0
2023-07-05 08:56:12 +00:00
ibaker
00005cb09d Replace exoplayer.dev@gmail.com with android-media-github@google.com
#minor-release

PiperOrigin-RevId: 544596686
(cherry picked from commit f2c0eab468)
2023-06-30 10:57:51 +01:00
tofunmi
1d73c68465 Fix version bump for media3:1.1.0
#minor-release

PiperOrigin-RevId: 543376501
(cherry picked from commit 10cf06386d)
2023-06-26 10:04:55 +00:00
tofunmi
5fdeabbed8 Version bump for exoplayer 2.19.0 continued
#minor-release

PiperOrigin-RevId: 543369900
(cherry picked from commit 81dfe9d4b4)
2023-06-26 10:04:55 +00:00
tofunmi
ece76c4b61 Version bump to media3-1.1.0 and exoplayer 2.19.0
#minor-release

PiperOrigin-RevId: 542881427
(cherry picked from commit 114364897b)
2023-06-23 18:11:57 +00:00
tofunmi
69c6038e32 Merge release notes for media3 1.1.0 stable release
Merged during cherry-pick

PiperOrigin-RevId: 542539300
(cherry picked from commit 7e475146dd)
2023-06-23 12:20:40 +00:00
ibaker
b1522b4069 Add a section to CONTRIBUTING.md about push access to PR forks
#minor-release

PiperOrigin-RevId: 542294607
(cherry picked from commit 3f7599e9c3)
2023-06-23 12:13:32 +00:00
ibaker
bcdadbfdf5 Fix two more unresolved SVGs in Timeline.Window and Timeline.Period
These were missed in 10342507f7

#minor-release

PiperOrigin-RevId: 541860649
(cherry picked from commit 71f73229dd)
2023-06-23 12:13:31 +00:00
bachinger
1ae8ddd0fd Document how to use a custom receiver app with the cast demo
#minor-release
Issue: androidx/media#452
PiperOrigin-RevId: 539915277
(cherry picked from commit 5afe7552fe)
2023-06-23 12:13:31 +00:00
bachinger
e53796fc25 Fix bug where PlayerView distorts video when video size is unknown
PiperOrigin-RevId: 541640959
(cherry picked from commit 8d8c514d12)
2023-06-19 17:03:25 +01:00
tofunmi
3631e1c6f3 Version bump to media3:1.1.0-rc01
#minor-release

PiperOrigin-RevId: 539632164
(cherry picked from commit 4bceb64dee)
2023-06-12 13:23:56 +00:00
tofunmi
66b59ec3a7 Update RELEASENOTES.md for media3-1.1.0-rc01 release
Removed unreleased changes in this cherry-pick.

PiperOrigin-RevId: 539606230
(cherry picked from commit 49b893f6f3)
2023-06-12 16:15:31 +00:00
Googler
2ee0900659 Rollback of a66f08ba97
*** Original commit ***

Add a timer to end a video stream prematurely in ExtTexMgr

***

This has been submitting for more than 1.5hrs. "This presubmit is running slowly because you have been throttled by Build Queue due to using too much of your Product Area's quota."

adding NO_SQ as this is a pure rollback

PiperOrigin-RevId: 539135970
(cherry picked from commit 5c29abbbf4)
2023-06-12 09:15:55 +00:00
tianyifeng
23e92805a1 Throw exception when TimestampAdjuster initialization hits timeout
Add `HlsMediaSource.Factory.setTimestampAdjusterInitializationTimeoutMs(long)` to set the timeout for the loading thread to wait for the `TimestampAdjuster` to initialize. If the initialization doesn't complete before the timeout, a `PlaybackException` is thrown to avoid the playback endless stalling. The timeout is set to zero by default.

This can avoid HLS playback endlessly stalls when manifest has missing discontinuities. According to the HLS spec, all variants and renditions have discontinuities at the same points in time. If not, the one with discontinuities will have a new `TimestampAdjuster` not shared by the others. When the loading thread of that variant is waiting for the other threads to initialize the timestamp and hits the timeout, the playback will stall.

Issue: androidx/media#323

#minor-release

PiperOrigin-RevId: 539108886
(cherry picked from commit db3e662bdc)
2023-06-12 09:15:54 +00:00
bachinger
21fb8c9942 Fix splitting ad playback state for partial ad group when joining
This change addresses the case when the user joins the live stream
on an ad period but the metadata for the ad period is not emitted.
This results in inserting a partial ad group.

In this case the ad group duration is longer than the partial ad
group. If now the partial ad group ends at the period before the
last period of the window (unknown duration), the splitting algorithm
didn't recognize that the ad group already ended and made the last
period wrongly an ad period.

This change handles this edge case by counting the mapped ads in
the partial ad group to detect this situation and stops splitting.

#minor-release

PiperOrigin-RevId: 539102785
(cherry picked from commit cd604e7ead)
2023-06-12 09:15:54 +00:00
claincly
4dae1a1679 Add missing empty lines
PiperOrigin-RevId: 539100987
(cherry picked from commit edf30433b6)
2023-06-12 09:15:54 +00:00
bachinger
56c62d1ab1 Make current period a placeholder when a live stream is reset
In case the player is reset while a live stream is playing, the current
period needs to be a placeholder. This makes sure that the default start
position is used when the first live timeline arrives after re-preparing.

#minor-release

PiperOrigin-RevId: 539044360
(cherry picked from commit 71153a43a8)
2023-06-12 09:15:54 +00:00
claincly
50f4caacd6 Add a timer to end a video stream prematurely in ExtTexMgr
PiperOrigin-RevId: 539036285
(cherry picked from commit a66f08ba97)
2023-06-12 09:15:54 +00:00
bachinger
1c8c563263 Do not reset period uid when DashMediaSource is released
When the source is prepared again after stop, the period uid
is calculated by subtracting the `firstPeriodId` from the
period uid that is passed in to `createPeriod`. When this
happens after stop, the uid from the old period uid that
is still stored and has the value of the last played uid.

Hence the `firstPeriodId` must not be reset when released.

Issue: google/ExoPlayer#10838
PiperOrigin-RevId: 539028570
(cherry picked from commit 319854d624)
2023-06-12 09:15:54 +00:00
rohks
f1529d63a1 Implement logging support for Common Media Client Data (CMCD)
Add support for including Common Media Client Data (CMCD) in the outgoing requests of adaptive streaming formats DASH, HLS, and SmoothStreaming.

API structure and API methods:
   *   CMCD logging is disabled by default, use `MediaSource.Factory.setCmcdConfigurationFactory(CmcdConfiguration.Factory cmcdConfigurationFactory)` to enable it.
   *   All keys are enabled by default, override `CmcdConfiguration.RequestConfig.isKeyAllowed(String key)` to filter out which keys are logged.
   *  Override `CmcdConfiguration.RequestConfig.getCustomData()` to enable custom key logging.

NOTE: Only the following fields have been implemented: `br`, `bl`, `cid`, `rtp`, and `sid`.

Issue: google/ExoPlayer#8699

#minor-release

PiperOrigin-RevId: 539021056
(cherry picked from commit b55ddf12b4)
2023-06-12 09:15:54 +00:00
bachinger
ec3446fe8b Enable re-preparing the ImaSSAIMediaSource
#minor-release

PiperOrigin-RevId: 538927855
(cherry picked from commit a67ce066df)
2023-06-12 09:15:53 +00:00
jbibik
f18ec2e0c5 Make StreamKey Bundleable and remove deprecated trackIndex
#minor-release

PiperOrigin-RevId: 538809105
(cherry picked from commit 28b8fb706a)
2023-06-12 09:15:53 +00:00
tofunmi
39b98fe5ad Add 'Keep every nth frame' frame dropping strategy.
#minor-release

PiperOrigin-RevId: 538804347
(cherry picked from commit 276f2f1fe6)
2023-06-12 09:15:53 +00:00
tianyifeng
78f23c0c9b Add seekPrev and seekNext buttons on the default compact notification
This change is for Android 12 and below, where the buttons are derived from the actions added with the notification. From Android 13 (https://developer.android.com/about/versions/13/behavior-changes-13#playback-controls), the system derives media controls from `PlaybackState` actions.

When adding the actions onto the notification, the logic will iterate all the command buttons. The `COMMAND_KEY_CONPACT_VIEW_INDEX` extra will be checked for each button. If that extra is set for the three buttons on the compact view, then the customized buttons and their order will be used. Otherwise, the compact view will be "seekPrev" (if any), "play/pause" (if any), "seekNext" (if any) buttons (in such order).

Issue: androidx/media#410
PiperOrigin-RevId: 538797874
(cherry picked from commit 2e2f19351f)
2023-06-12 09:15:53 +00:00
claincly
f1b942150c Fix calling extra registerInputStream and not handling EOS
PiperOrigin-RevId: 538796466
(cherry picked from commit a7cff4e0e3)
2023-06-12 09:15:53 +00:00
sheenachhabra
ebfb9cf402 Add support for passing custom metadata via transformer
Changes included:
1. Enable MP4 extractor to read all types of metadata.
2. Allow passing String and Float metadata via Transformer.

Reference to QuickTime spec: https://developer.apple.com/library/archive/documentation/QuickTime/QTFF/Metadata/Metadata.html#//apple_ref/doc/uid/TP40000939-CH1-SW21

PiperOrigin-RevId: 538783982
(cherry picked from commit 53c174f047)
2023-06-12 09:15:53 +00:00
sheenachhabra
f2c0d7e13c Enable nullness checker for Muxer module androidTest library
PiperOrigin-RevId: 538742957
(cherry picked from commit 2753fb0e3e)
2023-06-12 09:15:53 +00:00
huangdarwin
6dcfe44b89 Test: Add no-op effect test for GL tone mapping.
To ensure no regressions for the potentially confusing pipeline of:
* HDR electrical -> SDR linear EOTF+OOTF, and
* SDR linear -> SDR electrical OETF

PiperOrigin-RevId: 538741079
(cherry picked from commit 0c924fcb40)
2023-06-12 09:15:53 +00:00
tofunmi
5afc256eba DefaultVideoFrameProcessorMultipleTextureOutputPixelTest fixes & cleanup
PiperOrigin-RevId: 538495675
(cherry picked from commit ce203ccfed)
2023-06-12 09:15:52 +00:00
huangdarwin
797ee99baf Test: Move duplicated GL tone mapping logic into helper methods.
PiperOrigin-RevId: 538491957
(cherry picked from commit 9dad207603)
2023-06-12 09:15:52 +00:00
kimvde
71c2d7ba92 Remove unnecessary thread in AssetLoader tests
Also queue textures from a different thread in TextureAssetLoader, to
have a behaviour closer to reality.

PiperOrigin-RevId: 538473089
(cherry picked from commit 3ba8f6dd8f)
2023-06-12 09:15:52 +00:00
jbibik
ade2990503 Fix 1 ErrorProneStyle finding
PiperOrigin-RevId: 538469993
(cherry picked from commit e7f7e86f3e)
2023-06-12 09:15:52 +00:00
tofunmi
f7245a5ff2 Tests for disabled color transfers
#minor-release

PiperOrigin-RevId: 538466615
(cherry picked from commit c3b9328d74)
2023-06-12 09:15:52 +00:00
huangdarwin
295eb06145 Effect: Add multiple texture output test.
Confirms that multiple textures can be output, and that timestamps and pixels
are as expected.

PiperOrigin-RevId: 538459296
(cherry picked from commit adf53b4d50)
2023-06-12 09:15:52 +00:00
andrewlewis
752a49c8d0 Log additional information on test runner timeout
PiperOrigin-RevId: 538437142
(cherry picked from commit 828a05e0fa)
2023-06-12 09:15:52 +00:00
Tofunmi Adigun-Hameed
9b136d3368 Merge pull request #371 from tatsuyafujisaki:simplify-loadJSONFromAsset
PiperOrigin-RevId: 538423581
(cherry picked from commit 9aa519f1ee)
2023-06-12 09:15:52 +00:00
Tofunmi Adigun-Hameed
9db3769fac Merge pull request #439 from kaidokert:pick_workaround
PiperOrigin-RevId: 538209925
(cherry picked from commit 886717e3fe)
2023-06-12 09:15:51 +00:00
sheenachhabra
f1d285ed6f Add support for passing creation time via InAppMuxer
PiperOrigin-RevId: 538175466
(cherry picked from commit 7e14811e25)
2023-06-12 09:15:51 +00:00
Tofunmi Adigun-Hameed
d4e0a8d13d Merge pull request #425 from vishnuchilakala:set_min_live_position
PiperOrigin-RevId: 538173603
(cherry picked from commit 9ca6e5d90d)
2023-06-12 09:15:51 +00:00
tianyifeng
1c1ca3edaf Defer outputting the metadata sample when TimestampAdjuster isn't initialized
The sample timestamp carried by the emsg box can have a significant delta when comparing to the earliest presentation timestamp of the segment. Using this timestamp to intialize the timestamp offset in TimestampAdjuster will cause the media sample to have a wrong adjusted timestamp. So we should defer adjusting the metadata sample timestamp until the TimestampAdjuster is initialized with a real media sample.

PiperOrigin-RevId: 538172841
(cherry picked from commit f4bf376e89)
2023-06-12 09:15:51 +00:00
claincly
70a25b01bf Add utility to create ScheduledExecutorService
PiperOrigin-RevId: 538129792
(cherry picked from commit 08e7158be5)
2023-06-12 09:15:51 +00:00
jbibik
a5949d8806 Allow playback of MediaItems with LocalConfiguration
When initiated by MediaController, it should be possible for `MediaSession` to pass `MediaItems` to the `Player` if they have `LocalConfiguration`. In such case, it is not required to override `MediaSession.Callback.onAddMediaItems`, because the new current default implementation will handle it.

However, in other cases, MediaItem.toBundle() will continue to strip the LocalConfiguration information.

Issue: androidx/media#282

RELEASENOTES.md modified in cherrypick

PiperOrigin-RevId: 537993460
(cherry picked from commit d9764c18ad)
2023-06-12 09:15:01 +00:00
Googler
4a90efaf10 Override ParserException#getMessage
PiperOrigin-RevId: 537908595
(cherry picked from commit 83e9080b71)
2023-06-12 09:13:53 +00:00
ibaker
5792b9299e Add a 'more version details' box to the GitHub bug issue template
#minor-release

PiperOrigin-RevId: 537893360
(cherry picked from commit d328e62f69)
2023-06-12 09:13:53 +00:00
claincly
39ec69fe66 Fix recreation of DefaultShaderProgram in FinalWrapper
`outputSurfaceInfoChanged` is not reset when `defaultShaderProgram` is null.
That is, on the first time `ensureConfigured()` is called with output size
changed, `outputSurfaceInfoChanged` is not set to false after creating the
`defaultShaderProgram`, and `defaultShaderProgram` will be created again on the
second time `ensureConfigured()` is called.

PiperOrigin-RevId: 537870404
(cherry picked from commit 133943a635)
2023-06-12 09:13:53 +00:00
tofunmi
a8dbea74ce Revert AndroidTestUtil.canDecode to use EncoderUtil.findCodecForFormat
208eefc0fd introduced using `DefaultDecoderFactory.getDecoderInfo(format) != null` caused certain tests not to be skipped when they were expected to be, creating more mh failures.

PiperOrigin-RevId: 537820370
(cherry picked from commit 2af5752785)
2023-06-12 09:13:53 +00:00
sheenachhabra
83957eb67f Ignore ByteBuffer position when writing samples in Mp4Muxer
PiperOrigin-RevId: 537814319
(cherry picked from commit 997f2be5e5)
2023-06-12 09:13:53 +00:00
andrewlewis
3ef7bc291c Tidy color info checking tests
ExoPlayer extractors (backing `MetadataRetriever`) now parse the color format
from the bitstream so using `MetadataRetriever` should be an equivalent but
more lightweight way to verify the color info.

Also remove try/catch blocks in test code calling into these methods, and add
skipping based on decoder capabilities in the cases where it was missing.

PiperOrigin-RevId: 537789483
(cherry picked from commit 74478f2478)
2023-06-12 09:13:53 +00:00
huangdarwin
4bb00d5e2e Test: Add special effects for forcing transcode.
Previously, we would apply a general effect to signal wanting to transcode.

PiperOrigin-RevId: 537034455
(cherry picked from commit c52130a212)
2023-06-12 09:13:52 +00:00
Tofunmi Adigun-Hameed
568327ff2e Merge pull request #420 from changxiangzhong:fix/cp-missing
PiperOrigin-RevId: 537014587
(cherry picked from commit a739f6062e)
2023-06-12 09:13:52 +00:00
claincly
1238a5f328 Use the designated UNSET value for aspect ratio
PiperOrigin-RevId: 536770380
(cherry picked from commit f6dbe99c79)
2023-06-12 09:13:52 +00:00
kimvde
55a2e7ff9e Add TransformationRequest toString method
PiperOrigin-RevId: 536727079
(cherry picked from commit 108000834b)
2023-06-12 09:13:52 +00:00
ibaker
89c5e16d2f Soften MediaCodecRenderer's assumptions about using framework DRM
#minor-release

PiperOrigin-RevId: 536724725
(cherry picked from commit 0ddc024c69)
2023-06-12 09:13:52 +00:00
claincly
ba84de02f6 Fix codec's MIME type is not used
In some cases the codec selected for decoding has a different MIME type than
the media. In thoses cases Transformer continued to use the media's MIME type
and that caused codec configuration failures.

Removed `EncoderUtil.findCodecForFormat()` as we stopped using the method it
uses for finding a codec. Plus, the method is only used in the test.

See also `MediaCodecUtil.getALternativeCodecMimeType()`.

PiperOrigin-RevId: 536683663
(cherry picked from commit 208eefc0fd)
2023-06-12 09:13:52 +00:00
huangdarwin
db1b5f148d Exoplayer: Suppress check to allow video to run ahead of Audio.
Otherwise, texture output errors out if video decoding decodes faster than audio,
hitting the end of the file, while audio is still in the middle of the file.

PiperOrigin-RevId: 536679568
(cherry picked from commit e2821f10f5)
2023-06-12 09:13:52 +00:00
huangdarwin
2713f81fd0 Effect: Remove extra wait on taskExecutor release()
This future.get() duplicates the wait done in
singleThreadExecutorService.awaitTermination(). If awaitTermination times out, this future.get() would also result in unnecessary blocking.

PiperOrigin-RevId: 536442153
(cherry picked from commit 1c172e0bed)
2023-06-12 09:13:51 +00:00
sheenachhabra
6e74b1770c Add only supported MdtaMetadataEntry
PiperOrigin-RevId: 536351494
(cherry picked from commit 99d2cf6713)
2023-06-12 09:13:51 +00:00
jbibik
629ab59b5f Remove previously deprecated MediaItem.PlaybackProperties in favour of LocalConfiguration.
Deprecated field `MediaItem.playbackProperties` remains for backwards compatibility, but its type is changed from `MediaItem.PlaybackProperties` to `MediaItem.LocalConfiguration`. The private `MediaItem` constructor will now also take in a `LocalConfiguration` argument instead.

PiperOrigin-RevId: 535648420
(cherry picked from commit 25bf0c6738)
2023-06-12 09:13:51 +00:00
tofunmi
75ad65f14c Image transcoding: Add support for bmp image format.
With this change we will now support loading bitmaps from all the formats documented [here](https://developer.android.com/guide/topics/media/media-formats#image-formats) except for gifs (because they are animated). Java doc is added to express this.

PiperOrigin-RevId: 535610152
(cherry picked from commit 94d29f35fc)
2023-06-12 09:13:51 +00:00
kimvde
2ed784f156 Transmux video if rotation is only effect applied
PiperOrigin-RevId: 535554628
(cherry picked from commit f4d1a6c453)
2023-06-12 09:13:51 +00:00
Tofunmi Adigun-Hameed
b79ee36661 Removing unreleased Audio Offload changes from git 2023-06-07 09:05:51 +00:00
tofunmi
723424a852 Version bump to media3:1.1.0-beta01
#minor-release

PiperOrigin-RevId: 536464412
(cherry picked from commit 49ea280bb8)
2023-05-30 19:42:29 +00:00
Tofunmi Adigun-Hameed
6e0156766b Merge branch 'release' into release-1.1.0-beta01 2023-05-30 16:12:11 +00:00
huangdarwin
4d4f61b772 Rollback of 438ae0ed6a
*** Original commit ***

ExoPlayer: Add setVideoFrameProcessorFactory().

This allows apps to use a custom VideoFrameProcessor implementation for video
playback. This may be useful, for example, when outputting to a texture.
***

PiperOrigin-RevId: 536391597
(cherry picked from commit 06908e1a86)
2023-05-30 14:57:40 +00:00
tofunmi
a442919246 Update release notes for 1.1.0-beta01 release
PiperOrigin-RevId: 536383299
(cherry picked from commit ebbbcf9ac9)
Merged in cherry-pick
2023-05-30 14:57:05 +00:00
Tofunmi Adigun-Hameed
bd29a3553d Merge pull request #335 from cedricxperi:dts-direct-passthrough-support
Resolved Merge Conflict during cherrypicking

PiperOrigin-RevId: 535255453
(cherry picked from commit c3dd88d715)
2023-05-26 13:58:36 +00:00
ibaker
75a9de6c21 Add sections for each minor release to RELEASENOTES.md
#minor-release

PiperOrigin-RevId: 535240816
(cherry picked from commit 41b19df5fa)
2023-05-26 13:34:52 +00:00
Googler
d7e5c1bb0b Show the file path of the exported output video.
PiperOrigin-RevId: 535233266
(cherry picked from commit 86515f8683)
2023-05-26 13:34:52 +00:00
tofunmi
7047f44564 Move OnInputFrameProcessedListener into it's own file
PiperOrigin-RevId: 535183521
(cherry picked from commit a19e07c4d2)
2023-05-26 13:34:52 +00:00
tonihei
f2edc0bed1 Implement Player.replaceMediaItem(s)
This change moves the default logic into the actual Player
implementations, but does not introduce any behavior changes compared
to addMediaItems+removeMediaItems except to make the updates "atomic"
in ExoPlayerImpl, SimpleBasePlayer and MediaController. It also
provides backwards compatbility for cases where Players don't support
the operation.

Issue: google/ExoPlayer#8046

#minor-release

PiperOrigin-RevId: 534945089
(cherry picked from commit 2c07468908)
2023-05-26 13:25:10 +00:00
tonihei
638dee44a9 Merge pull request #386 from yschimke:icon
PiperOrigin-RevId: 534927167
(cherry picked from commit cf0334d793)
2023-05-26 13:25:10 +00:00
michaelkatz
df4803028f Use base Uri from the RTSP DESCRIBE response header for relative paths
Issue: google/ExoPlayer#11160

#minor-release

PiperOrigin-RevId: 534896789
(cherry picked from commit 85f83b1208)
2023-05-26 13:25:10 +00:00
huangdarwin
74a032d462 Effects: Have VFP texture output disable surface output.
Also, document that texture output disables manual frame release.

In the past, texture output would lead to surface output methods throwing. Now,
they're simply no-ops instead.

PiperOrigin-RevId: 534894168
(cherry picked from commit abf649cdfa)
2023-05-26 13:25:10 +00:00
andrewlewis
f59dac9d7d Clarify color transfers for internal textures
PiperOrigin-RevId: 534869452
(cherry picked from commit b988cce62c)
2023-05-26 13:25:10 +00:00
bachinger
5c498c3eca Keep aspect ratio of PlayerView when IDLE
When the video renderer is disabled, the video size is set to 0/0
and sent to listeners. The `PlayerView` potentially still has the last frame
displayed when the player is stopped or an error occurs. This may have the
effect that the frame is displayed distorted.

Not changing the aspect ratio when the video size arrives when the player is IDLE
avoids the problem. In the case when playback starts again and the renderes is
enabled, another video size is sent to the listener.

#minor-release

PiperOrigin-RevId: 534860889
(cherry picked from commit 6469fffd8f)
2023-05-26 13:25:10 +00:00
andrewlewis
a7501f4aaf Tidy TextureManager javadoc
Fix `@param`s and clarify wording.

PiperOrigin-RevId: 534857204
(cherry picked from commit 749c64c74f)
2023-05-26 13:25:10 +00:00
jbibik
171f48fccc Make MediaItem.AdsConfiguration bundleable
PiperOrigin-RevId: 534848363
(cherry picked from commit 3cc4e44fe3)
2023-05-26 13:25:09 +00:00
tonihei
8573a4ba85 Add clarifiying note to Player.replaceMediaItem
This helps to highlight that the replaced range doesn't need to have
the same size as before.

#minor-release

PiperOrigin-RevId: 534834917
(cherry picked from commit acb567d5a7)
2023-05-26 13:25:09 +00:00
sheenachhabra
c38f094b32 Add support for adding capture FPS via transformer
PiperOrigin-RevId: 534814892
(cherry picked from commit a944ffecb9)
2023-05-26 13:25:09 +00:00
sheenachhabra
fb952145fc Add support for adding XMP data via transformer
PiperOrigin-RevId: 534801202
(cherry picked from commit 71facd825e)
2023-05-26 13:25:09 +00:00
ibaker
6b19e5781c Clean up release notes (again)
I undid my last clean-up (b762ca993e) in 5a5c3ce3bd

#minor-release

PiperOrigin-RevId: 534763770
(cherry picked from commit 41492b6e29)
2023-05-26 13:25:09 +00:00
ibaker
c2d6c27d0b Remove deprecated onSeekProcessed
This change removes it from `Player.Listener` and `AnalyticsListener`,
use `onPositionDiscontinuity` with `DISCONTINUITY_REASON_SEEK` instead.

#minor-release

PiperOrigin-RevId: 534757426
(cherry picked from commit 5c713feb60)
2023-05-26 13:25:09 +00:00
huangdarwin
9e19c60907 Codec: Reduce limit for max decoder pending output frames.
Tentative/experimental value to reduce codec timeouts. We will reconsider using a larger limit after seeing whether this really does reduce error rate.

PiperOrigin-RevId: 534491615
(cherry picked from commit 66554b9b68)
2023-05-26 13:25:09 +00:00
claincly
38a341a458 Add logging for ExtTexMgr
- Number of frames from SurfaceTexture that is sent downstream
- Times ExtTexMgr signaled end of current input stream

PiperOrigin-RevId: 534487842
(cherry picked from commit d584a772e3)
2023-05-26 13:25:09 +00:00
sheenachhabra
d3f88a434b Add support for updating Metadata entries via InAppMuxer
Mp4Muxer already supports writing Mp4LocationData so added that
as supported Metadata entry.
Support for more Metadata entries will be added in upcoming CLs.

PiperOrigin-RevId: 534473866
(cherry picked from commit 7c477589e5)
2023-05-26 13:25:09 +00:00
ibaker
4d17a05b2b Ensure rootProject.name is only set from settings.gradle
I moved this assignment in 0888dfbd05
in order to provide a single source-of-truth for `publish.gradle`,
but as pointed out in Issue: androidx/media#416 this breaks apps that are depending
on our project locally using the instructions we publish. Instead we can
remove the `rootProject.name` check from `publish.gradle`, and check an
explicit boolean value instead to indicate if the root project is 'ours'
(with this boolean only set from `settings.gradle`, so it doesn't get
picked up by apps depending on us locally).

#minor-release

PiperOrigin-RevId: 534459085
(cherry picked from commit 9a79571284)
2023-05-26 13:25:09 +00:00
tonihei
88cdbe52d7 Improve MediaSource threading constraints documentation
And fix violation of this in AdsMediaSource.

#minor-release

PiperOrigin-RevId: 534441648
(cherry picked from commit c73955a4cd)
2023-05-26 13:25:09 +00:00
ibaker
6621287c86 Remove four deprecated AnalyticsListener decoder methods
Use the audio or video specific variants instead.

#minor-release

PiperOrigin-RevId: 534436644
(cherry picked from commit 5a5c3ce3bd)
2023-05-26 13:25:09 +00:00
ibaker
48c58cefc2 Remove deprecated OfflineLicenseHelper constructor
Use the non-deprecated constructor instead.

#minor-release

PiperOrigin-RevId: 534426655
(cherry picked from commit 48348df58a)
2023-05-26 13:25:09 +00:00
ibaker
c650a10256 Remove deprecated Cue constructors, use Cue.Builder instead
#minor-release

PiperOrigin-RevId: 534412494
(cherry picked from commit e6f5f58e47)
2023-05-26 13:25:09 +00:00
jbibik
16b09f6d63 Make MediaItem.SubtitleConfiguration bundleable
PiperOrigin-RevId: 534390168
(cherry picked from commit b7edc9e416)
2023-05-26 13:25:09 +00:00
ibaker
22ac971bbc Remove deprecated DownloadManager constructor
Use the constructor that takes an `Executor` instead.

#minor-release

PiperOrigin-RevId: 534370613
(cherry picked from commit ff0f1c4e9c)
2023-05-26 13:25:08 +00:00
bachinger
f8ef386065 Use artwork display mode in demo app
- Use artwork display mode `fill` to improve visual apperance
- Some minor cleanup

#minor-release

PiperOrigin-RevId: 534366246
(cherry picked from commit 230921e4ab)
2023-05-26 13:25:08 +00:00
ibaker
e8bcbd5249 Clean up release notes
This change merges some duplicate sections, moves some items to more
appropriate sections and removes unnecessary items (deprecations are
self-documenting, so don't need to be included here).

#minor-release

PiperOrigin-RevId: 534363065
(cherry picked from commit b762ca993e)
2023-05-26 13:25:08 +00:00
ibaker
ead2c0682a Remove deprecated DefaultLoadControl.Builder.createDefaultLoadControl()
Use `build()` instead.

#minor-release

PiperOrigin-RevId: 534348979
(cherry picked from commit 594e9ac50d)
2023-05-26 13:25:08 +00:00
ibaker
12ca8903ce Remove deprecated ExoPlayer.setHandleWakeLock(boolean)
Use `setWakeMode(int)` instead.

#minor-release

PiperOrigin-RevId: 534344010
(cherry picked from commit cad1ac2eb5)
2023-05-26 13:25:08 +00:00
bachinger
f372440882 Add artwork display mode to PlayerView
This change deprecates `PlayerView.setUseArtwork(boolean)` and
introduces `setArtworkDisplayMode(mode)` and
`artworkDisplayMode="off|fit|fill"` instead.

- off: no artwork is displayed (like deprecated useArtwork=false)
- fit: letterbox like media (like deprecated useArtwork=true)
- fill: scales the artwork to fill the entire width/weight of the player view

#minor-release

PiperOrigin-RevId: 534167226
(cherry picked from commit 46fb454b3f)
2023-05-26 13:25:08 +00:00
bachinger
5f3cb861fc Minor session demo app improvements
Basically this change removes a bug that makes video playback stuck when
a video is playing and the user taps the UMO notification to get to
the player activity.

- Use `launchMode="singleTop"` for `PlayerActivity`
- Change session activity to a back stacked activity on service `onDestroy`.

Using a back stacked activity `onDestroy()` will be useful once this demo
app implements playback resumption.

The rest of the changes are aesthetic:

- clean up and optimize screen space usage in UI of `PlayerActivity`
- changed some colors, paddings and spacings
- adds a default artwork for the `PlayerView`

PiperOrigin-RevId: 534152052
(cherry picked from commit 96a4ae7e40)
2023-05-26 13:25:08 +00:00
christosts
fbd0bae265 Fix seeking bug in opus
Fix a bug when seeking in an opus container. The calculations inside
DefaultOggSeeker may overflow a long primitive.

Issue: androidx/media#391

#minor-release

PiperOrigin-RevId: 534128513
(cherry picked from commit b9a4e614f7)
2023-05-26 13:25:08 +00:00
sheenachhabra
cebdb17134 Write metadata to Mp4Muxer in the release() method
Earlier metadata was written multiple times as it came.
With new changes, all the distinct metadata entries will
get collected and will be written at once in the end.

PiperOrigin-RevId: 534088401
(cherry picked from commit a9e3f5def4)
2023-05-26 13:25:08 +00:00
huangdarwin
9d04b11d49 Effect: Add GlTextureInfo release() and accessor methods.
This allows us to disallow access after release.

PiperOrigin-RevId: 534046475
(cherry picked from commit a6897aedaa)
2023-05-26 13:25:08 +00:00
huangdarwin
3d231cce05 ExoPlayer: Add setVideoFrameProcessorFactory().
This allows apps to use a custom VideoFrameProcessor implementation for video
playback. This may be useful, for example, when outputting to a texture.

PiperOrigin-RevId: 534044831
(cherry picked from commit 438ae0ed6a)
2023-05-26 13:25:08 +00:00
tonihei
5cdbd59756 Improve handling of adding items to empty playlist in MediaController
This is a follow-up to 99dac0be0f where we made the same change in
ExoPlayerImpl and SimpleBasePlayer, but for consistency it makes
sense to also update the masking code in MediaControllerImplBase to
assume the same logic.

Note: MediaControllerImplLegacy already handles this case via
setMediaItems and doesn't need to be updated further.

#minor-release

PiperOrigin-RevId: 534038759
(cherry picked from commit 33af245465)
2023-05-26 13:25:08 +00:00
tonihei
1b007deca0 Untangle PlayerInfo/PlaybackInfo updates
The methods in ExoPlayerImpl and MediaControllerImplBase that determine
the new PlayerInfo/PlaybackInfo currently have a hard-to-reason-about
setup where the method generating the new info accesses other methods
that rely on the existing class field instead of working with the
passed in PlayerInfo/PlaybackInfo. This prevents reuse of the util
methods (e.g. for replaceMediaItems) because they access potentially
stale state.

This change untangles these methods a bit by making the util methods
either static or at least ensure that they don't rely on existing
class fields of PlayerInfo/PlaybackInfo. Overall, the change is a
complete no-op.

#minor-release

PiperOrigin-RevId: 534036633
(cherry picked from commit 1fa790348e)
2023-05-26 13:25:08 +00:00
tonihei
44ffea2477 Keep pending initial position when setting empty playlist
MediaControllerImplBase currently drops the pending initial seek
position when a user sets an empty playlist.

When seeking in empty playlists and setting new empty playlists,
the class also drops the the period index (and wrongly assigns zero
instead of the windowIndex).

#minor-release

PiperOrigin-RevId: 534035046
(cherry picked from commit caf1c77af1)
2023-05-26 13:25:08 +00:00
tonihei
3704c7fc8d Extend main Player Javadoc
The main interface documentation hasn't been updated substantially
since 2017 and is missing notes for many of its current features and
requirements.

Also change the recommendation for implementors from BasePlayer to
SimpleBasePlayer to ensure new classes are more likely to cover all
of the interface requirements.

#minor-release

PiperOrigin-RevId: 534027117
(cherry picked from commit 6de6bd9c4f)
2023-05-26 13:25:08 +00:00
andrewlewis
8df047108c Remove unnecessary volatile
This field is always accessed with the mutex held.

PiperOrigin-RevId: 534027096
(cherry picked from commit ea0b94c0eb)
2023-05-26 13:25:07 +00:00
andrewlewis
8a9503c01a Use Ascii for conversion to lower case
PiperOrigin-RevId: 534016337
(cherry picked from commit b0418f1a2a)
2023-05-26 13:25:07 +00:00
andrewlewis
aa4f84d89a Run clang-format on GLSL
PiperOrigin-RevId: 534015933
(cherry picked from commit 2cbc2c6176)
2023-05-26 13:25:07 +00:00
ibaker
5c42c25ad3 Remove deprecated zero-arg DefaultTrackSelector constructor
Use `DefaultTrackSelector(Context)` instead.

#minor-release

PiperOrigin-RevId: 533985937
(cherry picked from commit 2b409da881)
2023-05-26 13:25:07 +00:00
jbibik
992c9aa470 Make DrmConfiguration Bundleable
PiperOrigin-RevId: 533721679
(cherry picked from commit 5008417c8c)
2023-05-26 13:25:07 +00:00
sheenachhabra
d40f37158a Move MdtaMetadataEntry class into container module
This class is to be shared between extractor, transformer
and muxer module.

PiperOrigin-RevId: 533490888
(cherry picked from commit b382a7c2da)
2023-05-26 13:25:07 +00:00
bachinger
b066a0912e Set video size to 0/0 when video render is disabled
In terms of MCVR with a `VideoRendererEventListener`, the video size is set to
0/0 right after `onVideoDisabled()` is called and is set to the actual size as
soon as the video size is known after 'onVideoEnabled()`.

For ExoPlayer and in terms of the `Player` interface, `Player.getVideoSize()`
returns a video size of 0/0 when `Player.getCurrentTracks()` does not support
`C.TRACK_TYPE_VIDEO`. This is ensured by the masking behavior of
`ExoPlayerImpl` that sets an empty track selection result when the playing
period changes due to a seek or timeline removal.

When transitioning playback from a video media item to the next, or when
seeking within the same video media item, the renderer is not disabled.

#minor-release

PiperOrigin-RevId: 533479600
(cherry picked from commit 2a6f893fba)
2023-05-26 13:25:07 +00:00
bachinger
ef6772b946 Return full media item when SystemUI calls service on device boot time
#minor-release

PiperOrigin-RevId: 533465595
(cherry picked from commit 3fa666c687)
2023-05-25 10:44:07 +00:00
ibaker
41de418c3d Remove deprecated ExoPlayer.retry(), use prepare() instead.
#minor-release

PiperOrigin-RevId: 533463348
(cherry picked from commit 50112c685b)
2023-05-25 10:44:07 +00:00
ibaker
7934eaf882 Add logging where we were swallowing failed futures in media3.session
This may not be completely exhaustive, but it's better than before!

#minor-release

PiperOrigin-RevId: 533457167
(cherry picked from commit fe19dc421d)
2023-05-25 10:44:07 +00:00
ibaker
c26659184c Add empty headings to the 'unreleased changes' section of release notes
PiperOrigin-RevId: 533403520
(cherry picked from commit 0e09c0041f)
2023-05-25 10:44:07 +00:00
claincly
1f8caa508f Add a getter method for texture manager
PiperOrigin-RevId: 533402277
(cherry picked from commit d7ad431cfc)
2023-05-25 10:44:07 +00:00
tonihei
5e98c938c0 Add FilteringMediaSource that only provides tracks of given types
This is useful for cases where only certain types (e.g. only video)
from a source are needed and other tracks should be filtered out
completely to avoid later track selection issues.

#minor-release

PiperOrigin-RevId: 533394658
(cherry picked from commit c44b3828ca)
2023-05-25 10:44:07 +00:00
huangdarwin
3ac01d43dd Effect: Use callback to release texture
This allows us to avoid needing a reference to the VideoFrameProcessor, which
can be especially difficult if an App only has a reference to the
VideoFrameProcessor.Factory it passes into Transformer/ExoPlayer.

PiperOrigin-RevId: 533205983
(cherry picked from commit 25fa2df2de)
2023-05-25 10:44:07 +00:00
ibaker
2b53139c5f Allow mock(Random.class) to work with Java 17
https://stackoverflow.com/questions/70993863/mockito-can-not-mock-random-in-java-17

#minor-release

PiperOrigin-RevId: 533161221
(cherry picked from commit 04106da932)
2023-05-25 10:44:07 +00:00
jbibik
9c1a80082f Use TestUtil.getPublicMethods instead of getDeclaredMethods
JaCoCo introduces private synthetic methods (even on interfaces) which
have to be skipped when checking that a 'forwarding' implementation does
forward everything. Instead we can use the existing `getPublicMethods()`
method which implicitly skips these (since they're private).

PiperOrigin-RevId: 533130932
(cherry picked from commit 620b9e1540)
2023-05-25 10:44:07 +00:00
sheenachhabra
400218c018 Add argument validation in Mp4LocationData
PiperOrigin-RevId: 533121451
(cherry picked from commit 209783bdf2)
2023-05-25 10:44:07 +00:00
claincly
dd425d53c9 Always use sRGB/BT.709 for bitmap inputs
PiperOrigin-RevId: 533117700
(cherry picked from commit 24a4396990)
2023-05-25 10:44:07 +00:00
Tofunmi Adigun-Hameed
cd9ff24086 Remove FfmpegVideoRenderer from 1.1.0 release 2023-05-18 18:04:45 +00:00
tofunmi
431b985a04 HDR texture asset loading
PiperOrigin-RevId: 532846248
(cherry picked from commit 5fe10d7652)
2023-05-18 16:07:52 +00:00
rohks
633c339dc1 Remove deprecated methods Format.copyWithXXX
Use `Format.buildUpon()` and `setXXX` instead.

#minor-release

PiperOrigin-RevId: 532840625
(cherry picked from commit 538524e579)
2023-05-18 16:07:52 +00:00
sheenachhabra
b97ec5edfc Add default constructor for InAppMuxer.Factory
PiperOrigin-RevId: 532838813
(cherry picked from commit 410840c9e1)
2023-05-18 16:07:52 +00:00
rohks
61a5dd76e3 Remove deprecated methods that create an instance of Format
Use `Format.Builder` instead.

#minor-release

PiperOrigin-RevId: 532808478
(cherry picked from commit 18aa664cb8)
2023-05-18 16:07:52 +00:00
huangdarwin
55c9d10022 HDR: Blocklist Galaxy Z Fold 4 for HLG tone mapping.
This device failed on HdrEditingTest's exportAndTranscode_hlg10File_whenHdrEditingUnsupported_toneMapsOrThrows
before this CL, and succeeds on that test after this CL.

PiperOrigin-RevId: 532796897
(cherry picked from commit 83190a0fe9)
2023-05-18 16:07:52 +00:00
sheenachhabra
7adca46e4b Move Mp4LocationData from extractor module to container module
This class will be shared between extractor and muxer module.

PiperOrigin-RevId: 532784415
(cherry picked from commit 7b62b33127)
2023-05-18 16:07:52 +00:00
ibaker
514f032afc Add main/dev-v2 branch options to bug.yml template
#minor-release

PiperOrigin-RevId: 532766676
(cherry picked from commit 84d0206c76)
2023-05-18 16:07:51 +00:00
ibaker
962499c9d8 Add Media3 1.0.2 and ExoPlayer 2.18.7 to bug.yml template
#minor-release

PiperOrigin-RevId: 532765549
(cherry picked from commit 4ede3d6007)
2023-05-18 16:07:51 +00:00
huangdarwin
ce5b57e03c Effect: Make TexturePool and use in FinalWrapper.
Have the FinalShaderProgramWrapper / VideoFrameProcessor texture
output access textures provided through a texture pool, that
recycles used textures.

Also, add the TexturePool interface to generally re-use textures.

PiperOrigin-RevId: 532754377
(cherry picked from commit 94efcd7917)
2023-05-18 16:07:51 +00:00
sheenachhabra
f5ec1bb6f9 Move NAL unit related methods from common to container module
PiperOrigin-RevId: 532750099
(cherry picked from commit e0d6f67dd9)
2023-05-18 16:07:51 +00:00
kimvde
6abc1a7155 Simplify FrameConsumptionManager onReadyToAcceptInputFrame logic
Propagate the "end of current stream" signal directly after queueing the
last frame, instead of waiting for the next onReadyToAcceptInputFrame()
call.

PiperOrigin-RevId: 532739462
(cherry picked from commit 028b3a7312)
2023-05-18 16:07:51 +00:00
tianyifeng
a5031a688b Avoid using @see in the summary fragment in C.java
PiperOrigin-RevId: 532536037
(cherry picked from commit 5d4c73eee5)
2023-05-18 16:07:51 +00:00
rohks
7773c88404 Remove deprecated WorkManagerScheduler constructor
Use a non deprecated constructor that includes the option to provide a `Context` parameter instead.

#minor-release

PiperOrigin-RevId: 532535770
(cherry picked from commit df52864420)
2023-05-18 16:07:51 +00:00
rohks
fa152ddc80 Remove deprecated String constants for Charsets
Use Kotlin Charsets from the `kotlin.text` package, the `java.nio.charset.StandardCharsets` or the `com.google.common.base.Charsets` instead.

#minor-release

PiperOrigin-RevId: 532469103
(cherry picked from commit 1061135cfd)
2023-05-18 16:07:51 +00:00
tofunmi
7fdae1ad0d Adjust image input ForPixelWidthHeightRatio
PiperOrigin-RevId: 532463400
(cherry picked from commit 63ee5ccb28)
2023-05-18 16:07:51 +00:00
rohks
5a72333554 Remove deprecated DownloadService constructor
Use a non deprecated constructor that includes the option to provide a `channelDescriptionResourceId` parameter.

#minor-release

PiperOrigin-RevId: 532450975
(cherry picked from commit 022a05c376)
2023-05-18 16:07:51 +00:00
ibaker
06c8433ce8 Remove deprecated DownloadHelper format-specific methods
Use `forMediaItem` instead.

PiperOrigin-RevId: 532414060
(cherry picked from commit 57479dd397)
2023-05-18 16:07:51 +00:00
bachinger
1510710c46 Enable live DASH stream for IMA DAI
This change enables the IMA extension to play live DASH streams
with DAI support. Samples streams can be found and played in the
main demo app.

Issue: google/ExoPlayer#10912
#minor-release
PiperOrigin-RevId: 532407708
(cherry picked from commit dab1353aad)
2023-05-17 16:59:56 +00:00
ibaker
3633ad15cc Update release notes for Media3 1.0.2
#minor-release

PiperOrigin-RevId: 532404001
(cherry picked from commit 1a38a0c41e)
2023-05-17 16:59:56 +00:00
tofunmi
43f8d080df Update mixed input test to include images of different aspect ratios
Makes this test a little more thorough.

PiperOrigin-RevId: 532386515
(cherry picked from commit 88642587ac)
2023-05-17 16:59:55 +00:00
huangdarwin
04a00c7ac4 Test: Suppress SSIM timeouts on galaxy fold/flip.
This is a failure only in SSIM, so it seems unlikely we'll prioritize this over
other work or bugs soon. Suppress test failures to reduce triage burden.

PiperOrigin-RevId: 532200729
(cherry picked from commit 62afbe87bb)
2023-05-17 16:59:55 +00:00
rohks
fc6429b2d4 Remove two deprecated InvalidResponseCodeException constructors
Use a non-deprecated constructor that accepts additional fields(`cause`, `responseBody`) to enhance error logging.

#minor-release

PiperOrigin-RevId: 532190896
(cherry picked from commit b120ef65ed)
2023-05-17 16:59:55 +00:00
tonihei
a8c56f2c60 Add Player.replaceMediaItem(s)
This methods allows to replace single items or a range of items directly
without using separate operations for add and remove. The advantage is
more readable code for apps and the potential for player
implementations to optimize this process (e.g. only replace values
without interrupting playback).

The current change just introduces the API with its default behavior.
The default logic will be removed again in the future in favor of
better logic in the Player implementations.

Issue: google/ExoPlayer#8046
PiperOrigin-RevId: 532151471
(cherry picked from commit b1cfeb04a0)
2023-05-17 16:59:55 +00:00
jbibik
27becc028d Allow ExoPlayer to opt into volume device control, forbidden by default
PiperOrigin-RevId: 532136692
(cherry picked from commit 1c6b894e88)
2023-05-17 16:59:55 +00:00
tonihei
7f1c1185e7 Remove unnecessary warning suppression
PiperOrigin-RevId: 532114601
(cherry picked from commit 79657692e4)
2023-05-17 16:59:55 +00:00
ibaker
7ac9cf0ec7 Remove deprecated DefaultDrmSessionManager constructors
Use `DefaultDrmSessionManager.Builder` instead.

#minor-release

PiperOrigin-RevId: 532102375
(cherry picked from commit 8a5cebb54d)
2023-05-17 16:59:55 +00:00
huangdarwin
a1fbb12ade Effect: Multiple Texture output
Allow the VideoFrameProcessor to output multiple textures at a time, so that
lifetime of textures is up to the consumer calling VFP.releaseOutputFrame.

The FinalShaderProgramWrapper also has a new maxCapacity limit added, to ensure
the a reasonable amount of textures is used and avoid using up memory.

PiperOrigin-RevId: 532094256
(cherry picked from commit 07ec1eaa48)
2023-05-17 16:59:55 +00:00
tonihei
c7004d43af Add consistency check to sending and receiving position updates
The periodic updates are only meant to happen while we are in the
same period or ad. This was already guaranteed except for two cases:
1. The Player in a session has updated its state without yet calling
   its listeners
2. The session scheduled a PlayerInfo update that hasn't been sent yet

... and in both cases, the following happened:
 - The change updated the mediaItemIndex to an index that didn't exist
   in a previous Timeline known to the Controller
 - One of the period position updates happened to be sent at exactly
   this time

This problem can be avoided by only scheduling the update if we are
still in the same period/ad and haven't scheduled a normal PlayerInfo
update already.

Since new MediaControllers may still connect to old sessons with this
bug, we need an equivalent change on the controller side to ignore such
buggy updates.

PiperOrigin-RevId: 532089328
(cherry picked from commit 96dd0ae583)
2023-05-17 16:59:55 +00:00
andrewlewis
5722e6472a Fix lost shader input capacity after end-of-stream
When exporting compositions with multiple images in a row, transformation could
get stuck if a shader was ready to accept input when end-of-stream was already
signaled and queued from upstream. Fix accounting for the downstream capacity.

Manually tested on concatenations with several images and several videos in a
row, by adding logging and verifying the capacity updates as expected across
edited media item transitions.

PiperOrigin-RevId: 532088793
(cherry picked from commit 6850391e45)
2023-05-17 16:59:55 +00:00
ibaker
1ebf5c2a6a Delete deprecated zero-arg DefaultBandwidthMeter constructor
Use `DefaultBandwidthMeter.Builder` instead.

#minor-release

PiperOrigin-RevId: 532069549
(cherry picked from commit 8f29a5eba9)
2023-05-17 16:59:55 +00:00
kimvde
5e926cdce5 Refactor SequenceAssetLoader release
In the past, the SequenceAssetLoader was released in TransformerInternal
when the export ended.

fc539da061 was made to release the SequenceAssetLoader earlier, when
loading ended. This was causing player release timeouts because the last
AssetLoader in the sequence was released before the SamplePipelines (see
0b40bc37ab for more information).

The code that was releasing the SequenceAssetLoader was first commented
out because we didn't have an understanding of what was happening.

This change removes the early SequenceAssetLoader release all together.
It doesn't have any effect as this code was already commented out.

PiperOrigin-RevId: 532065673
(cherry picked from commit 6dfb387117)
2023-05-17 16:59:55 +00:00
andrewlewis
b0f8a8f316 Signal end-of-stream after creating latch
The output end-of-stream notification from the last shader could theoretically
arrive before the latch for detecting it is created, which might cause waiting
on the latch indefinitely. Create the latch before signaling end of stream so
that it's guaranteed to be set before the end-of-stream signal arrives.

PiperOrigin-RevId: 532056472
(cherry picked from commit 857e6ebee8)
2023-05-17 16:59:55 +00:00
ibaker
7e30091196 Remove two deprecated SimpleCache constructors
Use a non-deprecated constructor that takes a `DatabaseProvider`
instead for better performance.

#minor-release

PiperOrigin-RevId: 532046598
(cherry picked from commit 0a86790be2)
2023-05-17 16:59:55 +00:00
ibaker
07ca741eb1 Rollback of 509830f38f
*** Original commit ***

Rollback of 221a56da38

*** Original commit ***

Rollback of 749d77b1d9

*** Original commit ***

PiperOrigin-RevId: 531530885
(cherry picked from commit 9366b4e50a)
2023-05-17 16:59:54 +00:00
huangdarwin
2ab9c0c556 Transformer: Add latest input format to DebugTraceUtil
This can provide more information to help debug muxer errors

PiperOrigin-RevId: 531521974
(cherry picked from commit 2736b11845)
2023-05-17 16:59:54 +00:00
bachinger
932bed1f79 Implement SystemUI contract for media resumption
When a `MediaButtonReceiver` is found in the manifest, the library
can implement the contract of SystemUI to signal that the app wants
a playback resumption notification to be displayed.

And, vice versa, if no `MediaButtonReceiver` is in the manifest, the
library will signal to not show the notification after the app has been
terminated.

#minor-release

PiperOrigin-RevId: 531516023
(cherry picked from commit 9bf6b7ea20)
2023-05-17 16:59:54 +00:00
sheenachhabra
f15e5733ce Add container module
This module will contain functionalities common to extractor and muxer.

PiperOrigin-RevId: 531501602
(cherry picked from commit eb8ec87a5c)
2023-05-17 16:59:54 +00:00
sheenachhabra
80aac22cf9 Add test file with metadata track
Mp4Muxer supports adding Metadata track.
Added test file to cover this scenario.

PiperOrigin-RevId: 531496409
(cherry picked from commit b3fd202e11)
2023-05-17 16:59:54 +00:00
sheenachhabra
2478b48997 Rollback of 925aa34e13
*** Original commit ***

Rollback of 65d5132f76

*** Original commit ***

Create InAppMuxer in transformer

To use the InAppMuxer, the client needs to pass InAppMuxer Factory.

***

***

PiperOrigin-RevId: 531470081
(cherry picked from commit 867355fdc5)
2023-05-17 16:59:54 +00:00
3473 changed files with 529287 additions and 60478 deletions

View file

@ -5,41 +5,33 @@ body:
- type: markdown
attributes:
value: |
We can only process bug reports that are actionable. Unclear bug reports or reports with
insufficient information may not get attention.
We can only process bug reports that are actionable. Unclear bug reports or reports with insufficient information may not get attention.
Before filing a bug:
-------------------------
- Search existing issues, including issues that are closed:
https://github.com/androidx/media/issues?q=is%3Aissue
- For ExoPlayer-related bugs, please also check for existing issues on the ExoPlayer
tracker: https://github.com/google/ExoPlayer/issues?q=is%3Aissue
- Search existing issues, including issues that are closed: https://github.com/androidx/media/issues?q=is%3Aissue
- For ExoPlayer-related bugs, please also check for existing issues on the ExoPlayer tracker: https://github.com/google/ExoPlayer/issues?q=is%3Aissue
- type: dropdown
attributes:
label: Version
description: What version of Media3 (or ExoPlayer) are you using?
options:
- Media3 1.1.1
- Media3 1.1.0
- Media3 1.0.2
- Media3 1.0.1
- Media3 1.0.0
- Media3 1.0.0-rc02
- Media3 1.0.0-rc01
- Media3 1.0.0-beta03
- Media3 1.0.0-beta02
- Media3 1.0.0-beta01
- Media3 1.0.0-alpha03
- Media3 1.0.0-alpha02
- Media3 1.0.0-alpha01
- Media3 `main` branch
- Media3 main branch
- Media3 pre-release (alpha, beta or RC not in this list)
- ExoPlayer 2.19.1
- ExoPlayer 2.19.0
- ExoPlayer 2.18.7
- ExoPlayer 2.18.6
- ExoPlayer 2.18.5
- Media3 1.5.1
- Media3 1.5.0
- Media3 1.4.1
- Media3 1.4.0
- Media3 1.3.1
- Media3 1.3.0
- Media3 1.2.1
- Media3 1.2.0
- Media3 1.1.1 / ExoPlayer 2.19.1
- Media3 1.1.0 / ExoPlayer 2.19.0
- Media3 1.0.2 / ExoPlayer 2.18.7
- Media3 1.0.1 / ExoPlayer 2.18.6
- Media3 1.0.0 / ExoPlayer 2.18.5
- ExoPlayer 2.18.4
- ExoPlayer 2.18.3
- ExoPlayer 2.18.2
@ -54,14 +46,14 @@ body:
- ExoPlayer 2.14.2
- ExoPlayer 2.14.1
- ExoPlayer 2.14.0
- ExoPlayer `dev-v2` branch
- ExoPlayer dev-v2 branch
- Older (unsupported)
validations:
required: true
- type: textarea
attributes:
label: More version details
description: |
description: >
Required if you selected `main` or `dev-v2` (please provide an exact commit SHA),
or 'pre-release' or 'older' (please provide the version).
- type: textarea

41
.gitignore vendored
View file

@ -52,30 +52,31 @@ tmp
# External native builds
.externalNativeBuild
.cxx
# VP9 extension
extensions/vp9/src/main/jni/libvpx
extensions/vp9/src/main/jni/libvpx_android_configs
extensions/vp9/src/main/jni/libyuv
# VP9 decoder extension
libraries/decoder_vp9/src/main/jni/libvpx
libraries/decoder_vp9/src/main/jni/libvpx_android_configs
libraries/decoder_vp9/src/main/jni/libyuv
# AV1 extension
extensions/av1/src/main/jni/cpu_features
extensions/av1/src/main/jni/libgav1
# AV1 decoder extension
libraries/decoder_av1/src/main/jni/cpu_features
libraries/decoder_av1/src/main/jni/libgav1
# Opus extension
extensions/opus/src/main/jni/libopus
# Opus decoder extension
libraries/decoder_opus/src/main/jni/libopus
# FLAC extension
extensions/flac/src/main/jni/flac
# FLAC decoder extension
libraries/decoder_flac/src/main/jni/flac
# FFmpeg extension
extensions/ffmpeg/src/main/jni/ffmpeg
# FFmpeg decoder extension
libraries/decoder_ffmpeg/src/main/jni/ffmpeg
# Cronet extension
extensions/cronet/jniLibs/*
!extensions/cronet/jniLibs/README.md
extensions/cronet/libs/*
!extensions/cronet/libs/README.md
# Cronet datasource extension
libraries/datasource_cronet/jniLibs/*
!libraries/datasource_cronet/jniLibs/README.md
libraries/datasource_cronet/libs/*
!libraries/datasource_cronet/libs/README.md
# MIDI extension
extensions/midi/lib
# MIDI decoder extension
libraries/decoder_midi/lib

View file

@ -47,13 +47,21 @@ also possible to clone this GitHub repository and depend on the modules locally.
#### 1. Add module dependencies
The easiest way to get started using AndroidX Media is to add gradle
dependencies on the libraries you need in the `build.gradle` file of your app
module.
dependencies on the libraries you need in the `build.gradle.kts` file of your
app module.
For example, to depend on ExoPlayer with DASH playback support and UI components
you can add dependencies on the modules like this:
```gradle
```kotlin
implementation("androidx.media3:media3-exoplayer:1.X.X")
implementation("androidx.media3:media3-exoplayer-dash:1.X.X")
implementation("androidx.media3:media3-ui:1.X.X")
```
Or in Gradle Groovy DSL `build.gradle`:
```groovy
implementation 'androidx.media3:media3-exoplayer:1.X.X'
implementation 'androidx.media3:media3-exoplayer-dash:1.X.X'
implementation 'androidx.media3:media3-ui:1.X.X'
@ -75,21 +83,23 @@ details.
#### 2. Turn on Java 8 support
If not enabled already, you also need to turn on Java 8 support in all
`build.gradle` files depending on AndroidX Media, by adding the following to the
`android` section:
`build.gradle.kts` files depending on AndroidX Media, by adding the following to
the `android` section:
```gradle
```kotlin
compileOptions {
targetCompatibility = JavaVersion.VERSION_1_8
}
```
Or in Gradle Groovy DSL `build.gradle`:
```groovy
compileOptions {
targetCompatibility JavaVersion.VERSION_1_8
}
```
#### 3. Enable multidex
If your Gradle `minSdkVersion` is 20 or lower, you should
[enable multidex](https://developer.android.com/studio/build/multidex) in order
to prevent build errors.
### Locally
Cloning the repository and depending on the modules locally is required when
@ -100,24 +110,59 @@ First, clone the repository into a local directory:
```sh
git clone https://github.com/androidx/media.git
cd media
```
Next, add the following to your project's `settings.gradle` file, replacing
Next, add the following to your project's `settings.gradle.kts` file, replacing
`path/to/media` with the path to your local copy:
```gradle
gradle.ext.androidxMediaModulePrefix = 'media-'
```kotlin
(gradle as ExtensionAware).extra["androidxMediaModulePrefix"] = "media3-"
apply(from = file("path/to/media/core_settings.gradle"))
```
Or in Gradle Groovy DSL `settings.gradle`:
```groovy
gradle.ext.androidxMediaModulePrefix = 'media3-'
apply from: file("path/to/media/core_settings.gradle")
```
You should now see the AndroidX Media modules appear as part of your project.
You can depend on them as you would on any other local module, for example:
You can depend on them from `build.gradle.kts` as you would on any other local
module, for example:
```gradle
implementation project(':media-lib-exoplayer')
implementation project(':media-lib-exoplayer-dash')
implementation project(':media-lib-ui')
```kotlin
implementation(project(":media3-lib-exoplayer"))
implementation(project(":media3-lib-exoplayer-dash"))
implementation(project(":media3-lib-ui"))
```
Or in Gradle Groovy DSL `build.gradle`:
```groovy
implementation project(':media3-lib-exoplayer')
implementation project(':media3-lib-exoplayer-dash')
implementation project(':media3-lib-ui')
```
#### MIDI module
By default the [MIDI module](libraries/decoder_midi) is disabled as a local
dependency, because it requires additional Maven repository config. If you want
to use it as a local dependency, please configure the JitPack repository as
[described in the module README](libraries/decoder_midi/README.md#getting-the-module),
and then enable building the module in your `settings.gradle.kts` file:
```kotlin
gradle.extra.apply {
set("androidxMediaEnableMidiModule", true)
}
```
Or in Gradle Groovy DSL `settings.gradle`:
```groovy
gradle.ext.androidxMediaEnableMidiModule = true
```
## Developing AndroidX Media

File diff suppressed because it is too large Load diff

103
api.txt
View file

@ -1,4 +1,4 @@
// Signature format: 3.0
// Signature format: 2.0
package androidx.media3.common {
public final class AdOverlayInfo {
@ -26,7 +26,7 @@ package androidx.media3.common {
}
public final class AudioAttributes {
method @RequiresApi(21) public androidx.media3.common.AudioAttributes.AudioAttributesV21 getAudioAttributesV21();
method public androidx.media3.common.AudioAttributes.AudioAttributesV21 getAudioAttributesV21();
field public static final androidx.media3.common.AudioAttributes DEFAULT;
field @androidx.media3.common.C.AudioAllowedCapturePolicy public final int allowedCapturePolicy;
field @androidx.media3.common.C.AudioContentType public final int contentType;
@ -35,7 +35,7 @@ package androidx.media3.common {
field @androidx.media3.common.C.AudioUsage public final int usage;
}
@RequiresApi(21) public static final class AudioAttributes.AudioAttributesV21 {
public static final class AudioAttributes.AudioAttributesV21 {
field public final android.media.AudioAttributes audioAttributes;
}
@ -79,6 +79,7 @@ package androidx.media3.common {
field public static final java.util.UUID PLAYREADY_UUID;
field public static final float RATE_UNSET = -3.4028235E38f;
field public static final int ROLE_FLAG_ALTERNATE = 2; // 0x2
field public static final int ROLE_FLAG_AUXILIARY = 32768; // 0x8000
field public static final int ROLE_FLAG_CAPTION = 64; // 0x40
field public static final int ROLE_FLAG_COMMENTARY = 8; // 0x8
field public static final int ROLE_FLAG_DESCRIBES_MUSIC_AND_SOUND = 1024; // 0x400
@ -156,7 +157,7 @@ package androidx.media3.common {
@IntDef(open=true, value={androidx.media3.common.C.CRYPTO_TYPE_UNSUPPORTED, androidx.media3.common.C.CRYPTO_TYPE_NONE, androidx.media3.common.C.CRYPTO_TYPE_FRAMEWORK}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target(java.lang.annotation.ElementType.TYPE_USE) public static @interface C.CryptoType {
}
@IntDef(flag=true, value={androidx.media3.common.C.ROLE_FLAG_MAIN, androidx.media3.common.C.ROLE_FLAG_ALTERNATE, androidx.media3.common.C.ROLE_FLAG_SUPPLEMENTARY, androidx.media3.common.C.ROLE_FLAG_COMMENTARY, androidx.media3.common.C.ROLE_FLAG_DUB, androidx.media3.common.C.ROLE_FLAG_EMERGENCY, androidx.media3.common.C.ROLE_FLAG_CAPTION, androidx.media3.common.C.ROLE_FLAG_SUBTITLE, androidx.media3.common.C.ROLE_FLAG_SIGN, androidx.media3.common.C.ROLE_FLAG_DESCRIBES_VIDEO, androidx.media3.common.C.ROLE_FLAG_DESCRIBES_MUSIC_AND_SOUND, androidx.media3.common.C.ROLE_FLAG_ENHANCED_DIALOG_INTELLIGIBILITY, androidx.media3.common.C.ROLE_FLAG_TRANSCRIBES_DIALOG, androidx.media3.common.C.ROLE_FLAG_EASY_TO_READ, androidx.media3.common.C.ROLE_FLAG_TRICK_PLAY}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target({java.lang.annotation.ElementType.FIELD, java.lang.annotation.ElementType.METHOD, java.lang.annotation.ElementType.PARAMETER, java.lang.annotation.ElementType.LOCAL_VARIABLE, java.lang.annotation.ElementType.TYPE_USE}) public static @interface C.RoleFlags {
@IntDef(flag=true, value={androidx.media3.common.C.ROLE_FLAG_MAIN, androidx.media3.common.C.ROLE_FLAG_ALTERNATE, androidx.media3.common.C.ROLE_FLAG_SUPPLEMENTARY, androidx.media3.common.C.ROLE_FLAG_COMMENTARY, androidx.media3.common.C.ROLE_FLAG_DUB, androidx.media3.common.C.ROLE_FLAG_EMERGENCY, androidx.media3.common.C.ROLE_FLAG_CAPTION, androidx.media3.common.C.ROLE_FLAG_SUBTITLE, androidx.media3.common.C.ROLE_FLAG_SIGN, androidx.media3.common.C.ROLE_FLAG_DESCRIBES_VIDEO, androidx.media3.common.C.ROLE_FLAG_DESCRIBES_MUSIC_AND_SOUND, androidx.media3.common.C.ROLE_FLAG_ENHANCED_DIALOG_INTELLIGIBILITY, androidx.media3.common.C.ROLE_FLAG_TRANSCRIBES_DIALOG, androidx.media3.common.C.ROLE_FLAG_EASY_TO_READ, androidx.media3.common.C.ROLE_FLAG_TRICK_PLAY, androidx.media3.common.C.ROLE_FLAG_AUXILIARY}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target({java.lang.annotation.ElementType.FIELD, java.lang.annotation.ElementType.METHOD, java.lang.annotation.ElementType.PARAMETER, java.lang.annotation.ElementType.LOCAL_VARIABLE, java.lang.annotation.ElementType.TYPE_USE}) public static @interface C.RoleFlags {
}
@IntDef(flag=true, value={androidx.media3.common.C.SELECTION_FLAG_DEFAULT, androidx.media3.common.C.SELECTION_FLAG_FORCED, androidx.media3.common.C.SELECTION_FLAG_AUTOSELECT}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target({java.lang.annotation.ElementType.FIELD, java.lang.annotation.ElementType.METHOD, java.lang.annotation.ElementType.PARAMETER, java.lang.annotation.ElementType.LOCAL_VARIABLE, java.lang.annotation.ElementType.TYPE_USE}) public static @interface C.SelectionFlags {
@ -226,8 +227,8 @@ package androidx.media3.common {
public final class MediaItem {
method public androidx.media3.common.MediaItem.Builder buildUpon();
method public static androidx.media3.common.MediaItem fromUri(String);
method public static androidx.media3.common.MediaItem fromUri(android.net.Uri);
method public static androidx.media3.common.MediaItem fromUri(String);
field public static final String DEFAULT_MEDIA_ID = "";
field public static final androidx.media3.common.MediaItem EMPTY;
field public final androidx.media3.common.MediaItem.ClippingConfiguration clippingConfiguration;
@ -264,8 +265,8 @@ package androidx.media3.common {
method public androidx.media3.common.MediaItem.Builder setRequestMetadata(androidx.media3.common.MediaItem.RequestMetadata);
method public androidx.media3.common.MediaItem.Builder setSubtitleConfigurations(java.util.List<androidx.media3.common.MediaItem.SubtitleConfiguration>);
method public androidx.media3.common.MediaItem.Builder setTag(@Nullable Object);
method public androidx.media3.common.MediaItem.Builder setUri(@Nullable String);
method public androidx.media3.common.MediaItem.Builder setUri(@Nullable android.net.Uri);
method public androidx.media3.common.MediaItem.Builder setUri(@Nullable String);
}
public static class MediaItem.ClippingConfiguration {
@ -548,6 +549,7 @@ package androidx.media3.common {
field public static final String APPLICATION_PGS = "application/pgs";
field @Deprecated public static final String APPLICATION_RAWCC = "application/x-rawcc";
field public static final String APPLICATION_RTSP = "application/x-rtsp";
field public static final String APPLICATION_SDP = "application/sdp";
field public static final String APPLICATION_SS = "application/vnd.ms-sstr+xml";
field public static final String APPLICATION_SUBRIP = "application/x-subrip";
field public static final String APPLICATION_TTML = "application/ttml+xml";
@ -617,17 +619,24 @@ package androidx.media3.common {
public class PlaybackException extends java.lang.Exception {
method @CallSuper public boolean errorInfoEquals(@Nullable androidx.media3.common.PlaybackException);
method public static String getErrorCodeName(@androidx.media3.common.PlaybackException.ErrorCode int);
method public final String getErrorCodeName();
method public static String getErrorCodeName(@androidx.media3.common.PlaybackException.ErrorCode int);
field public static final int CUSTOM_ERROR_CODE_BASE = 1000000; // 0xf4240
field public static final int ERROR_CODE_AUDIO_TRACK_INIT_FAILED = 5001; // 0x1389
field public static final int ERROR_CODE_AUDIO_TRACK_OFFLOAD_INIT_FAILED = 5004; // 0x138c
field public static final int ERROR_CODE_AUDIO_TRACK_OFFLOAD_WRITE_FAILED = 5003; // 0x138b
field public static final int ERROR_CODE_AUDIO_TRACK_WRITE_FAILED = 5002; // 0x138a
field public static final int ERROR_CODE_AUTHENTICATION_EXPIRED = -102; // 0xffffff9a
field public static final int ERROR_CODE_BAD_VALUE = -3; // 0xfffffffd
field public static final int ERROR_CODE_BEHIND_LIVE_WINDOW = 1002; // 0x3ea
field public static final int ERROR_CODE_CONCURRENT_STREAM_LIMIT = -104; // 0xffffff98
field public static final int ERROR_CODE_CONTENT_ALREADY_PLAYING = -110; // 0xffffff92
field public static final int ERROR_CODE_DECODER_INIT_FAILED = 4001; // 0xfa1
field public static final int ERROR_CODE_DECODER_QUERY_FAILED = 4002; // 0xfa2
field public static final int ERROR_CODE_DECODING_FAILED = 4003; // 0xfa3
field public static final int ERROR_CODE_DECODING_FORMAT_EXCEEDS_CAPABILITIES = 4004; // 0xfa4
field public static final int ERROR_CODE_DECODING_FORMAT_UNSUPPORTED = 4005; // 0xfa5
field public static final int ERROR_CODE_DISCONNECTED = -100; // 0xffffff9c
field public static final int ERROR_CODE_DRM_CONTENT_ERROR = 6003; // 0x1773
field public static final int ERROR_CODE_DRM_DEVICE_REVOKED = 6007; // 0x1777
field public static final int ERROR_CODE_DRM_DISALLOWED_OPERATION = 6005; // 0x1775
@ -637,7 +646,9 @@ package androidx.media3.common {
field public static final int ERROR_CODE_DRM_SCHEME_UNSUPPORTED = 6001; // 0x1771
field public static final int ERROR_CODE_DRM_SYSTEM_ERROR = 6006; // 0x1776
field public static final int ERROR_CODE_DRM_UNSPECIFIED = 6000; // 0x1770
field public static final int ERROR_CODE_END_OF_PLAYLIST = -109; // 0xffffff93
field public static final int ERROR_CODE_FAILED_RUNTIME_CHECK = 1004; // 0x3ec
field public static final int ERROR_CODE_INVALID_STATE = -2; // 0xfffffffe
field public static final int ERROR_CODE_IO_BAD_HTTP_STATUS = 2004; // 0x7d4
field public static final int ERROR_CODE_IO_CLEARTEXT_NOT_PERMITTED = 2007; // 0x7d7
field public static final int ERROR_CODE_IO_FILE_NOT_FOUND = 2005; // 0x7d5
@ -647,18 +658,25 @@ package androidx.media3.common {
field public static final int ERROR_CODE_IO_NO_PERMISSION = 2006; // 0x7d6
field public static final int ERROR_CODE_IO_READ_POSITION_OUT_OF_RANGE = 2008; // 0x7d8
field public static final int ERROR_CODE_IO_UNSPECIFIED = 2000; // 0x7d0
field public static final int ERROR_CODE_NOT_AVAILABLE_IN_REGION = -106; // 0xffffff96
field public static final int ERROR_CODE_NOT_SUPPORTED = -6; // 0xfffffffa
field public static final int ERROR_CODE_PARENTAL_CONTROL_RESTRICTED = -105; // 0xffffff97
field public static final int ERROR_CODE_PARSING_CONTAINER_MALFORMED = 3001; // 0xbb9
field public static final int ERROR_CODE_PARSING_CONTAINER_UNSUPPORTED = 3003; // 0xbbb
field public static final int ERROR_CODE_PARSING_MANIFEST_MALFORMED = 3002; // 0xbba
field public static final int ERROR_CODE_PARSING_MANIFEST_UNSUPPORTED = 3004; // 0xbbc
field public static final int ERROR_CODE_PERMISSION_DENIED = -4; // 0xfffffffc
field public static final int ERROR_CODE_PREMIUM_ACCOUNT_REQUIRED = -103; // 0xffffff99
field public static final int ERROR_CODE_REMOTE_ERROR = 1001; // 0x3e9
field public static final int ERROR_CODE_SETUP_REQUIRED = -108; // 0xffffff94
field public static final int ERROR_CODE_SKIP_LIMIT_REACHED = -107; // 0xffffff95
field public static final int ERROR_CODE_TIMEOUT = 1003; // 0x3eb
field public static final int ERROR_CODE_UNSPECIFIED = 1000; // 0x3e8
field @androidx.media3.common.PlaybackException.ErrorCode public final int errorCode;
field public final long timestampMs;
}
@IntDef(open=true, value={androidx.media3.common.PlaybackException.ERROR_CODE_UNSPECIFIED, androidx.media3.common.PlaybackException.ERROR_CODE_REMOTE_ERROR, androidx.media3.common.PlaybackException.ERROR_CODE_BEHIND_LIVE_WINDOW, androidx.media3.common.PlaybackException.ERROR_CODE_TIMEOUT, androidx.media3.common.PlaybackException.ERROR_CODE_FAILED_RUNTIME_CHECK, androidx.media3.common.PlaybackException.ERROR_CODE_IO_UNSPECIFIED, androidx.media3.common.PlaybackException.ERROR_CODE_IO_NETWORK_CONNECTION_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_IO_NETWORK_CONNECTION_TIMEOUT, androidx.media3.common.PlaybackException.ERROR_CODE_IO_INVALID_HTTP_CONTENT_TYPE, androidx.media3.common.PlaybackException.ERROR_CODE_IO_BAD_HTTP_STATUS, androidx.media3.common.PlaybackException.ERROR_CODE_IO_FILE_NOT_FOUND, androidx.media3.common.PlaybackException.ERROR_CODE_IO_NO_PERMISSION, androidx.media3.common.PlaybackException.ERROR_CODE_IO_CLEARTEXT_NOT_PERMITTED, androidx.media3.common.PlaybackException.ERROR_CODE_IO_READ_POSITION_OUT_OF_RANGE, androidx.media3.common.PlaybackException.ERROR_CODE_PARSING_CONTAINER_MALFORMED, androidx.media3.common.PlaybackException.ERROR_CODE_PARSING_MANIFEST_MALFORMED, androidx.media3.common.PlaybackException.ERROR_CODE_PARSING_CONTAINER_UNSUPPORTED, androidx.media3.common.PlaybackException.ERROR_CODE_PARSING_MANIFEST_UNSUPPORTED, androidx.media3.common.PlaybackException.ERROR_CODE_DECODER_INIT_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_DECODER_QUERY_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_DECODING_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_DECODING_FORMAT_EXCEEDS_CAPABILITIES, androidx.media3.common.PlaybackException.ERROR_CODE_DECODING_FORMAT_UNSUPPORTED, androidx.media3.common.PlaybackException.ERROR_CODE_AUDIO_TRACK_INIT_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_AUDIO_TRACK_WRITE_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_UNSPECIFIED, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_SCHEME_UNSUPPORTED, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_PROVISIONING_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_CONTENT_ERROR, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_LICENSE_ACQUISITION_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_DISALLOWED_OPERATION, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_SYSTEM_ERROR, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_DEVICE_REVOKED, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_LICENSE_EXPIRED}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target({java.lang.annotation.ElementType.FIELD, java.lang.annotation.ElementType.METHOD, java.lang.annotation.ElementType.PARAMETER, java.lang.annotation.ElementType.LOCAL_VARIABLE, java.lang.annotation.ElementType.TYPE_USE}) public static @interface PlaybackException.ErrorCode {
@IntDef(open=true, value={androidx.media3.common.PlaybackException.ERROR_CODE_INVALID_STATE, androidx.media3.common.PlaybackException.ERROR_CODE_BAD_VALUE, androidx.media3.common.PlaybackException.ERROR_CODE_PERMISSION_DENIED, androidx.media3.common.PlaybackException.ERROR_CODE_NOT_SUPPORTED, androidx.media3.common.PlaybackException.ERROR_CODE_DISCONNECTED, androidx.media3.common.PlaybackException.ERROR_CODE_AUTHENTICATION_EXPIRED, androidx.media3.common.PlaybackException.ERROR_CODE_PREMIUM_ACCOUNT_REQUIRED, androidx.media3.common.PlaybackException.ERROR_CODE_CONCURRENT_STREAM_LIMIT, androidx.media3.common.PlaybackException.ERROR_CODE_PARENTAL_CONTROL_RESTRICTED, androidx.media3.common.PlaybackException.ERROR_CODE_NOT_AVAILABLE_IN_REGION, androidx.media3.common.PlaybackException.ERROR_CODE_SKIP_LIMIT_REACHED, androidx.media3.common.PlaybackException.ERROR_CODE_SETUP_REQUIRED, androidx.media3.common.PlaybackException.ERROR_CODE_END_OF_PLAYLIST, androidx.media3.common.PlaybackException.ERROR_CODE_CONTENT_ALREADY_PLAYING, androidx.media3.common.PlaybackException.ERROR_CODE_UNSPECIFIED, androidx.media3.common.PlaybackException.ERROR_CODE_REMOTE_ERROR, androidx.media3.common.PlaybackException.ERROR_CODE_BEHIND_LIVE_WINDOW, androidx.media3.common.PlaybackException.ERROR_CODE_TIMEOUT, androidx.media3.common.PlaybackException.ERROR_CODE_FAILED_RUNTIME_CHECK, androidx.media3.common.PlaybackException.ERROR_CODE_IO_UNSPECIFIED, androidx.media3.common.PlaybackException.ERROR_CODE_IO_NETWORK_CONNECTION_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_IO_NETWORK_CONNECTION_TIMEOUT, androidx.media3.common.PlaybackException.ERROR_CODE_IO_INVALID_HTTP_CONTENT_TYPE, androidx.media3.common.PlaybackException.ERROR_CODE_IO_BAD_HTTP_STATUS, androidx.media3.common.PlaybackException.ERROR_CODE_IO_FILE_NOT_FOUND, androidx.media3.common.PlaybackException.ERROR_CODE_IO_NO_PERMISSION, androidx.media3.common.PlaybackException.ERROR_CODE_IO_CLEARTEXT_NOT_PERMITTED, androidx.media3.common.PlaybackException.ERROR_CODE_IO_READ_POSITION_OUT_OF_RANGE, androidx.media3.common.PlaybackException.ERROR_CODE_PARSING_CONTAINER_MALFORMED, androidx.media3.common.PlaybackException.ERROR_CODE_PARSING_MANIFEST_MALFORMED, androidx.media3.common.PlaybackException.ERROR_CODE_PARSING_CONTAINER_UNSUPPORTED, androidx.media3.common.PlaybackException.ERROR_CODE_PARSING_MANIFEST_UNSUPPORTED, androidx.media3.common.PlaybackException.ERROR_CODE_DECODER_INIT_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_DECODER_QUERY_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_DECODING_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_DECODING_FORMAT_EXCEEDS_CAPABILITIES, androidx.media3.common.PlaybackException.ERROR_CODE_DECODING_FORMAT_UNSUPPORTED, androidx.media3.common.PlaybackException.ERROR_CODE_AUDIO_TRACK_INIT_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_AUDIO_TRACK_WRITE_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_AUDIO_TRACK_OFFLOAD_INIT_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_AUDIO_TRACK_OFFLOAD_WRITE_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_UNSPECIFIED, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_SCHEME_UNSUPPORTED, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_PROVISIONING_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_CONTENT_ERROR, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_LICENSE_ACQUISITION_FAILED, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_DISALLOWED_OPERATION, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_SYSTEM_ERROR, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_DEVICE_REVOKED, androidx.media3.common.PlaybackException.ERROR_CODE_DRM_LICENSE_EXPIRED}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target({java.lang.annotation.ElementType.FIELD, java.lang.annotation.ElementType.METHOD, java.lang.annotation.ElementType.PARAMETER, java.lang.annotation.ElementType.LOCAL_VARIABLE, java.lang.annotation.ElementType.TYPE_USE}) public static @interface PlaybackException.ErrorCode {
}
public final class PlaybackParameters {
@ -674,8 +692,8 @@ package androidx.media3.common {
method public void addListener(androidx.media3.common.Player.Listener);
method public void addMediaItem(androidx.media3.common.MediaItem);
method public void addMediaItem(int, androidx.media3.common.MediaItem);
method public void addMediaItems(java.util.List<androidx.media3.common.MediaItem>);
method public void addMediaItems(int, java.util.List<androidx.media3.common.MediaItem>);
method public void addMediaItems(java.util.List<androidx.media3.common.MediaItem>);
method public boolean canAdvertiseSession();
method public void clearMediaItems();
method public void clearVideoSurface();
@ -751,21 +769,22 @@ package androidx.media3.common {
method public void replaceMediaItems(int, int, java.util.List<androidx.media3.common.MediaItem>);
method public void seekBack();
method public void seekForward();
method public void seekTo(long);
method public void seekTo(int, long);
method public void seekTo(long);
method public void seekToDefaultPosition();
method public void seekToDefaultPosition(int);
method public void seekToNext();
method public void seekToNextMediaItem();
method public void seekToPrevious();
method public void seekToPreviousMediaItem();
method public void setAudioAttributes(androidx.media3.common.AudioAttributes, boolean);
method @Deprecated public void setDeviceMuted(boolean);
method public void setDeviceMuted(boolean, @androidx.media3.common.C.VolumeFlags int);
method @Deprecated public void setDeviceVolume(@IntRange(from=0) int);
method public void setDeviceVolume(@IntRange(from=0) int, int);
method public void setDeviceVolume(@IntRange(from=0) int, @androidx.media3.common.C.VolumeFlags int);
method public void setMediaItem(androidx.media3.common.MediaItem);
method public void setMediaItem(androidx.media3.common.MediaItem, long);
method public void setMediaItem(androidx.media3.common.MediaItem, boolean);
method public void setMediaItem(androidx.media3.common.MediaItem, long);
method public void setMediaItems(java.util.List<androidx.media3.common.MediaItem>);
method public void setMediaItems(java.util.List<androidx.media3.common.MediaItem>, boolean);
method public void setMediaItems(java.util.List<androidx.media3.common.MediaItem>, int, long);
@ -807,6 +826,7 @@ package androidx.media3.common {
field public static final int COMMAND_SEEK_TO_NEXT_MEDIA_ITEM = 8; // 0x8
field public static final int COMMAND_SEEK_TO_PREVIOUS = 7; // 0x7
field public static final int COMMAND_SEEK_TO_PREVIOUS_MEDIA_ITEM = 6; // 0x6
field public static final int COMMAND_SET_AUDIO_ATTRIBUTES = 35; // 0x23
field @Deprecated public static final int COMMAND_SET_DEVICE_VOLUME = 25; // 0x19
field public static final int COMMAND_SET_DEVICE_VOLUME_WITH_FLAGS = 33; // 0x21
field public static final int COMMAND_SET_MEDIA_ITEM = 31; // 0x1f
@ -824,6 +844,7 @@ package androidx.media3.common {
field public static final int DISCONTINUITY_REASON_REMOVE = 4; // 0x4
field public static final int DISCONTINUITY_REASON_SEEK = 1; // 0x1
field public static final int DISCONTINUITY_REASON_SEEK_ADJUSTMENT = 2; // 0x2
field public static final int DISCONTINUITY_REASON_SILENCE_SKIP = 6; // 0x6
field public static final int DISCONTINUITY_REASON_SKIP = 3; // 0x3
field public static final int EVENT_AUDIO_ATTRIBUTES_CHANGED = 20; // 0x14
field public static final int EVENT_AUDIO_SESSION_ID = 21; // 0x15
@ -881,7 +902,7 @@ package androidx.media3.common {
field public static final int TIMELINE_CHANGE_REASON_SOURCE_UPDATE = 1; // 0x1
}
@IntDef({androidx.media3.common.Player.COMMAND_INVALID, androidx.media3.common.Player.COMMAND_PLAY_PAUSE, androidx.media3.common.Player.COMMAND_PREPARE, androidx.media3.common.Player.COMMAND_STOP, androidx.media3.common.Player.COMMAND_SEEK_TO_DEFAULT_POSITION, androidx.media3.common.Player.COMMAND_SEEK_IN_CURRENT_MEDIA_ITEM, androidx.media3.common.Player.COMMAND_SEEK_TO_PREVIOUS_MEDIA_ITEM, androidx.media3.common.Player.COMMAND_SEEK_TO_PREVIOUS, androidx.media3.common.Player.COMMAND_SEEK_TO_NEXT_MEDIA_ITEM, androidx.media3.common.Player.COMMAND_SEEK_TO_NEXT, androidx.media3.common.Player.COMMAND_SEEK_TO_MEDIA_ITEM, androidx.media3.common.Player.COMMAND_SEEK_BACK, androidx.media3.common.Player.COMMAND_SEEK_FORWARD, androidx.media3.common.Player.COMMAND_SET_SPEED_AND_PITCH, androidx.media3.common.Player.COMMAND_SET_SHUFFLE_MODE, androidx.media3.common.Player.COMMAND_SET_REPEAT_MODE, androidx.media3.common.Player.COMMAND_GET_CURRENT_MEDIA_ITEM, androidx.media3.common.Player.COMMAND_GET_TIMELINE, androidx.media3.common.Player.COMMAND_GET_MEDIA_ITEMS_METADATA, androidx.media3.common.Player.COMMAND_GET_METADATA, androidx.media3.common.Player.COMMAND_SET_MEDIA_ITEMS_METADATA, androidx.media3.common.Player.COMMAND_SET_PLAYLIST_METADATA, androidx.media3.common.Player.COMMAND_SET_MEDIA_ITEM, androidx.media3.common.Player.COMMAND_CHANGE_MEDIA_ITEMS, androidx.media3.common.Player.COMMAND_GET_AUDIO_ATTRIBUTES, androidx.media3.common.Player.COMMAND_GET_VOLUME, androidx.media3.common.Player.COMMAND_GET_DEVICE_VOLUME, androidx.media3.common.Player.COMMAND_SET_VOLUME, androidx.media3.common.Player.COMMAND_SET_DEVICE_VOLUME, androidx.media3.common.Player.COMMAND_SET_DEVICE_VOLUME_WITH_FLAGS, androidx.media3.common.Player.COMMAND_ADJUST_DEVICE_VOLUME, androidx.media3.common.Player.COMMAND_ADJUST_DEVICE_VOLUME_WITH_FLAGS, androidx.media3.common.Player.COMMAND_SET_VIDEO_SURFACE, androidx.media3.common.Player.COMMAND_GET_TEXT, androidx.media3.common.Player.COMMAND_SET_TRACK_SELECTION_PARAMETERS, androidx.media3.common.Player.COMMAND_GET_TRACKS, androidx.media3.common.Player.COMMAND_RELEASE}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target({java.lang.annotation.ElementType.FIELD, java.lang.annotation.ElementType.METHOD, java.lang.annotation.ElementType.PARAMETER, java.lang.annotation.ElementType.LOCAL_VARIABLE, java.lang.annotation.ElementType.TYPE_USE}) public static @interface Player.Command {
@IntDef({androidx.media3.common.Player.COMMAND_INVALID, androidx.media3.common.Player.COMMAND_PLAY_PAUSE, androidx.media3.common.Player.COMMAND_PREPARE, androidx.media3.common.Player.COMMAND_STOP, androidx.media3.common.Player.COMMAND_SEEK_TO_DEFAULT_POSITION, androidx.media3.common.Player.COMMAND_SEEK_IN_CURRENT_MEDIA_ITEM, androidx.media3.common.Player.COMMAND_SEEK_TO_PREVIOUS_MEDIA_ITEM, androidx.media3.common.Player.COMMAND_SEEK_TO_PREVIOUS, androidx.media3.common.Player.COMMAND_SEEK_TO_NEXT_MEDIA_ITEM, androidx.media3.common.Player.COMMAND_SEEK_TO_NEXT, androidx.media3.common.Player.COMMAND_SEEK_TO_MEDIA_ITEM, androidx.media3.common.Player.COMMAND_SEEK_BACK, androidx.media3.common.Player.COMMAND_SEEK_FORWARD, androidx.media3.common.Player.COMMAND_SET_SPEED_AND_PITCH, androidx.media3.common.Player.COMMAND_SET_SHUFFLE_MODE, androidx.media3.common.Player.COMMAND_SET_REPEAT_MODE, androidx.media3.common.Player.COMMAND_GET_CURRENT_MEDIA_ITEM, androidx.media3.common.Player.COMMAND_GET_TIMELINE, androidx.media3.common.Player.COMMAND_GET_MEDIA_ITEMS_METADATA, androidx.media3.common.Player.COMMAND_GET_METADATA, androidx.media3.common.Player.COMMAND_SET_MEDIA_ITEMS_METADATA, androidx.media3.common.Player.COMMAND_SET_PLAYLIST_METADATA, androidx.media3.common.Player.COMMAND_SET_MEDIA_ITEM, androidx.media3.common.Player.COMMAND_CHANGE_MEDIA_ITEMS, androidx.media3.common.Player.COMMAND_GET_AUDIO_ATTRIBUTES, androidx.media3.common.Player.COMMAND_GET_VOLUME, androidx.media3.common.Player.COMMAND_GET_DEVICE_VOLUME, androidx.media3.common.Player.COMMAND_SET_VOLUME, androidx.media3.common.Player.COMMAND_SET_DEVICE_VOLUME, androidx.media3.common.Player.COMMAND_SET_DEVICE_VOLUME_WITH_FLAGS, androidx.media3.common.Player.COMMAND_ADJUST_DEVICE_VOLUME, androidx.media3.common.Player.COMMAND_ADJUST_DEVICE_VOLUME_WITH_FLAGS, androidx.media3.common.Player.COMMAND_SET_AUDIO_ATTRIBUTES, androidx.media3.common.Player.COMMAND_SET_VIDEO_SURFACE, androidx.media3.common.Player.COMMAND_GET_TEXT, androidx.media3.common.Player.COMMAND_SET_TRACK_SELECTION_PARAMETERS, androidx.media3.common.Player.COMMAND_GET_TRACKS, androidx.media3.common.Player.COMMAND_RELEASE}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target({java.lang.annotation.ElementType.FIELD, java.lang.annotation.ElementType.METHOD, java.lang.annotation.ElementType.PARAMETER, java.lang.annotation.ElementType.LOCAL_VARIABLE, java.lang.annotation.ElementType.TYPE_USE}) public static @interface Player.Command {
}
public static final class Player.Commands {
@ -892,7 +913,7 @@ package androidx.media3.common {
field public static final androidx.media3.common.Player.Commands EMPTY;
}
@IntDef({androidx.media3.common.Player.DISCONTINUITY_REASON_AUTO_TRANSITION, androidx.media3.common.Player.DISCONTINUITY_REASON_SEEK, androidx.media3.common.Player.DISCONTINUITY_REASON_SEEK_ADJUSTMENT, androidx.media3.common.Player.DISCONTINUITY_REASON_SKIP, androidx.media3.common.Player.DISCONTINUITY_REASON_REMOVE, androidx.media3.common.Player.DISCONTINUITY_REASON_INTERNAL}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target({java.lang.annotation.ElementType.FIELD, java.lang.annotation.ElementType.METHOD, java.lang.annotation.ElementType.PARAMETER, java.lang.annotation.ElementType.LOCAL_VARIABLE, java.lang.annotation.ElementType.TYPE_USE}) public static @interface Player.DiscontinuityReason {
@IntDef({androidx.media3.common.Player.DISCONTINUITY_REASON_AUTO_TRANSITION, androidx.media3.common.Player.DISCONTINUITY_REASON_SEEK, androidx.media3.common.Player.DISCONTINUITY_REASON_SEEK_ADJUSTMENT, androidx.media3.common.Player.DISCONTINUITY_REASON_SKIP, androidx.media3.common.Player.DISCONTINUITY_REASON_REMOVE, androidx.media3.common.Player.DISCONTINUITY_REASON_INTERNAL, androidx.media3.common.Player.DISCONTINUITY_REASON_SILENCE_SKIP}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target({java.lang.annotation.ElementType.FIELD, java.lang.annotation.ElementType.METHOD, java.lang.annotation.ElementType.PARAMETER, java.lang.annotation.ElementType.LOCAL_VARIABLE, java.lang.annotation.ElementType.TYPE_USE}) public static @interface Player.DiscontinuityReason {
}
@IntDef({androidx.media3.common.Player.EVENT_TIMELINE_CHANGED, androidx.media3.common.Player.EVENT_MEDIA_ITEM_TRANSITION, androidx.media3.common.Player.EVENT_TRACKS_CHANGED, androidx.media3.common.Player.EVENT_IS_LOADING_CHANGED, androidx.media3.common.Player.EVENT_PLAYBACK_STATE_CHANGED, androidx.media3.common.Player.EVENT_PLAY_WHEN_READY_CHANGED, androidx.media3.common.Player.EVENT_PLAYBACK_SUPPRESSION_REASON_CHANGED, androidx.media3.common.Player.EVENT_IS_PLAYING_CHANGED, androidx.media3.common.Player.EVENT_REPEAT_MODE_CHANGED, androidx.media3.common.Player.EVENT_SHUFFLE_MODE_ENABLED_CHANGED, androidx.media3.common.Player.EVENT_PLAYER_ERROR, androidx.media3.common.Player.EVENT_POSITION_DISCONTINUITY, androidx.media3.common.Player.EVENT_PLAYBACK_PARAMETERS_CHANGED, androidx.media3.common.Player.EVENT_AVAILABLE_COMMANDS_CHANGED, androidx.media3.common.Player.EVENT_MEDIA_METADATA_CHANGED, androidx.media3.common.Player.EVENT_PLAYLIST_METADATA_CHANGED, androidx.media3.common.Player.EVENT_SEEK_BACK_INCREMENT_CHANGED, androidx.media3.common.Player.EVENT_SEEK_FORWARD_INCREMENT_CHANGED, androidx.media3.common.Player.EVENT_MAX_SEEK_TO_PREVIOUS_POSITION_CHANGED, androidx.media3.common.Player.EVENT_TRACK_SELECTION_PARAMETERS_CHANGED, androidx.media3.common.Player.EVENT_AUDIO_ATTRIBUTES_CHANGED, androidx.media3.common.Player.EVENT_AUDIO_SESSION_ID, androidx.media3.common.Player.EVENT_VOLUME_CHANGED, androidx.media3.common.Player.EVENT_SKIP_SILENCE_ENABLED_CHANGED, androidx.media3.common.Player.EVENT_SURFACE_SIZE_CHANGED, androidx.media3.common.Player.EVENT_VIDEO_SIZE_CHANGED, androidx.media3.common.Player.EVENT_RENDERED_FIRST_FRAME, androidx.media3.common.Player.EVENT_CUES, androidx.media3.common.Player.EVENT_METADATA, androidx.media3.common.Player.EVENT_DEVICE_INFO_CHANGED, androidx.media3.common.Player.EVENT_DEVICE_VOLUME_CHANGED}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target({java.lang.annotation.ElementType.FIELD, java.lang.annotation.ElementType.METHOD, java.lang.annotation.ElementType.PARAMETER, java.lang.annotation.ElementType.LOCAL_VARIABLE, java.lang.annotation.ElementType.TYPE_USE}) public static @interface Player.Event {
@ -1073,14 +1094,11 @@ package androidx.media3.common {
method public androidx.media3.common.TrackSelectionParameters.Builder buildUpon();
method public static androidx.media3.common.TrackSelectionParameters fromBundle(android.os.Bundle);
method public static androidx.media3.common.TrackSelectionParameters getDefaults(android.content.Context);
method public android.os.Bundle toBundle();
field public final int audioOffloadModePreference;
method @CallSuper public android.os.Bundle toBundle();
field public final com.google.common.collect.ImmutableSet<java.lang.Integer> disabledTrackTypes;
field public final boolean forceHighestSupportedBitrate;
field public final boolean forceLowestBitrate;
field @androidx.media3.common.C.SelectionFlags public final int ignoredTextSelectionFlags;
field public final boolean isGaplessSupportRequired;
field public final boolean isSpeedChangeSupportRequired;
field public final int maxAudioBitrate;
field public final int maxAudioChannelCount;
field public final int maxVideoBitrate;
@ -1114,7 +1132,6 @@ package androidx.media3.common {
method public androidx.media3.common.TrackSelectionParameters.Builder clearOverridesOfType(@androidx.media3.common.C.TrackType int);
method public androidx.media3.common.TrackSelectionParameters.Builder clearVideoSizeConstraints();
method public androidx.media3.common.TrackSelectionParameters.Builder clearViewportSizeConstraints();
method public androidx.media3.common.TrackSelectionParameters.Builder setAudioOffloadPreference(int, boolean, boolean);
method public androidx.media3.common.TrackSelectionParameters.Builder setForceHighestSupportedBitrate(boolean);
method public androidx.media3.common.TrackSelectionParameters.Builder setForceLowestBitrate(boolean);
method public androidx.media3.common.TrackSelectionParameters.Builder setIgnoredTextSelectionFlags(@androidx.media3.common.C.SelectionFlags int);
@ -1175,7 +1192,7 @@ package androidx.media3.common {
field public static final androidx.media3.common.VideoSize UNKNOWN;
field @IntRange(from=0) public final int height;
field @FloatRange(from=0, fromInclusive=false) public final float pixelWidthHeightRatio;
field @IntRange(from=0, to=359) public final int unappliedRotationDegrees;
field @Deprecated @IntRange(from=0, to=359) public final int unappliedRotationDegrees;
field @IntRange(from=0) public final int width;
}
@ -1347,7 +1364,6 @@ package androidx.media3.exoplayer {
method public void addAnalyticsListener(androidx.media3.exoplayer.analytics.AnalyticsListener);
method @Nullable public androidx.media3.exoplayer.ExoPlaybackException getPlayerError();
method public void removeAnalyticsListener(androidx.media3.exoplayer.analytics.AnalyticsListener);
method public void setAudioAttributes(androidx.media3.common.AudioAttributes, boolean);
method public void setHandleAudioBecomingNoisy(boolean);
method public void setWakeMode(@androidx.media3.common.C.WakeMode int);
}
@ -1372,7 +1388,7 @@ package androidx.media3.exoplayer.analytics {
package androidx.media3.exoplayer.drm {
@RequiresApi(18) public final class FrameworkMediaDrm {
public final class FrameworkMediaDrm {
method public static boolean isCryptoSchemeSupported(java.util.UUID);
}
@ -1390,6 +1406,29 @@ package androidx.media3.exoplayer.ima {
method public androidx.media3.exoplayer.ima.ImaAdsLoader build();
}
public final class ImaServerSideAdInsertionMediaSource implements androidx.media3.exoplayer.source.MediaSource {
}
public static final class ImaServerSideAdInsertionMediaSource.AdsLoader {
method public androidx.media3.exoplayer.ima.ImaServerSideAdInsertionMediaSource.AdsLoader.State release();
method public void setPlayer(androidx.media3.common.Player);
}
public static final class ImaServerSideAdInsertionMediaSource.AdsLoader.Builder {
ctor public ImaServerSideAdInsertionMediaSource.AdsLoader.Builder(android.content.Context, androidx.media3.common.AdViewProvider);
method public androidx.media3.exoplayer.ima.ImaServerSideAdInsertionMediaSource.AdsLoader build();
method public androidx.media3.exoplayer.ima.ImaServerSideAdInsertionMediaSource.AdsLoader.Builder setAdsLoaderState(androidx.media3.exoplayer.ima.ImaServerSideAdInsertionMediaSource.AdsLoader.State);
}
public static class ImaServerSideAdInsertionMediaSource.AdsLoader.State {
method public static androidx.media3.exoplayer.ima.ImaServerSideAdInsertionMediaSource.AdsLoader.State fromBundle(android.os.Bundle);
method public android.os.Bundle toBundle();
}
public static final class ImaServerSideAdInsertionMediaSource.Factory implements androidx.media3.exoplayer.source.MediaSource.Factory {
ctor public ImaServerSideAdInsertionMediaSource.Factory(androidx.media3.exoplayer.ima.ImaServerSideAdInsertionMediaSource.AdsLoader, androidx.media3.exoplayer.source.MediaSource.Factory);
}
}
package androidx.media3.exoplayer.source {
@ -1399,6 +1438,7 @@ package androidx.media3.exoplayer.source {
method public androidx.media3.exoplayer.source.DefaultMediaSourceFactory clearLocalAdInsertionComponents();
method public androidx.media3.exoplayer.source.DefaultMediaSourceFactory setDataSourceFactory(androidx.media3.datasource.DataSource.Factory);
method public androidx.media3.exoplayer.source.DefaultMediaSourceFactory setLocalAdInsertionComponents(androidx.media3.exoplayer.source.ads.AdsLoader.Provider, androidx.media3.common.AdViewProvider);
method public androidx.media3.exoplayer.source.DefaultMediaSourceFactory setServerSideAdInsertionMediaSourceFactory(@Nullable androidx.media3.exoplayer.source.MediaSource.Factory);
}
public interface MediaSource {
@ -1487,7 +1527,7 @@ package androidx.media3.session {
field @Nullable public final V value;
}
@IntDef({androidx.media3.session.LibraryResult.RESULT_SUCCESS, androidx.media3.session.LibraryResult.RESULT_ERROR_UNKNOWN, androidx.media3.session.LibraryResult.RESULT_ERROR_INVALID_STATE, androidx.media3.session.LibraryResult.RESULT_ERROR_BAD_VALUE, androidx.media3.session.LibraryResult.RESULT_ERROR_PERMISSION_DENIED, androidx.media3.session.LibraryResult.RESULT_ERROR_IO, androidx.media3.session.LibraryResult.RESULT_INFO_SKIPPED, androidx.media3.session.LibraryResult.RESULT_ERROR_SESSION_DISCONNECTED, androidx.media3.session.LibraryResult.RESULT_ERROR_NOT_SUPPORTED, androidx.media3.session.LibraryResult.RESULT_ERROR_SESSION_AUTHENTICATION_EXPIRED, androidx.media3.session.LibraryResult.RESULT_ERROR_SESSION_PREMIUM_ACCOUNT_REQUIRED, androidx.media3.session.LibraryResult.RESULT_ERROR_SESSION_CONCURRENT_STREAM_LIMIT, androidx.media3.session.LibraryResult.RESULT_ERROR_SESSION_PARENTAL_CONTROL_RESTRICTED, androidx.media3.session.LibraryResult.RESULT_ERROR_SESSION_NOT_AVAILABLE_IN_REGION, androidx.media3.session.LibraryResult.RESULT_ERROR_SESSION_SKIP_LIMIT_REACHED, androidx.media3.session.LibraryResult.RESULT_ERROR_SESSION_SETUP_REQUIRED}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target(java.lang.annotation.ElementType.TYPE_USE) public static @interface LibraryResult.Code {
@IntDef({androidx.media3.session.LibraryResult.RESULT_SUCCESS, androidx.media3.session.SessionError.INFO_CANCELLED, androidx.media3.session.SessionError.ERROR_UNKNOWN, androidx.media3.session.SessionError.ERROR_INVALID_STATE, androidx.media3.session.SessionError.ERROR_BAD_VALUE, androidx.media3.session.SessionError.ERROR_PERMISSION_DENIED, androidx.media3.session.SessionError.ERROR_IO, androidx.media3.session.SessionError.ERROR_SESSION_DISCONNECTED, androidx.media3.session.SessionError.ERROR_NOT_SUPPORTED, androidx.media3.session.SessionError.ERROR_SESSION_AUTHENTICATION_EXPIRED, androidx.media3.session.SessionError.ERROR_SESSION_PREMIUM_ACCOUNT_REQUIRED, androidx.media3.session.SessionError.ERROR_SESSION_CONCURRENT_STREAM_LIMIT, androidx.media3.session.SessionError.ERROR_SESSION_PARENTAL_CONTROL_RESTRICTED, androidx.media3.session.SessionError.ERROR_SESSION_NOT_AVAILABLE_IN_REGION, androidx.media3.session.SessionError.ERROR_SESSION_SKIP_LIMIT_REACHED, androidx.media3.session.SessionError.ERROR_SESSION_SETUP_REQUIRED}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target(java.lang.annotation.ElementType.TYPE_USE) public static @interface LibraryResult.Code {
}
public final class MediaBrowser extends androidx.media3.session.MediaController {
@ -1525,8 +1565,8 @@ package androidx.media3.session {
method public final void addListener(androidx.media3.common.Player.Listener);
method public final void addMediaItem(androidx.media3.common.MediaItem);
method public final void addMediaItem(int, androidx.media3.common.MediaItem);
method public final void addMediaItems(java.util.List<androidx.media3.common.MediaItem>);
method public final void addMediaItems(int, java.util.List<androidx.media3.common.MediaItem>);
method public final void addMediaItems(java.util.List<androidx.media3.common.MediaItem>);
method public final boolean canAdvertiseSession();
method public final void clearMediaItems();
method public final void clearVideoSurface();
@ -1593,8 +1633,8 @@ package androidx.media3.session {
method public final boolean isLoading();
method public final boolean isPlaying();
method public final boolean isPlayingAd();
method public final boolean isSessionCommandAvailable(@androidx.media3.session.SessionCommand.CommandCode int);
method public final boolean isSessionCommandAvailable(androidx.media3.session.SessionCommand);
method public final boolean isSessionCommandAvailable(@androidx.media3.session.SessionCommand.CommandCode int);
method public final void moveMediaItem(int, int);
method public final void moveMediaItems(int, int, int);
method public final void pause();
@ -1609,8 +1649,8 @@ package androidx.media3.session {
method public final void replaceMediaItems(int, int, java.util.List<androidx.media3.common.MediaItem>);
method public final void seekBack();
method public final void seekForward();
method public final void seekTo(long);
method public final void seekTo(int, long);
method public final void seekTo(long);
method public final void seekToDefaultPosition();
method public final void seekToDefaultPosition(int);
method public final void seekToNext();
@ -1618,13 +1658,14 @@ package androidx.media3.session {
method public final void seekToPrevious();
method public final void seekToPreviousMediaItem();
method public final com.google.common.util.concurrent.ListenableFuture<androidx.media3.session.SessionResult> sendCustomCommand(androidx.media3.session.SessionCommand, android.os.Bundle);
method public final void setAudioAttributes(androidx.media3.common.AudioAttributes, boolean);
method @Deprecated public final void setDeviceMuted(boolean);
method public final void setDeviceMuted(boolean, @androidx.media3.common.C.VolumeFlags int);
method @Deprecated public final void setDeviceVolume(@IntRange(from=0) int);
method public final void setDeviceVolume(@IntRange(from=0) int, @androidx.media3.common.C.VolumeFlags int);
method public final void setMediaItem(androidx.media3.common.MediaItem);
method public final void setMediaItem(androidx.media3.common.MediaItem, long);
method public final void setMediaItem(androidx.media3.common.MediaItem, boolean);
method public final void setMediaItem(androidx.media3.common.MediaItem, long);
method public final void setMediaItems(java.util.List<androidx.media3.common.MediaItem>);
method public final void setMediaItems(java.util.List<androidx.media3.common.MediaItem>, boolean);
method public final void setMediaItems(java.util.List<androidx.media3.common.MediaItem>, int, long);
@ -1632,8 +1673,8 @@ package androidx.media3.session {
method public final void setPlaybackParameters(androidx.media3.common.PlaybackParameters);
method public final void setPlaybackSpeed(float);
method public final void setPlaylistMetadata(androidx.media3.common.MediaMetadata);
method public final com.google.common.util.concurrent.ListenableFuture<androidx.media3.session.SessionResult> setRating(String, androidx.media3.common.Rating);
method public final com.google.common.util.concurrent.ListenableFuture<androidx.media3.session.SessionResult> setRating(androidx.media3.common.Rating);
method public final com.google.common.util.concurrent.ListenableFuture<androidx.media3.session.SessionResult> setRating(String, androidx.media3.common.Rating);
method public final void setRepeatMode(@androidx.media3.common.Player.RepeatMode int);
method public final void setShuffleModeEnabled(boolean);
method public final void setTrackSelectionParameters(androidx.media3.common.TrackSelectionParameters);
@ -1745,8 +1786,8 @@ package androidx.media3.session {
method public default void onDisconnected(androidx.media3.session.MediaSession, androidx.media3.session.MediaSession.ControllerInfo);
method @Deprecated @androidx.media3.session.SessionResult.Code public default int onPlayerCommandRequest(androidx.media3.session.MediaSession, androidx.media3.session.MediaSession.ControllerInfo, @androidx.media3.common.Player.Command int);
method public default void onPostConnect(androidx.media3.session.MediaSession, androidx.media3.session.MediaSession.ControllerInfo);
method public default com.google.common.util.concurrent.ListenableFuture<androidx.media3.session.SessionResult> onSetRating(androidx.media3.session.MediaSession, androidx.media3.session.MediaSession.ControllerInfo, String, androidx.media3.common.Rating);
method public default com.google.common.util.concurrent.ListenableFuture<androidx.media3.session.SessionResult> onSetRating(androidx.media3.session.MediaSession, androidx.media3.session.MediaSession.ControllerInfo, androidx.media3.common.Rating);
method public default com.google.common.util.concurrent.ListenableFuture<androidx.media3.session.SessionResult> onSetRating(androidx.media3.session.MediaSession, androidx.media3.session.MediaSession.ControllerInfo, String, androidx.media3.common.Rating);
}
public static final class MediaSession.ConnectionResult {
@ -1762,6 +1803,7 @@ package androidx.media3.session {
method public int getControllerVersion();
method public String getPackageName();
method public int getUid();
field public static final String LEGACY_CONTROLLER_PACKAGE_NAME = "android.media.session.MediaController";
field public static final int LEGACY_CONTROLLER_VERSION = 0; // 0x0
}
@ -1810,6 +1852,7 @@ package androidx.media3.session {
ctor public SessionCommands.Builder();
method public androidx.media3.session.SessionCommands.Builder add(androidx.media3.session.SessionCommand);
method public androidx.media3.session.SessionCommands.Builder add(@androidx.media3.session.SessionCommand.CommandCode int);
method public androidx.media3.session.SessionCommands.Builder addSessionCommands(java.util.Collection<androidx.media3.session.SessionCommand>);
method public androidx.media3.session.SessionCommands build();
method public androidx.media3.session.SessionCommands.Builder remove(androidx.media3.session.SessionCommand);
method public androidx.media3.session.SessionCommands.Builder remove(@androidx.media3.session.SessionCommand.CommandCode int);
@ -1839,7 +1882,7 @@ package androidx.media3.session {
field @androidx.media3.session.SessionResult.Code public final int resultCode;
}
@IntDef({androidx.media3.session.SessionResult.RESULT_SUCCESS, androidx.media3.session.SessionResult.RESULT_ERROR_UNKNOWN, androidx.media3.session.SessionResult.RESULT_ERROR_INVALID_STATE, androidx.media3.session.SessionResult.RESULT_ERROR_BAD_VALUE, androidx.media3.session.SessionResult.RESULT_ERROR_PERMISSION_DENIED, androidx.media3.session.SessionResult.RESULT_ERROR_IO, androidx.media3.session.SessionResult.RESULT_INFO_SKIPPED, androidx.media3.session.SessionResult.RESULT_ERROR_SESSION_DISCONNECTED, androidx.media3.session.SessionResult.RESULT_ERROR_NOT_SUPPORTED, androidx.media3.session.SessionResult.RESULT_ERROR_SESSION_AUTHENTICATION_EXPIRED, androidx.media3.session.SessionResult.RESULT_ERROR_SESSION_PREMIUM_ACCOUNT_REQUIRED, androidx.media3.session.SessionResult.RESULT_ERROR_SESSION_CONCURRENT_STREAM_LIMIT, androidx.media3.session.SessionResult.RESULT_ERROR_SESSION_PARENTAL_CONTROL_RESTRICTED, androidx.media3.session.SessionResult.RESULT_ERROR_SESSION_NOT_AVAILABLE_IN_REGION, androidx.media3.session.SessionResult.RESULT_ERROR_SESSION_SKIP_LIMIT_REACHED, androidx.media3.session.SessionResult.RESULT_ERROR_SESSION_SETUP_REQUIRED}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target(java.lang.annotation.ElementType.TYPE_USE) public static @interface SessionResult.Code {
@IntDef({androidx.media3.session.SessionResult.RESULT_SUCCESS, androidx.media3.session.SessionError.INFO_CANCELLED, androidx.media3.session.SessionError.ERROR_UNKNOWN, androidx.media3.session.SessionError.ERROR_INVALID_STATE, androidx.media3.session.SessionError.ERROR_BAD_VALUE, androidx.media3.session.SessionError.ERROR_PERMISSION_DENIED, androidx.media3.session.SessionError.ERROR_IO, androidx.media3.session.SessionError.ERROR_SESSION_DISCONNECTED, androidx.media3.session.SessionError.ERROR_NOT_SUPPORTED, androidx.media3.session.SessionError.ERROR_SESSION_AUTHENTICATION_EXPIRED, androidx.media3.session.SessionError.ERROR_SESSION_PREMIUM_ACCOUNT_REQUIRED, androidx.media3.session.SessionError.ERROR_SESSION_CONCURRENT_STREAM_LIMIT, androidx.media3.session.SessionError.ERROR_SESSION_PARENTAL_CONTROL_RESTRICTED, androidx.media3.session.SessionError.ERROR_SESSION_NOT_AVAILABLE_IN_REGION, androidx.media3.session.SessionError.ERROR_SESSION_SKIP_LIMIT_REACHED, androidx.media3.session.SessionError.ERROR_SESSION_SETUP_REQUIRED}) @java.lang.annotation.Documented @java.lang.annotation.Retention(java.lang.annotation.RetentionPolicy.SOURCE) @java.lang.annotation.Target(java.lang.annotation.ElementType.TYPE_USE) public static @interface SessionResult.Code {
}
public final class SessionToken {

View file

@ -17,9 +17,9 @@ buildscript {
mavenCentral()
}
dependencies {
classpath 'com.android.tools.build:gradle:8.0.1'
classpath 'com.android.tools.build:gradle:8.3.2'
classpath 'com.google.android.gms:strict-version-matcher-plugin:1.2.4'
classpath 'org.jetbrains.kotlin:kotlin-gradle-plugin:1.8.20'
classpath 'org.jetbrains.kotlin:kotlin-gradle-plugin:1.9.10'
}
}
allprojects {

View file

@ -14,6 +14,8 @@
apply from: "$gradle.ext.androidxMediaSettingsDir/constants.gradle"
apply plugin: 'com.android.library'
group = 'androidx.media3'
android {
compileSdkVersion project.ext.compileSdkVersion
@ -25,11 +27,9 @@ android {
aarMetadata {
minCompileSdk = project.ext.compileSdkVersion
}
multiDexEnabled true
}
compileOptions {
coreLibraryDesugaringEnabled true
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
@ -41,8 +41,3 @@ android {
unitTests.includeAndroidResources true
}
}
dependencies {
androidTestImplementation 'androidx.multidex:multidex:' + androidxMultidexVersion
coreLibraryDesugaring 'com.android.tools:desugar_jdk_libs:1.1.5'
}

View file

@ -12,40 +12,42 @@
// See the License for the specific language governing permissions and
// limitations under the License.
project.ext {
releaseVersion = '1.1.1'
releaseVersionCode = 1_001_001_3_00
minSdkVersion = 16
releaseVersion = '1.5.1'
releaseVersionCode = 1_005_001_3_00
minSdkVersion = 21
// See https://developer.android.com/training/cars/media/automotive-os#automotive-module
automotiveMinSdkVersion = 28
appTargetSdkVersion = 34
// Upgrading this requires [Internal ref: b/193254928] to be fixed, or some
// additional robolectric config.
targetSdkVersion = 30
compileSdkVersion = 34
compileSdkVersion = 35
dexmakerVersion = '2.28.3'
// Use the same JUnit version as the Android repo:
// https://cs.android.com/android/platform/superproject/main/+/main:external/junit/METADATA
junitVersion = '4.13.2'
// Use the same Guava version as the Android repo:
// https://cs.android.com/android/platform/superproject/+/master:external/guava/METADATA
guavaVersion = '31.1-android'
// https://cs.android.com/android/platform/superproject/main/+/main:external/guava/METADATA
guavaVersion = '33.3.1-android'
glideVersion = '4.14.2'
kotlinxCoroutinesVersion = '1.8.1'
leakCanaryVersion = '2.10'
mockitoVersion = '3.12.4'
robolectricVersion = '4.10.3'
robolectricVersion = '4.11'
// Keep this in sync with Google's internal Checker Framework version.
checkerframeworkVersion = '3.13.0'
errorProneVersion = '2.18.0'
jsr305Version = '3.0.2'
kotlinAnnotationsVersion = '1.8.20'
// Updating this to 1.4.0+ will import Kotlin stdlib [internal ref: b/277891049].
androidxAnnotationVersion = '1.3.0'
// Updating this to 1.3.0+ will import Kotlin stdlib [internal ref: b/277891049].
androidxAnnotationExperimentalVersion = '1.2.0'
kotlinAnnotationsVersion = '1.9.0'
androidxAnnotationVersion = '1.6.0'
androidxAnnotationExperimentalVersion = '1.3.1'
androidxAppCompatVersion = '1.6.1'
androidxCollectionVersion = '1.2.0'
androidxConstraintLayoutVersion = '2.1.4'
// Updating this to 1.9.0+ will import Kotlin stdlib [internal ref: b/277891049].
androidxCoreVersion = '1.8.0'
androidxExifInterfaceVersion = '1.3.6'
androidxFuturesVersion = '1.1.0'
androidxMediaVersion = '1.6.0'
androidxMedia2Version = '1.2.1'
androidxMultidexVersion = '2.0.1'
androidxLifecycleVersion = '2.6.0'
androidxMediaVersion = '1.7.0'
androidxRecyclerViewVersion = '1.3.0'
androidxMaterialVersion = '1.8.0'
androidxTestCoreVersion = '1.5.0'
@ -53,10 +55,9 @@ project.ext {
androidxTestJUnitVersion = '1.1.5'
androidxTestRunnerVersion = '1.5.2'
androidxTestRulesVersion = '1.5.0'
androidxTestServicesStorageVersion = '1.4.2'
androidxTestTruthVersion = '1.5.0'
truthVersion = '1.1.3'
okhttpVersion = '4.11.0'
truthVersion = '1.4.0'
okhttpVersion = '4.12.0'
modulePrefix = ':'
if (gradle.ext.has('androidxMediaModulePrefix')) {
modulePrefix += gradle.ext.androidxMediaModulePrefix

View file

@ -24,6 +24,9 @@ if (gradle.ext.has('androidxMediaModulePrefix')) {
include modulePrefix + 'lib-common'
project(modulePrefix + 'lib-common').projectDir = new File(rootDir, 'libraries/common')
include modulePrefix + 'lib-common-ktx'
project(modulePrefix + 'lib-common-ktx').projectDir = new File(rootDir, 'libraries/common_ktx')
include modulePrefix + 'lib-container'
project(modulePrefix + 'lib-container').projectDir = new File(rootDir, 'libraries/container')
@ -57,6 +60,8 @@ include modulePrefix + 'lib-datasource'
project(modulePrefix + 'lib-datasource').projectDir = new File(rootDir, 'libraries/datasource')
include modulePrefix + 'lib-datasource-cronet'
project(modulePrefix + 'lib-datasource-cronet').projectDir = new File(rootDir, 'libraries/datasource_cronet')
include modulePrefix + 'lib-datasource-httpengine'
project(modulePrefix + 'lib-datasource-httpengine').projectDir = new File(rootDir, 'libraries/datasource_httpengine')
include modulePrefix + 'lib-datasource-rtmp'
project(modulePrefix + 'lib-datasource-rtmp').projectDir = new File(rootDir, 'libraries/datasource_rtmp')
include modulePrefix + 'lib-datasource-okhttp'
@ -70,8 +75,12 @@ include modulePrefix + 'lib-decoder-ffmpeg'
project(modulePrefix + 'lib-decoder-ffmpeg').projectDir = new File(rootDir, 'libraries/decoder_ffmpeg')
include modulePrefix + 'lib-decoder-flac'
project(modulePrefix + 'lib-decoder-flac').projectDir = new File(rootDir, 'libraries/decoder_flac')
include modulePrefix + 'lib-decoder-midi'
project(modulePrefix + 'lib-decoder-midi').projectDir = new File(rootDir, 'libraries/decoder_midi')
include modulePrefix + 'lib-decoder-iamf'
project(modulePrefix + 'lib-decoder-iamf').projectDir = new File(rootDir, 'libraries/decoder_iamf')
if (gradle.ext.has('androidxMediaEnableMidiModule') && gradle.ext.androidxMediaEnableMidiModule) {
include modulePrefix + 'lib-decoder-midi'
project(modulePrefix + 'lib-decoder-midi').projectDir = new File(rootDir, 'libraries/decoder_midi')
}
include modulePrefix + 'lib-decoder-opus'
project(modulePrefix + 'lib-decoder-opus').projectDir = new File(rootDir, 'libraries/decoder_opus')
include modulePrefix + 'lib-decoder-vp9'
@ -98,7 +107,3 @@ include modulePrefix + 'test-data'
project(modulePrefix + 'test-data').projectDir = new File(rootDir, 'libraries/test_data')
include modulePrefix + 'test-utils'
project(modulePrefix + 'test-utils').projectDir = new File(rootDir, 'libraries/test_utils')
include modulePrefix + 'test-session-common'
project(modulePrefix + 'test-session-common').projectDir = new File(rootDir, 'libraries/test_session_common')
include modulePrefix + 'test-session-current'
project(modulePrefix + 'test-session-current').projectDir = new File(rootDir, 'libraries/test_session_current')

View file

@ -17,7 +17,7 @@ apply plugin: 'com.android.application'
android {
namespace 'androidx.media3.demo.cast'
compileSdkVersion project.ext.compileSdkVersion
compileSdk project.ext.compileSdkVersion
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
@ -29,7 +29,6 @@ android {
versionCode project.ext.releaseVersionCode
minSdkVersion project.ext.minSdkVersion
targetSdkVersion project.ext.appTargetSdkVersion
multiDexEnabled true
}
buildTypes {
@ -62,7 +61,6 @@ dependencies {
implementation project(modulePrefix + 'lib-ui')
implementation project(modulePrefix + 'lib-cast')
implementation 'androidx.appcompat:appcompat:' + androidxAppCompatVersion
implementation 'androidx.multidex:multidex:' + androidxMultidexVersion
implementation 'androidx.recyclerview:recyclerview:' + androidxRecyclerViewVersion
implementation 'com.google.android.material:material:' + androidxMaterialVersion
}

View file

@ -23,7 +23,6 @@
<uses-sdk/>
<application
android:name="androidx.multidex.MultiDexApplication"
android:label="@string/application_name"
android:icon="@mipmap/ic_launcher"
android:largeHeap="true"

View file

@ -44,6 +44,7 @@ import androidx.recyclerview.widget.RecyclerView.ViewHolder;
import com.google.android.gms.cast.framework.CastButtonFactory;
import com.google.android.gms.cast.framework.CastContext;
import com.google.android.gms.dynamite.DynamiteModule;
import com.google.common.util.concurrent.MoreExecutors;
/**
* An activity that plays video using {@link ExoPlayer} and supports casting using ExoPlayer's Cast
@ -65,7 +66,7 @@ public class MainActivity extends AppCompatActivity
super.onCreate(savedInstanceState);
// Getting the cast context later than onStart can cause device discovery not to take place.
try {
castContext = CastContext.getSharedInstance(this);
castContext = CastContext.getSharedInstance(this, MoreExecutors.directExecutor()).getResult();
} catch (RuntimeException e) {
Throwable cause = e.getCause();
while (cause != null) {

View file

@ -14,6 +14,9 @@
* limitations under the License.
*/
@NonNullApi
@OptIn(markerClass = UnstableApi.class)
package androidx.media3.demo.cast;
import androidx.annotation.OptIn;
import androidx.media3.common.util.NonNullApi;
import androidx.media3.common.util.UnstableApi;

14
demos/compose/README.md Normal file
View file

@ -0,0 +1,14 @@
# ExoPlayer demo with Compose integration
This is an experimental ExoPlayer demo app that is built fully using Compose
features. This should be taken as Work-In-Progress, rather than experimental API
for testing out application development with the media3 and Jetpack Compose
libraries. Please await further announcement via Release Notes for when the
implementation is fully integrated into the library.
For an intermediate solution, use Jetpack Compose Interop with AndroidView and
PlayerView. However, note that it provides limited functionality and some
features may not be supported.
See the [demos README](../README.md) for instructions on how to build and run
this demo.

View file

@ -0,0 +1,87 @@
// Copyright 2024 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
//
// https://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.
apply from: '../../constants.gradle'
apply plugin: 'com.android.application'
apply plugin: 'kotlin-android'
android {
namespace 'androidx.media3.demo.compose'
compileSdk project.ext.compileSdkVersion
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
kotlinOptions {
jvmTarget = '1.8'
}
defaultConfig {
versionName project.ext.releaseVersion
versionCode project.ext.releaseVersionCode
minSdkVersion project.ext.minSdkVersion
targetSdkVersion project.ext.appTargetSdkVersion
}
buildTypes {
release {
shrinkResources true
minifyEnabled true
signingConfig signingConfigs.debug
}
debug {
jniDebuggable = true
}
}
lintOptions {
// The demo app isn't indexed, and doesn't have translations.
disable 'GoogleAppIndexingWarning','MissingTranslation'
}
buildFeatures {
viewBinding true
compose true
}
composeOptions {
kotlinCompilerExtensionVersion = "1.5.3"
}
testOptions {
unitTests {
includeAndroidResources = true
}
}
}
dependencies {
def composeBom = platform('androidx.compose:compose-bom:2024.05.00')
implementation composeBom
implementation 'androidx.activity:activity-compose:1.9.0'
implementation 'androidx.compose.foundation:foundation-android:1.6.7'
implementation 'androidx.compose.material3:material3-android:1.2.1'
implementation 'com.google.android.material:material:' + androidxMaterialVersion
implementation project(modulePrefix + 'lib-exoplayer')
// For detecting and debugging leaks only. LeakCanary is not needed for demo app to work.
debugImplementation 'com.squareup.leakcanary:leakcanary-android:' + leakCanaryVersion
testImplementation 'org.jetbrains.kotlinx:kotlinx-coroutines-test:' + kotlinxCoroutinesVersion
testImplementation 'org.robolectric:robolectric:' + robolectricVersion
testImplementation project(modulePrefix + 'test-utils')
}

View file

@ -0,0 +1,38 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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
https://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.
-->
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
package="androidx.media3.demo.compose">
<uses-sdk/>
<uses-permission android:name="android.permission.INTERNET" />
<application
android:allowBackup="false"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:theme="@style/Theme.Media3ComposeDemo">
<activity
android:name="androidx.media3.demo.compose.MainActivity"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
</manifest>

View file

@ -0,0 +1,63 @@
/*
* Copyright 2024 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
*
* https://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 androidx.media3.demo.compose
import android.os.Bundle
import androidx.activity.ComponentActivity
import androidx.activity.compose.setContent
import androidx.activity.enableEdgeToEdge
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
import androidx.compose.material3.Surface
import androidx.compose.runtime.remember
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.platform.LocalContext
import androidx.media3.common.MediaItem
import androidx.media3.common.Player
import androidx.media3.demo.compose.data.videos
import androidx.media3.exoplayer.ExoPlayer
class MainActivity : ComponentActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
enableEdgeToEdge()
setContent {
Surface {
Column(
verticalArrangement = Arrangement.Center,
horizontalAlignment = Alignment.CenterHorizontally,
) {
val context = LocalContext.current
val exoPlayer = remember {
ExoPlayer.Builder(context).build().apply {
setMediaItem(MediaItem.fromUri(videos[0]))
prepare()
playWhenReady = true
repeatMode = Player.REPEAT_MODE_ONE
}
}
PlayerSurface(
player = exoPlayer,
surfaceType = SURFACE_TYPE_SURFACE_VIEW,
modifier = Modifier.align(Alignment.CenterHorizontally),
)
}
}
}
}
}

View file

@ -0,0 +1,76 @@
/*
* Copyright 2024 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
*
* https://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 androidx.media3.demo.compose
import android.view.Surface
import android.view.SurfaceView
import android.view.TextureView
import androidx.annotation.IntDef
import androidx.compose.foundation.AndroidEmbeddedExternalSurface
import androidx.compose.foundation.AndroidExternalSurface
import androidx.compose.foundation.AndroidExternalSurfaceScope
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.media3.common.Player
/**
* Provides a dedicated drawing [Surface] for media playbacks using a [Player].
*
* The player's video output is displayed with either a [SurfaceView]/[AndroidExternalSurface] or a
* [TextureView]/[AndroidEmbeddedExternalSurface].
*
* [Player] takes care of attaching the rendered output to the [Surface] and clearing it, when it is
* destroyed.
*
* See
* [Choosing a surface type](https://developer.android.com/media/media3/ui/playerview#surfacetype)
* for more information.
*/
@Composable
fun PlayerSurface(player: Player, surfaceType: @SurfaceType Int, modifier: Modifier = Modifier) {
val onSurfaceCreated: (Surface) -> Unit = { surface -> player.setVideoSurface(surface) }
val onSurfaceDestroyed: () -> Unit = { player.setVideoSurface(null) }
val onSurfaceInitialized: AndroidExternalSurfaceScope.() -> Unit = {
onSurface { surface, _, _ ->
onSurfaceCreated(surface)
surface.onDestroyed { onSurfaceDestroyed() }
}
}
when (surfaceType) {
SURFACE_TYPE_SURFACE_VIEW ->
AndroidExternalSurface(modifier = modifier, onInit = onSurfaceInitialized)
SURFACE_TYPE_TEXTURE_VIEW ->
AndroidEmbeddedExternalSurface(modifier = modifier, onInit = onSurfaceInitialized)
else -> throw IllegalArgumentException("Unrecognized surface type: $surfaceType")
}
}
/**
* The type of surface view used for media playbacks. One of [SURFACE_TYPE_SURFACE_VIEW] or
* [SURFACE_TYPE_TEXTURE_VIEW].
*/
@MustBeDocumented
@Retention(AnnotationRetention.SOURCE)
@Target(AnnotationTarget.CLASS, AnnotationTarget.TYPE, AnnotationTarget.TYPE_PARAMETER)
@IntDef(SURFACE_TYPE_SURFACE_VIEW, SURFACE_TYPE_TEXTURE_VIEW)
annotation class SurfaceType
/** Surface type equivalent to [SurfaceView] . */
const val SURFACE_TYPE_SURFACE_VIEW = 1
/** Surface type equivalent to [TextureView]. */
const val SURFACE_TYPE_TEXTURE_VIEW = 2

View file

@ -0,0 +1,23 @@
/*
* Copyright 2024 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
*
* https://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 androidx.media3.demo.compose.data
val videos =
listOf(
"https://html5demos.com/assets/dizzy.mp4",
"https://devstreaming-cdn.apple.com/videos/streaming/examples/bipbop_4x3/gear0/fileSequence0.aac",
"https://storage.googleapis.com/exoplayer-test-media-1/gen-3/screens/dash-vod-single-segment/video-vp9-360.webm",
)

View file

@ -0,0 +1,20 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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.
-->
<shape
xmlns:android="http://schemas.android.com/apk/res/android">
<gradient android:startColor="@color/grey" android:endColor="@color/grey"/>
</shape>

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

View file

@ -0,0 +1,31 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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
https://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.
-->
<resources>
<!-- Base application theme. -->
<style name="Theme.Media3ComposeDemo" parent="Theme.MaterialComponents.DayNight.DarkActionBar">
<!-- Primary brand color. -->
<item name="colorPrimary">@color/purple_200</item>
<item name="colorPrimaryVariant">@color/purple_700</item>
<item name="colorOnPrimary">@color/black</item>
<!-- Secondary brand color. -->
<item name="colorSecondary">@color/teal_200</item>
<item name="colorSecondaryVariant">@color/teal_200</item>
<item name="colorOnSecondary">@color/black</item>
<!-- Status bar color. -->
<item name="android:statusBarColor">?attr/colorPrimaryVariant</item>
<!-- Customize your theme here. -->
</style>
</resources>

View file

@ -0,0 +1,30 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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
https://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.
-->
<resources>
<color name="purple_200">#FFBB86FC</color>
<color name="purple_500">#FF6200EE</color>
<color name="purple_700">#FF3700B3</color>
<color name="teal_200">#FF03DAC5</color>
<color name="teal_700">#FF018786</color>
<color name="black">#FF000000</color>
<color name="white">#FFFFFFFF</color>
<color name="grey">#FF999999</color>
<color name="background">#292929</color>
<color name="player_background">#1c1c1c</color>
<color name="playlist_item_background">#363434</color>
<color name="playlist_item_foreground">#635E5E</color>
<color name="divider">#646464</color>
</resources>

View file

@ -0,0 +1,26 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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
https://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.
-->
<resources>
<string name="app_name">Media3 Compose Demo</string>
<string name="current_playlist_name">Current playlist</string>
<string name="open_player_content_description">Click to view your play list</string>
<string name="added_media_item_format">Added %1$s to playlist</string>
<string name="shuffle">Shuffle</string>
<string name="play_button">Play</string>
<string name="waiting_for_metadata">Waiting for playlist to load…</string>
<string name="notification_permission_denied">
"Without notification access the app can't warn about failed background operations"</string>
</resources>

View file

@ -0,0 +1,31 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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
https://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.
-->
<resources>
<!-- Base application theme. -->
<style name="Theme.Media3ComposeDemo" parent="Theme.MaterialComponents.DayNight.DarkActionBar">
<!-- Primary brand color. -->
<item name="colorPrimary">@color/purple_500</item>
<item name="colorPrimaryVariant">@color/purple_700</item>
<item name="colorOnPrimary">@color/white</item>
<!-- Secondary brand color. -->
<item name="colorSecondary">@color/teal_200</item>
<item name="colorSecondaryVariant">@color/teal_700</item>
<item name="colorOnSecondary">@color/black</item>
<!-- Status bar color. -->
<item name="android:statusBarColor">?attr/colorPrimaryVariant</item>
<!-- Customize your theme here. -->
</style>
</resources>

View file

@ -0,0 +1,8 @@
# Composition demo
This app is an **EXPERIMENTAL** demo app created to explore the potential of `Composition` and `CompositionPlayer` APIs. It may exhibit limited features, occasional bugs, or unexpected behaviors.
**Attention**: `CompositionPlayer` APIs should be taken as work in progress, rather than experimental API. Please await further announcement via [Release Notes](https://github.com/androidx/media/releases) for when the APIs are fully integrated.
See the [demos README](../README.md) for instructions on how to build and run
this demo.

View file

@ -0,0 +1,62 @@
/*
* Copyright 2024 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.
*/
apply from: '../../constants.gradle'
apply plugin: 'com.android.application'
android {
namespace 'androidx.media3.demo.composition'
compileSdk project.ext.compileSdkVersion
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
defaultConfig {
versionName project.ext.releaseVersion
versionCode project.ext.releaseVersionCode
minSdkVersion project.ext.minSdkVersion
targetSdkVersion project.ext.appTargetSdkVersion
}
buildTypes {
release {
shrinkResources true
minifyEnabled true
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.txt'
signingConfig signingConfigs.debug
}
}
lintOptions {
// This demo app isn't indexed and doesn't have translations.
disable 'GoogleAppIndexingWarning','MissingTranslation'
}
}
dependencies {
implementation 'androidx.appcompat:appcompat:1.6.1'
implementation 'com.google.android.material:material:' + androidxMaterialVersion
implementation project(modulePrefix + 'lib-effect')
implementation project(modulePrefix + 'lib-exoplayer')
implementation project(modulePrefix + 'lib-exoplayer-dash')
implementation project(modulePrefix + 'lib-muxer')
implementation project(modulePrefix + 'lib-transformer')
implementation project(modulePrefix + 'lib-ui')
implementation 'androidx.annotation:annotation:' + androidxAnnotationVersion
compileOnly 'org.checkerframework:checker-qual:' + checkerframeworkVersion
}

View file

@ -0,0 +1 @@
# Proguard rules specific to the composition demo app.

View file

@ -0,0 +1,51 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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.
-->
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
package="androidx.media3.demo.composition">
<uses-sdk />
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.READ_MEDIA_VIDEO"/>
<application
android:allowBackup="false"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:supportsRtl="true"
android:requestLegacyExternalStorage="true"
tools:targetApi="29"
android:taskAffinity=""
android:theme="@style/Theme.AppCompat" >
<activity android:name=".CompositionPreviewActivity"
android:configChanges="keyboard|keyboardHidden|orientation|screenSize|screenLayout|smallestScreenSize|uiMode"
android:launchMode="singleTop"
android:label="@string/app_name"
android:exported="true"
android:theme="@style/Theme.MaterialComponents.DayNight.NoActionBar">
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
</activity>
</application>
</manifest>

View file

@ -0,0 +1,69 @@
/*
* Copyright 2024 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 androidx.media3.demo.composition;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;
import androidx.recyclerview.widget.RecyclerView;
import java.util.List;
/** A {@link RecyclerView.Adapter} that displays assets in a sequence in a {@link RecyclerView}. */
public final class AssetItemAdapter extends RecyclerView.Adapter<AssetItemAdapter.ViewHolder> {
private static final String TAG = "AssetItemAdapter";
private final List<String> data;
/**
* Creates a new instance
*
* @param data A list of items to populate RecyclerView with.
*/
public AssetItemAdapter(List<String> data) {
this.data = data;
}
@Override
public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.preset_item, parent, false);
return new ViewHolder(v);
}
@Override
public void onBindViewHolder(ViewHolder holder, int position) {
holder.getTextView().setText(data.get(position));
}
@Override
public int getItemCount() {
return data.size();
}
/** A {@link RecyclerView.ViewHolder} used to build {@link AssetItemAdapter}. */
public static final class ViewHolder extends RecyclerView.ViewHolder {
private final TextView textView;
private ViewHolder(View view) {
super(view);
textView = view.findViewById(R.id.preset_name_text);
}
private TextView getTextView() {
return textView;
}
}
}

View file

@ -0,0 +1,505 @@
/*
* Copyright 2024 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 androidx.media3.demo.composition;
import static androidx.media3.transformer.Composition.HDR_MODE_EXPERIMENTAL_FORCE_INTERPRET_HDR_AS_SDR;
import static androidx.media3.transformer.Composition.HDR_MODE_KEEP_HDR;
import static androidx.media3.transformer.Composition.HDR_MODE_TONE_MAP_HDR_TO_SDR_USING_MEDIACODEC;
import static androidx.media3.transformer.Composition.HDR_MODE_TONE_MAP_HDR_TO_SDR_USING_OPEN_GL;
import android.app.Activity;
import android.content.DialogInterface;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.ArrayAdapter;
import android.widget.CheckBox;
import android.widget.Spinner;
import android.widget.Toast;
import androidx.annotation.Nullable;
import androidx.appcompat.app.AlertDialog;
import androidx.appcompat.app.AppCompatActivity;
import androidx.appcompat.widget.AppCompatButton;
import androidx.appcompat.widget.AppCompatCheckBox;
import androidx.appcompat.widget.AppCompatTextView;
import androidx.media3.common.Effect;
import androidx.media3.common.MediaItem;
import androidx.media3.common.MimeTypes;
import androidx.media3.common.PlaybackException;
import androidx.media3.common.Player;
import androidx.media3.common.audio.SonicAudioProcessor;
import androidx.media3.common.util.Clock;
import androidx.media3.common.util.Log;
import androidx.media3.common.util.Util;
import androidx.media3.effect.DebugTraceUtil;
import androidx.media3.effect.LanczosResample;
import androidx.media3.effect.Presentation;
import androidx.media3.effect.RgbFilter;
import androidx.media3.transformer.Composition;
import androidx.media3.transformer.CompositionPlayer;
import androidx.media3.transformer.EditedMediaItem;
import androidx.media3.transformer.EditedMediaItemSequence;
import androidx.media3.transformer.Effects;
import androidx.media3.transformer.ExportException;
import androidx.media3.transformer.ExportResult;
import androidx.media3.transformer.InAppMuxer;
import androidx.media3.transformer.JsonUtil;
import androidx.media3.transformer.Transformer;
import androidx.media3.ui.PlayerView;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import com.google.common.base.Stopwatch;
import com.google.common.base.Ticker;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableMap;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.TimeUnit;
import org.json.JSONException;
import org.json.JSONObject;
/**
* An {@link Activity} that previews compositions, using {@link
* androidx.media3.transformer.CompositionPlayer}.
*/
public final class CompositionPreviewActivity extends AppCompatActivity {
private static final String TAG = "CompPreviewActivity";
private static final String AUDIO_URI =
"https://storage.googleapis.com/exoplayer-test-media-0/play.mp3";
private static final String SAME_AS_INPUT_OPTION = "same as input";
private static final ImmutableMap<String, @Composition.HdrMode Integer> HDR_MODE_DESCRIPTIONS =
new ImmutableMap.Builder<String, @Composition.HdrMode Integer>()
.put("Keep HDR", HDR_MODE_KEEP_HDR)
.put("MediaCodec tone-map HDR to SDR", HDR_MODE_TONE_MAP_HDR_TO_SDR_USING_MEDIACODEC)
.put("OpenGL tone-map HDR to SDR", HDR_MODE_TONE_MAP_HDR_TO_SDR_USING_OPEN_GL)
.put("Force Interpret HDR as SDR", HDR_MODE_EXPERIMENTAL_FORCE_INTERPRET_HDR_AS_SDR)
.build();
private static final ImmutableList<String> RESOLUTION_HEIGHTS =
ImmutableList.of(
SAME_AS_INPUT_OPTION, "144", "240", "360", "480", "720", "1080", "1440", "2160");
private ArrayList<String> sequenceAssetTitles;
private boolean[] selectedMediaItems;
private String[] presetDescriptions;
private AssetItemAdapter assetItemAdapter;
@Nullable private CompositionPlayer compositionPlayer;
@Nullable private Transformer transformer;
@Nullable private File outputFile;
private PlayerView playerView;
private AppCompatButton exportButton;
private AppCompatTextView exportInformationTextView;
private Stopwatch exportStopwatch;
private boolean includeBackgroundAudioTrack;
private boolean appliesVideoEffects;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.composition_preview_activity);
playerView = findViewById(R.id.composition_player_view);
findViewById(R.id.preview_button).setOnClickListener(view -> previewComposition());
findViewById(R.id.edit_sequence_button).setOnClickListener(view -> selectPreset());
RecyclerView presetList = findViewById(R.id.composition_preset_list);
presetList.addItemDecoration(new DividerItemDecoration(this, DividerItemDecoration.VERTICAL));
LinearLayoutManager layoutManager =
new LinearLayoutManager(this, LinearLayoutManager.VERTICAL, /* reverseLayout= */ false);
presetList.setLayoutManager(layoutManager);
exportInformationTextView = findViewById(R.id.export_information_text);
exportButton = findViewById(R.id.composition_export_button);
exportButton.setOnClickListener(view -> showExportSettings());
AppCompatCheckBox backgroundAudioCheckBox = findViewById(R.id.background_audio_checkbox);
backgroundAudioCheckBox.setOnCheckedChangeListener(
(compoundButton, checked) -> includeBackgroundAudioTrack = checked);
ArrayAdapter<String> resolutionHeightAdapter =
new ArrayAdapter<>(/* context= */ this, R.layout.spinner_item);
resolutionHeightAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
Spinner resolutionHeightSpinner = findViewById(R.id.resolution_height_spinner);
resolutionHeightSpinner.setAdapter(resolutionHeightAdapter);
resolutionHeightAdapter.addAll(RESOLUTION_HEIGHTS);
ArrayAdapter<String> hdrModeAdapter = new ArrayAdapter<>(this, R.layout.spinner_item);
hdrModeAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
Spinner hdrModeSpinner = findViewById(R.id.hdr_mode_spinner);
hdrModeSpinner.setAdapter(hdrModeAdapter);
hdrModeAdapter.addAll(HDR_MODE_DESCRIPTIONS.keySet());
AppCompatCheckBox applyVideoEffectsCheckBox = findViewById(R.id.apply_video_effects_checkbox);
applyVideoEffectsCheckBox.setOnCheckedChangeListener(
((compoundButton, checked) -> appliesVideoEffects = checked));
presetDescriptions = getResources().getStringArray(R.array.preset_descriptions);
// Select two media items by default.
selectedMediaItems = new boolean[presetDescriptions.length];
selectedMediaItems[0] = true;
selectedMediaItems[2] = true;
sequenceAssetTitles = new ArrayList<>();
for (int i = 0; i < selectedMediaItems.length; i++) {
if (selectedMediaItems[i]) {
sequenceAssetTitles.add(presetDescriptions[i]);
}
}
assetItemAdapter = new AssetItemAdapter(sequenceAssetTitles);
presetList.setAdapter(assetItemAdapter);
exportStopwatch =
Stopwatch.createUnstarted(
new Ticker() {
@Override
public long read() {
return android.os.SystemClock.elapsedRealtimeNanos();
}
});
}
@Override
protected void onStart() {
super.onStart();
playerView.onResume();
}
@Override
protected void onStop() {
super.onStop();
playerView.onPause();
releasePlayer();
cancelExport();
exportStopwatch.reset();
}
private Composition prepareComposition() {
String[] presetUris = getResources().getStringArray(/* id= */ R.array.preset_uris);
int[] presetDurationsUs = getResources().getIntArray(/* id= */ R.array.preset_durations);
List<EditedMediaItem> mediaItems = new ArrayList<>();
ImmutableList.Builder<Effect> videoEffectsBuilder = new ImmutableList.Builder<>();
if (appliesVideoEffects) {
videoEffectsBuilder.add(MatrixTransformationFactory.createDizzyCropEffect());
videoEffectsBuilder.add(RgbFilter.createGrayscaleFilter());
}
Spinner resolutionHeightSpinner = findViewById(R.id.resolution_height_spinner);
String selectedResolutionHeight = String.valueOf(resolutionHeightSpinner.getSelectedItem());
if (!SAME_AS_INPUT_OPTION.equals(selectedResolutionHeight)) {
int resolutionHeight = Integer.parseInt(selectedResolutionHeight);
videoEffectsBuilder.add(LanczosResample.scaleToFit(10000, resolutionHeight));
videoEffectsBuilder.add(Presentation.createForHeight(resolutionHeight));
}
ImmutableList<Effect> videoEffects = videoEffectsBuilder.build();
// Preview requires all sequences to be the same duration, so calculate main sequence duration
// and limit background sequence duration to match.
long videoSequenceDurationUs = 0;
for (int i = 0; i < selectedMediaItems.length; i++) {
if (selectedMediaItems[i]) {
SonicAudioProcessor pitchChanger = new SonicAudioProcessor();
pitchChanger.setPitch(mediaItems.size() % 2 == 0 ? 2f : 0.2f);
MediaItem mediaItem =
new MediaItem.Builder()
.setUri(presetUris[i])
.setImageDurationMs(Util.usToMs(presetDurationsUs[i])) // Ignored for audio/video
.build();
EditedMediaItem.Builder itemBuilder =
new EditedMediaItem.Builder(mediaItem)
.setEffects(
new Effects(
/* audioProcessors= */ ImmutableList.of(pitchChanger),
/* videoEffects= */ videoEffects))
.setDurationUs(presetDurationsUs[i]);
videoSequenceDurationUs += presetDurationsUs[i];
mediaItems.add(itemBuilder.build());
}
}
EditedMediaItemSequence videoSequence = new EditedMediaItemSequence.Builder(mediaItems).build();
List<EditedMediaItemSequence> compositionSequences = new ArrayList<>();
compositionSequences.add(videoSequence);
if (includeBackgroundAudioTrack) {
compositionSequences.add(getAudioBackgroundSequence(Util.usToMs(videoSequenceDurationUs)));
}
SonicAudioProcessor sampleRateChanger = new SonicAudioProcessor();
sampleRateChanger.setOutputSampleRateHz(8_000);
Spinner hdrModeSpinner = findViewById(R.id.hdr_mode_spinner);
int selectedHdrMode =
HDR_MODE_DESCRIPTIONS.get(String.valueOf(hdrModeSpinner.getSelectedItem()));
return new Composition.Builder(compositionSequences)
.setEffects(
new Effects(
/* audioProcessors= */ ImmutableList.of(sampleRateChanger),
/* videoEffects= */ ImmutableList.of()))
.setHdrMode(selectedHdrMode)
.build();
}
private EditedMediaItemSequence getAudioBackgroundSequence(long durationMs) {
MediaItem audioMediaItem =
new MediaItem.Builder()
.setUri(AUDIO_URI)
.setClippingConfiguration(
new MediaItem.ClippingConfiguration.Builder()
.setStartPositionMs(0)
.setEndPositionMs(durationMs)
.build())
.build();
EditedMediaItem audioItem =
new EditedMediaItem.Builder(audioMediaItem).setDurationUs(59_000_000).build();
return new EditedMediaItemSequence.Builder(audioItem).build();
}
private void previewComposition() {
releasePlayer();
Composition composition = prepareComposition();
playerView.setPlayer(null);
CompositionPlayer player = new CompositionPlayer.Builder(getApplicationContext()).build();
this.compositionPlayer = player;
playerView.setPlayer(compositionPlayer);
playerView.setControllerAutoShow(false);
player.addListener(
new Player.Listener() {
@Override
public void onPlayerError(PlaybackException error) {
Toast.makeText(getApplicationContext(), "Preview error: " + error, Toast.LENGTH_LONG)
.show();
Log.e(TAG, "Preview error", error);
}
});
player.setRepeatMode(Player.REPEAT_MODE_ALL);
player.setComposition(composition);
player.prepare();
player.play();
}
private void selectPreset() {
new AlertDialog.Builder(/* context= */ this)
.setTitle(R.string.select_preset_title)
.setMultiChoiceItems(presetDescriptions, selectedMediaItems, this::selectPresetInDialog)
.setPositiveButton(R.string.ok, /* listener= */ null)
.setCancelable(false)
.create()
.show();
}
private void selectPresetInDialog(DialogInterface dialog, int which, boolean isChecked) {
selectedMediaItems[which] = isChecked;
// The items will be added to a the sequence in the order they were selected.
if (isChecked) {
sequenceAssetTitles.add(presetDescriptions[which]);
assetItemAdapter.notifyItemInserted(sequenceAssetTitles.size() - 1);
} else {
int index = sequenceAssetTitles.indexOf(presetDescriptions[which]);
sequenceAssetTitles.remove(presetDescriptions[which]);
assetItemAdapter.notifyItemRemoved(index);
}
}
private void showExportSettings() {
AlertDialog.Builder alertDialogBuilder = new AlertDialog.Builder(this);
LayoutInflater inflater = this.getLayoutInflater();
View exportSettingsDialogView = inflater.inflate(R.layout.export_settings, null);
alertDialogBuilder
.setView(exportSettingsDialogView)
.setTitle(R.string.export_settings)
.setPositiveButton(
R.string.export, (dialog, id) -> exportComposition(exportSettingsDialogView))
.setNegativeButton(R.string.cancel, (dialog, id) -> dialog.dismiss());
ArrayAdapter<String> audioMimeAdapter =
new ArrayAdapter<>(/* context= */ this, R.layout.spinner_item);
audioMimeAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
Spinner audioMimeSpinner = exportSettingsDialogView.findViewById(R.id.audio_mime_spinner);
audioMimeSpinner.setAdapter(audioMimeAdapter);
audioMimeAdapter.addAll(
SAME_AS_INPUT_OPTION, MimeTypes.AUDIO_AAC, MimeTypes.AUDIO_AMR_NB, MimeTypes.AUDIO_AMR_WB);
ArrayAdapter<String> videoMimeAdapter =
new ArrayAdapter<>(/* context= */ this, R.layout.spinner_item);
videoMimeAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item);
Spinner videoMimeSpinner = exportSettingsDialogView.findViewById(R.id.video_mime_spinner);
videoMimeSpinner.setAdapter(videoMimeAdapter);
videoMimeAdapter.addAll(
SAME_AS_INPUT_OPTION,
MimeTypes.VIDEO_H263,
MimeTypes.VIDEO_H264,
MimeTypes.VIDEO_H265,
MimeTypes.VIDEO_MP4V,
MimeTypes.VIDEO_AV1);
CheckBox enableDebugTracingCheckBox =
exportSettingsDialogView.findViewById(R.id.enable_debug_tracing_checkbox);
enableDebugTracingCheckBox.setOnCheckedChangeListener(
(buttonView, isChecked) -> DebugTraceUtil.enableTracing = isChecked);
// Connect producing fragmented MP4 to using Media3 Muxer
CheckBox useMedia3MuxerCheckBox =
exportSettingsDialogView.findViewById(R.id.use_media3_muxer_checkbox);
CheckBox produceFragmentedMp4CheckBox =
exportSettingsDialogView.findViewById(R.id.produce_fragmented_mp4_checkbox);
useMedia3MuxerCheckBox.setOnCheckedChangeListener(
(buttonView, isChecked) -> {
if (!isChecked) {
produceFragmentedMp4CheckBox.setChecked(false);
}
});
produceFragmentedMp4CheckBox.setOnCheckedChangeListener(
(buttonView, isChecked) -> {
if (isChecked) {
useMedia3MuxerCheckBox.setChecked(true);
}
});
AlertDialog dialog = alertDialogBuilder.create();
dialog.show();
}
private void exportComposition(View exportSettingsDialogView) {
// Cancel and clean up files from any ongoing export.
cancelExport();
Composition composition = prepareComposition();
try {
outputFile =
createExternalCacheFile(
"composition-preview-" + Clock.DEFAULT.elapsedRealtime() + ".mp4");
} catch (IOException e) {
Toast.makeText(
getApplicationContext(),
"Aborting export! Unable to create output file: " + e,
Toast.LENGTH_LONG)
.show();
Log.e(TAG, "Aborting export! Unable to create output file: ", e);
return;
}
String filePath = outputFile.getAbsolutePath();
Transformer.Builder transformerBuilder = new Transformer.Builder(/* context= */ this);
Spinner audioMimeTypeSpinner = exportSettingsDialogView.findViewById(R.id.audio_mime_spinner);
String selectedAudioMimeType = String.valueOf(audioMimeTypeSpinner.getSelectedItem());
if (!SAME_AS_INPUT_OPTION.equals(selectedAudioMimeType)) {
transformerBuilder.setAudioMimeType(selectedAudioMimeType);
}
Spinner videoMimeTypeSpinner = exportSettingsDialogView.findViewById(R.id.video_mime_spinner);
String selectedVideoMimeType = String.valueOf(videoMimeTypeSpinner.getSelectedItem());
if (!SAME_AS_INPUT_OPTION.equals(selectedVideoMimeType)) {
transformerBuilder.setVideoMimeType(selectedVideoMimeType);
}
CheckBox useMedia3MuxerCheckBox =
exportSettingsDialogView.findViewById(R.id.use_media3_muxer_checkbox);
CheckBox produceFragmentedMp4CheckBox =
exportSettingsDialogView.findViewById(R.id.produce_fragmented_mp4_checkbox);
if (useMedia3MuxerCheckBox.isChecked()) {
transformerBuilder.setMuxerFactory(
new InAppMuxer.Factory.Builder()
.setOutputFragmentedMp4(produceFragmentedMp4CheckBox.isChecked())
.build());
}
transformer =
transformerBuilder
.addListener(
new Transformer.Listener() {
@Override
public void onCompleted(Composition composition, ExportResult exportResult) {
exportStopwatch.stop();
long elapsedTimeMs = exportStopwatch.elapsed(TimeUnit.MILLISECONDS);
String details =
getString(R.string.export_completed, elapsedTimeMs / 1000.f, filePath);
Log.d(TAG, DebugTraceUtil.generateTraceSummary());
Log.i(TAG, details);
exportInformationTextView.setText(details);
try {
JSONObject resultJson =
JsonUtil.exportResultAsJsonObject(exportResult)
.put("elapsedTimeMs", elapsedTimeMs)
.put("device", JsonUtil.getDeviceDetailsAsJsonObject());
for (String line : Util.split(resultJson.toString(2), "\n")) {
Log.i(TAG, line);
}
} catch (JSONException e) {
Log.w(TAG, "Unable to convert exportResult to JSON", e);
}
}
@Override
public void onError(
Composition composition,
ExportResult exportResult,
ExportException exportException) {
exportStopwatch.stop();
Toast.makeText(
getApplicationContext(),
"Export error: " + exportException,
Toast.LENGTH_LONG)
.show();
Log.e(TAG, "Export error", exportException);
Log.d(TAG, DebugTraceUtil.generateTraceSummary());
exportInformationTextView.setText(R.string.export_error);
}
})
.build();
exportInformationTextView.setText(R.string.export_started);
exportStopwatch.reset();
exportStopwatch.start();
transformer.start(composition, filePath);
Log.i(TAG, "Export started");
}
private void releasePlayer() {
if (compositionPlayer != null) {
compositionPlayer.release();
compositionPlayer = null;
}
}
/** Cancels any ongoing export operation, and deletes output file contents. */
private void cancelExport() {
if (transformer != null) {
transformer.cancel();
transformer = null;
}
if (outputFile != null) {
outputFile.delete();
outputFile = null;
}
exportInformationTextView.setText("");
}
/**
* Creates a {@link File} of the {@code fileName} in the application cache directory.
*
* <p>If a file of that name already exists, it is overwritten.
*/
// TODO: b/320636291 - Refactor duplicate createExternalCacheFile functions.
private File createExternalCacheFile(String fileName) throws IOException {
File file = new File(getExternalCacheDir(), fileName);
if (file.exists() && !file.delete()) {
throw new IOException("Could not delete file: " + file.getAbsolutePath());
}
if (!file.createNewFile()) {
throw new IOException("Could not create file: " + file.getAbsolutePath());
}
return file;
}
}

View file

@ -0,0 +1,93 @@
/*
* Copyright 2024 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 androidx.media3.demo.composition;
import android.graphics.Matrix;
import androidx.media3.common.C;
import androidx.media3.common.util.Util;
import androidx.media3.effect.GlMatrixTransformation;
import androidx.media3.effect.MatrixTransformation;
/**
* Factory for {@link GlMatrixTransformation GlMatrixTransformations} and {@link
* MatrixTransformation MatrixTransformations} that create video effects by applying transformation
* matrices to the individual video frames.
*/
/* package */ final class MatrixTransformationFactory {
/**
* Returns a {@link MatrixTransformation} that rescales the frames over the first {@link
* #ZOOM_DURATION_SECONDS} seconds, such that the rectangle filled with the input frame increases
* linearly in size from a single point to filling the full output frame.
*/
public static MatrixTransformation createZoomInTransition() {
return MatrixTransformationFactory::calculateZoomInTransitionMatrix;
}
/**
* Returns a {@link MatrixTransformation} that crops frames to a rectangle that moves on an
* ellipse.
*/
public static MatrixTransformation createDizzyCropEffect() {
return MatrixTransformationFactory::calculateDizzyCropMatrix;
}
/**
* Returns a {@link GlMatrixTransformation} that rotates a frame in 3D around the y-axis and
* applies perspective projection to 2D.
*/
public static GlMatrixTransformation createSpin3dEffect() {
return MatrixTransformationFactory::calculate3dSpinMatrix;
}
private static final float ZOOM_DURATION_SECONDS = 2f;
private static final float DIZZY_CROP_ROTATION_PERIOD_US = 5_000_000f;
private static Matrix calculateZoomInTransitionMatrix(long presentationTimeUs) {
Matrix transformationMatrix = new Matrix();
float scale = Math.min(1, presentationTimeUs / (C.MICROS_PER_SECOND * ZOOM_DURATION_SECONDS));
transformationMatrix.postScale(/* sx= */ scale, /* sy= */ scale);
return transformationMatrix;
}
private static android.graphics.Matrix calculateDizzyCropMatrix(long presentationTimeUs) {
double theta = presentationTimeUs * 2 * Math.PI / DIZZY_CROP_ROTATION_PERIOD_US;
float centerX = 0.5f * (float) Math.cos(theta);
float centerY = 0.5f * (float) Math.sin(theta);
android.graphics.Matrix transformationMatrix = new android.graphics.Matrix();
transformationMatrix.postTranslate(/* dx= */ centerX, /* dy= */ centerY);
transformationMatrix.postScale(/* sx= */ 2f, /* sy= */ 2f);
return transformationMatrix;
}
private static float[] calculate3dSpinMatrix(long presentationTimeUs) {
float[] transformationMatrix = new float[16];
android.opengl.Matrix.frustumM(
transformationMatrix,
/* offset= */ 0,
/* left= */ -1f,
/* right= */ 1f,
/* bottom= */ -1f,
/* top= */ 1f,
/* near= */ 3f,
/* far= */ 5f);
android.opengl.Matrix.translateM(
transformationMatrix, /* mOffset= */ 0, /* x= */ 0f, /* y= */ 0f, /* z= */ -4f);
float theta = Util.usToMs(presentationTimeUs) / 10f;
android.opengl.Matrix.rotateM(
transformationMatrix, /* mOffset= */ 0, theta, /* x= */ 0f, /* y= */ 1f, /* z= */ 0f);
return transformationMatrix;
}
}

View file

@ -1,5 +1,5 @@
/*
* Copyright 2020 The Android Open Source Project
* Copyright (C) 2024 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.
@ -13,11 +13,10 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package androidx.media3.demo.cast;
@NonNullApi
@OptIn(markerClass = UnstableApi.class)
package androidx.media3.demo.composition;
import androidx.multidex.MultiDexApplication;
// Note: Multidex is enabled in code not AndroidManifest.xml because the internal build system
// doesn't dejetify MultiDexApplication in AndroidManifest.xml.
/** Application for multidex support. */
public final class DemoApplication extends MultiDexApplication {}
import androidx.annotation.OptIn;
import androidx.media3.common.util.NonNullApi;
import androidx.media3.common.util.UnstableApi;

View file

@ -0,0 +1,178 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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.
-->
<androidx.constraintlayout.widget.ConstraintLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="16dp">
<com.google.android.material.card.MaterialCardView
android:id="@+id/composition_preview_card_view"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:cardCornerRadius="4dp"
app:cardElevation="2dp">
<LinearLayout
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="wrap_content" >
<androidx.appcompat.widget.AppCompatTextView
android:id="@+id/input_text_view"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginBottom="8dp"
android:padding="8dp"
android:textAppearance="@style/TextAppearance.AppCompat.Medium"
android:text="@string/preview_composition" />
<FrameLayout
android:layout_width="match_parent"
android:layout_height="200dp" >
<androidx.media3.ui.PlayerView
android:id="@+id/composition_player_view"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</FrameLayout>
</LinearLayout>
</com.google.android.material.card.MaterialCardView>
<androidx.appcompat.widget.AppCompatTextView
android:id="@+id/sequence_header_text"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/video_sequence_items"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/composition_preview_card_view"
app:layout_constraintBottom_toTopOf="@id/composition_preset_list"/>
<androidx.appcompat.widget.AppCompatButton
android:id="@+id/edit_sequence_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textAppearance="@style/TextAppearance.AppCompat.Small"
android:text="@string/edit"
app:layout_constraintStart_toEndOf="@id/sequence_header_text"
app:layout_constraintTop_toTopOf="@id/sequence_header_text"
app:layout_constraintBottom_toBottomOf="@id/sequence_header_text"/>
<androidx.appcompat.widget.AppCompatCheckBox
android:id="@+id/apply_video_effects_checkbox"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/add_effects"
app:layout_constraintStart_toEndOf="@id/edit_sequence_button"
app:layout_constraintTop_toTopOf="@id/sequence_header_text"
app:layout_constraintBottom_toBottomOf="@id/sequence_header_text" />
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/composition_preset_list"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_marginTop="16dp"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/edit_sequence_button"
app:layout_constraintBottom_toTopOf="@id/export_information_text"/>
<androidx.appcompat.widget.AppCompatTextView
android:id="@+id/export_information_text"
android:layout_width="match_parent"
android:layout_height="wrap_content"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintBottom_toTopOf="@id/background_audio_checkbox"/>
<androidx.appcompat.widget.AppCompatCheckBox
android:id="@+id/background_audio_checkbox"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/add_background_audio"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintBottom_toTopOf="@id/resolution_height_setting" />
<LinearLayout
android:id="@+id/resolution_height_setting"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:gravity="center_vertical"
android:layout_marginBottom="8dp"
app:layout_constraintBottom_toTopOf="@id/hdr_mode_setting">
<TextView
android:layout_height="wrap_content"
android:layout_width="0dp"
android:layout_weight="1"
android:text="@string/output_video_resolution"/>
<Spinner
android:id="@+id/resolution_height_spinner"
android:layout_gravity="end|center_vertical"
android:gravity="end"
android:layout_height="wrap_content"
android:layout_width="wrap_content"/>
</LinearLayout>
<LinearLayout
android:id="@+id/hdr_mode_setting"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:gravity="center_vertical"
android:layout_marginBottom="12dp"
app:layout_constraintBottom_toTopOf="@id/preview_button">
<TextView
android:layout_height="wrap_content"
android:layout_width="0dp"
android:layout_weight="1"
android:text="@string/hdr_mode" />
<Spinner
android:id="@+id/hdr_mode_spinner"
android:layout_gravity="end|center_vertical"
android:gravity="end"
android:layout_height="wrap_content"
android:layout_width="wrap_content"/>
</LinearLayout>
<androidx.appcompat.widget.AppCompatButton
android:id="@+id/composition_export_button"
android:text="@string/export"
android:layout_marginTop="16dp"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:layout_constraintStart_toEndOf="@id/preview_button"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintBottom_toBottomOf="parent"/>
<androidx.appcompat.widget.AppCompatButton
android:id="@+id/preview_button"
android:text="@string/preview"
android:layout_marginTop="16dp"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toStartOf="@id/composition_export_button"
app:layout_constraintBottom_toBottomOf="parent"/>
</androidx.constraintlayout.widget.ConstraintLayout>

View file

@ -0,0 +1,110 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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.
-->
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/export_settings_list"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
android:padding="8dp">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:gravity="center_vertical"
android:layout_marginBottom="12dp"
android:layout_marginTop="12dp">
<TextView
android:layout_height="wrap_content"
android:layout_width="0dp"
android:layout_weight="1"
android:text="@string/output_audio_mime_type"/>
<Spinner
android:id="@+id/audio_mime_spinner"
android:layout_gravity="end|center_vertical"
android:gravity="end"
android:layout_height="wrap_content"
android:layout_width="wrap_content"/>
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:gravity="center_vertical"
android:layout_marginBottom="12dp">
<TextView
android:layout_height="wrap_content"
android:layout_width="0dp"
android:layout_weight="1"
android:text="@string/output_video_mime_type"/>
<Spinner
android:id="@+id/video_mime_spinner"
android:layout_gravity="end|center_vertical"
android:gravity="end"
android:layout_height="wrap_content"
android:layout_width="wrap_content"/>
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:gravity="center_vertical">
<TextView
android:layout_height="wrap_content"
android:layout_width="0dp"
android:layout_weight="1"
android:text="@string/enable_debug_tracing"/>
<CheckBox
android:id="@+id/enable_debug_tracing_checkbox"
android:layout_gravity="end"
android:checked="false"
android:layout_height="wrap_content"
android:layout_width="wrap_content"/>
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:gravity="center_vertical">
<TextView
android:text="@string/use_media3_muxer"
android:layout_height="wrap_content"
android:layout_width="0dp"
android:layout_weight="1" />
<CheckBox
android:id="@+id/use_media3_muxer_checkbox"
android:layout_gravity="end"
android:checked="false"
android:layout_height="wrap_content"
android:layout_width="wrap_content"/>
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:gravity="center_vertical">
<TextView
android:text="@string/produce_fragmented_mp4"
android:layout_height="wrap_content"
android:layout_width="0dp"
android:layout_weight="1" />
<CheckBox
android:id="@+id/produce_fragmented_mp4_checkbox"
android:layout_gravity="end"
android:checked="false"
android:layout_height="wrap_content"
android:layout_width="wrap_content"/>
</LinearLayout>
</LinearLayout>

View file

@ -0,0 +1,30 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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.
-->
<androidx.appcompat.widget.LinearLayoutCompat
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:padding="8dp">
<androidx.appcompat.widget.AppCompatTextView
android:id="@+id/preset_name_text"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_weight="1"/>
</androidx.appcompat.widget.LinearLayoutCompat>

View file

@ -0,0 +1,25 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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.
-->
<TextView
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="32dp"
android:gravity="start|center_vertical"
android:paddingLeft="4dp"
android:paddingRight="4dp"
android:layout_marginLeft="4dp"
android:layout_marginRight="4dp"
android:textIsSelectable="false" />

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

View file

@ -0,0 +1,31 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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.
-->
<resources xmlns:tools="http://schemas.android.com/tools">
<!-- Base application theme. -->
<style name="Theme.Media3internal" parent="Theme.MaterialComponents.DayNight.DarkActionBar">
<!-- Primary brand color. -->
<item name="colorPrimary">@color/purple_200</item>
<item name="colorPrimaryVariant">@color/purple_700</item>
<item name="colorOnPrimary">@color/black</item>
<!-- Secondary brand color. -->
<item name="colorSecondary">@color/teal_200</item>
<item name="colorSecondaryVariant">@color/teal_200</item>
<item name="colorOnSecondary">@color/black</item>
<!-- Status bar color. -->
<item name="android:statusBarColor">?attr/colorPrimaryVariant</item>
<!-- Customize your theme here. -->
</style>
</resources>

View file

@ -0,0 +1,77 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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.
-->
<resources>
<string-array name="preset_descriptions">
<item>720p H264 video and AAC audio</item>
<item>1080p H265 video and AAC audio</item>
<item>360p H264 video and AAC audio</item>
<item>360p VP8 video and Vorbis audio</item>
<item>4K H264 video and AAC audio (portrait, no B-frames)</item>
<item>8k H265 video and AAC audio</item>
<item>Short 1080p H265 video and AAC audio</item>
<item>Long 180p H264 video and AAC audio</item>
<item>H264 video and AAC audio (portrait, H &gt; W, 0°)</item>
<item>H264 video and AAC audio (portrait, H &lt; W, 90°)</item>
<item>SEF slow motion with 240 fps</item>
<item>480p DASH (non-square pixels)</item>
<item>HDR (HDR10+) H265 limited range video (encoding may fail)</item>
<item>HDR (HLG) H265 limited range video (encoding may fail)</item>
<item>720p H264 video with no audio</item>
<item>London JPG image (plays for 5 secs at 30 fps)</item>
<item>Tokyo JPG image (portrait, plays for 5 secs at 30 fps)</item>
<item>Pixel 7 shorter audio track</item>
</string-array>
<string-array name="preset_uris">
<item>https://storage.googleapis.com/exoplayer-test-media-1/mp4/android-screens-10s.mp4</item>
<item>https://storage.googleapis.com/exoplayer-test-media-0/android-block-1080-hevc.mp4</item>
<item>https://html5demos.com/assets/dizzy.mp4</item>
<item>https://html5demos.com/assets/dizzy.webm</item>
<item>https://storage.googleapis.com/exoplayer-test-media-1/mp4/portrait_4k60.mp4</item>
<item>https://storage.googleapis.com/exoplayer-test-media-1/mp4/8k24fps_4s.mp4</item>
<item>https://storage.googleapis.com/exoplayer-test-media-1/mp4/1920w_1080h_4s.mp4</item>
<item>https://storage.googleapis.com/exoplayer-test-media-0/BigBuckBunny_320x180.mp4</item>
<item>https://storage.googleapis.com/exoplayer-test-media-1/mp4/portrait_avc_aac.mp4</item>
<item>https://storage.googleapis.com/exoplayer-test-media-1/mp4/portrait_rotated_avc_aac.mp4</item>
<item>https://storage.googleapis.com/exoplayer-test-media-1/mp4/slow-motion/slowMotion_stopwatch_240fps_long.mp4</item>
<item>https://storage.googleapis.com/exoplayer-test-media-1/gen/screens/dash-vod-single-segment/manifest-baseline.mpd</item>
<item>https://storage.googleapis.com/exoplayer-test-media-1/mp4/samsung-s21-hdr-hdr10.mp4</item>
<item>https://storage.googleapis.com/exoplayer-test-media-1/mp4/Pixel7Pro_HLG_1080P.mp4</item>
<item>https://storage.googleapis.com/exoplayer-test-media-1/mp4/sample_video_track_only.mp4</item>
<item>https://storage.googleapis.com/exoplayer-test-media-1/jpg/london.jpg</item>
<item>https://storage.googleapis.com/exoplayer-test-media-1/jpg/tokyo.jpg</item>
<item>https://storage.googleapis.com/exoplayer-temp/audio-blip/metronome_selfie_pixel.mp4</item>
</string-array>
<integer-array name="preset_durations">
<item>10024000</item>
<item>23823000</item>
<item>25000000</item>
<item>25000000</item>
<item>3745000</item>
<item>4421000</item>
<item>3923000</item>
<item>596459000</item>
<item>3687000</item>
<item>2235000</item>
<item>47987000</item>
<item>128270000</item>
<item>4236000</item>
<item>5167000</item>
<item>1001000</item>
<item>5000000</item>
<item>5000000</item>
<item>2170000</item>
</integer-array>
</resources>

View file

@ -0,0 +1,24 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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.
-->
<resources>
<color name="purple_200">#FFBB86FC</color>
<color name="purple_500">#FF6200EE</color>
<color name="purple_700">#FF3700B3</color>
<color name="teal_200">#FF03DAC5</color>
<color name="teal_700">#FF018786</color>
<color name="black">#FF000000</color>
<color name="white">#FFFFFFFF</color>
</resources>

View file

@ -0,0 +1,39 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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.
-->
<resources>
<string name="app_name">Composition Demo</string>
<string name="edit">Edit</string>
<string name="add_effects">Add effects</string>
<string name="preview" translatable="false">Preview</string>
<string name="preview_composition" translatable="false">Composition preview</string>
<string name="video_sequence_items" translatable="false">Video sequence items:</string>
<string name="select_preset_title" translatable="false">Choose preset input</string>
<string name="export" translatable="false">Export</string>
<string name="export_completed" translatable="false">Export completed in %.3f seconds.\nOutput: %s</string>
<string name="export_error" translatable="false">Export error</string>
<string name="export_started" translatable="false">Export started</string>
<string name="add_background_audio" translatable="false">Add background audio</string>
<string name="output_video_resolution" translatable="false">Output video resolution</string>
<string name="hdr_mode" translatable="false">HDR mode</string>
<string name="ok" translatable="false">OK</string>
<string name="cancel" translatable="false">Cancel</string>
<string name="export_settings" translatable="false">Export Settings</string>
<string name="output_audio_mime_type" translatable="false">Output audio MIME type</string>
<string name="output_video_mime_type" translatable="false">Output video MIME type</string>
<string name="enable_debug_tracing" translatable="false">Enable debug tracing</string>
<string name="use_media3_muxer" translatable="false">Use Media3 muxer</string>
<string name="produce_fragmented_mp4" translatable="false">Produce fragmented MP4</string>
</resources>

View file

@ -0,0 +1,31 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2024 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.
-->
<resources xmlns:tools="http://schemas.android.com/tools">
<!-- Base application theme. -->
<style name="Theme.Media3internal" parent="Theme.MaterialComponents.DayNight.DarkActionBar">
<!-- Primary brand color. -->
<item name="colorPrimary">@color/purple_500</item>
<item name="colorPrimaryVariant">@color/purple_700</item>
<item name="colorOnPrimary">@color/white</item>
<!-- Secondary brand color. -->
<item name="colorSecondary">@color/teal_200</item>
<item name="colorSecondaryVariant">@color/teal_700</item>
<item name="colorOnSecondary">@color/black</item>
<!-- Status bar color. -->
<item name="android:statusBarColor">?attr/colorPrimaryVariant</item>
<!-- Customize your theme here. -->
</style>
</resources>

View file

@ -17,7 +17,7 @@ apply plugin: 'com.android.application'
android {
namespace 'androidx.media3.demo.gl'
compileSdkVersion project.ext.compileSdkVersion
compileSdk project.ext.compileSdkVersion
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
@ -29,7 +29,6 @@ android {
versionCode project.ext.releaseVersionCode
minSdkVersion project.ext.minSdkVersion
targetSdkVersion project.ext.appTargetSdkVersion
multiDexEnabled true
}
buildTypes {
@ -55,6 +54,5 @@ dependencies {
implementation project(modulePrefix + 'lib-exoplayer-smoothstreaming')
implementation project(modulePrefix + 'lib-ui')
implementation 'androidx.annotation:annotation:' + androidxAnnotationVersion
implementation 'androidx.multidex:multidex:' + androidxMultidexVersion
compileOnly 'org.checkerframework:checker-qual:' + checkerframeworkVersion
}

View file

@ -22,7 +22,6 @@
<uses-sdk/>
<application
android:name="androidx.multidex.MultiDexApplication"
android:allowBackup="false"
android:icon="@mipmap/ic_launcher"
android:label="@string/application_name">

View file

@ -63,7 +63,7 @@ import org.checkerframework.checker.nullness.qual.MonotonicNonNull;
paint = new Paint();
paint.setTextSize(64);
paint.setAntiAlias(true);
paint.setARGB(0xFF, 0xFF, 0xFF, 0xFF);
paint.setColor(Color.WHITE);
textures = new int[1];
overlayBitmap = Bitmap.createBitmap(OVERLAY_WIDTH, OVERLAY_HEIGHT, Bitmap.Config.ARGB_8888);
overlayCanvas = new Canvas(overlayBitmap);

View file

@ -143,7 +143,7 @@ public final class MainActivity extends Activity {
? Assertions.checkNotNull(intent.getData())
: Uri.parse(DEFAULT_MEDIA_URI);
DrmSessionManager drmSessionManager;
if (Util.SDK_INT >= 18 && intent.hasExtra(DRM_SCHEME_EXTRA)) {
if (intent.hasExtra(DRM_SCHEME_EXTRA)) {
String drmScheme = Assertions.checkNotNull(intent.getStringExtra(DRM_SCHEME_EXTRA));
String drmLicenseUrl = Assertions.checkNotNull(intent.getStringExtra(DRM_LICENSE_URL_EXTRA));
UUID drmSchemeUuid = Assertions.checkNotNull(Util.getDrmUuid(drmScheme));

View file

@ -14,6 +14,9 @@
* limitations under the License.
*/
@NonNullApi
@OptIn(markerClass = UnstableApi.class)
package androidx.media3.demo.gl;
import androidx.annotation.OptIn;
import androidx.media3.common.util.NonNullApi;
import androidx.media3.common.util.UnstableApi;

View file

@ -19,7 +19,7 @@ apply plugin: 'kotlin-android'
android {
namespace 'androidx.media3.demo.main'
compileSdkVersion project.ext.compileSdkVersion
compileSdk project.ext.compileSdkVersion
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
@ -31,7 +31,6 @@ android {
versionCode project.ext.releaseVersionCode
minSdkVersion project.ext.minSdkVersion
targetSdkVersion project.ext.appTargetSdkVersion
multiDexEnabled true
}
buildTypes {
@ -55,7 +54,9 @@ android {
disable 'GoogleAppIndexingWarning','MissingTranslation','IconDensities'
}
flavorDimensions "decoderExtensions"
flavorDimensions = ["decoderExtensions"]
buildFeatures.buildConfig true
productFlavors {
noDecoderExtensions {
@ -73,7 +74,6 @@ dependencies {
compileOnly 'org.checkerframework:checker-qual:' + checkerframeworkVersion
implementation 'androidx.annotation:annotation:' + androidxAnnotationVersion
implementation 'androidx.appcompat:appcompat:' + androidxAppCompatVersion
implementation 'androidx.multidex:multidex:' + androidxMultidexVersion
implementation 'com.google.android.material:material:' + androidxMaterialVersion
implementation project(modulePrefix + 'lib-exoplayer')
implementation project(modulePrefix + 'lib-exoplayer-dash')
@ -87,6 +87,7 @@ dependencies {
withDecoderExtensionsImplementation project(modulePrefix + 'lib-decoder-ffmpeg')
withDecoderExtensionsImplementation project(modulePrefix + 'lib-decoder-flac')
withDecoderExtensionsImplementation project(modulePrefix + 'lib-decoder-opus')
withDecoderExtensionsImplementation project(modulePrefix + 'lib-decoder-iamf')
withDecoderExtensionsImplementation project(modulePrefix + 'lib-decoder-vp9')
withDecoderExtensionsImplementation project(modulePrefix + 'lib-decoder-midi')
withDecoderExtensionsImplementation project(modulePrefix + 'lib-datasource-rtmp')

View file

@ -40,7 +40,6 @@
android:largeHeap="true"
android:allowBackup="false"
android:supportsRtl="true"
android:name="androidx.multidex.MultiDexApplication"
tools:targetApi="29">
<activity android:name=".SampleChooserActivity"

View file

@ -143,6 +143,12 @@
"drm_scheme": "widevine",
"drm_license_uri": "https://proxy.uat.widevine.com/proxy?video_id=GTS_HW_SECURE_ALL&provider=widevine_test"
},
{
"name": "20s license with renewal",
"uri": "https://storage.googleapis.com/wvmedia/cenc/h264/tears/tears.mpd",
"drm_scheme": "widevine",
"drm_license_uri": "https://proxy.uat.widevine.com/proxy?video_id=GTS_CAN_RENEW&provider=widevine_test"
},
{
"name": "30s license (fails at ~30s)",
"uri": "https://storage.googleapis.com/wvmedia/cenc/h264/tears/tears.mpd",
@ -474,6 +480,34 @@
"uri": "https://html5demos.com/assets/dizzy.mp4"
}
]
},
{
"name": "Playlist: No ads - DASH live: Tears of Steel (mid) - No ads",
"playlist": [
{
"uri": "https://html5demos.com/assets/dizzy.mp4"
},
{
"uri": "ssai://dai.google.com/?assetKey=PSzZMzAkSXCmlJOWDmRj8Q&format=0&adsId=1"
},
{
"uri": "https://html5demos.com/assets/dizzy.mp4"
}
]
},
{
"name": "Playlist: No ads - HLS live: Big Buck Bunny - No ads",
"playlist": [
{
"uri": "https://html5demos.com/assets/dizzy.mp4"
},
{
"uri": "ssai://dai.google.com/?assetKey=sN_IYUG8STe1ZzhIIE_ksA&format=2&adsId=3"
},
{
"uri": "https://html5demos.com/assets/dizzy.mp4"
}
]
}
]
},
@ -559,6 +593,27 @@
"clip_start_position_ms": 10000
}
]
},
{
"name": "Image -> Video -> Image -> Image",
"playlist": [
{
"uri": "https://storage.googleapis.com/exoplayer-test-media-1/jpg/tokyo.jpg",
"image_duration_ms": 2000
},
{
"uri": "https://html5demos.com/assets/dizzy.mp4",
"clip_end_position_ms": 2000
},
{
"uri": "https://storage.googleapis.com/exoplayer-test-media-1/jpg/london.jpg",
"image_duration_ms": 2000
},
{
"uri": "https://storage.googleapis.com/exoplayer-test-media-1/jpg/tokyo.jpg",
"image_duration_ms": 2000
}
]
}
]
},
@ -650,7 +705,7 @@
]
},
{
"name": "Misc",
"name": "Progressive",
"samples": [
{
"name": "Dizzy (MP4)",
@ -703,6 +758,44 @@
{
"name": "One hour frame counter (MP4)",
"uri": "https://storage.googleapis.com/exoplayer-test-media-1/mp4/frame-counter-one-hour.mp4"
},
{
"name": "Immersive Audio Format Sample (MP4, IAMF)",
"uri": "https://github.com/AOMediaCodec/libiamf/raw/main/tests/test_000036_s.mp4"
}
]
},
{
"name": "Images",
"samples": [
{
"name": "JPEG (wide)",
"uri": "https://storage.googleapis.com/exoplayer-test-media-1/jpg/london.jpg",
"image_duration_ms": 2000
},
{
"name": "JPEG (tall)",
"uri": "https://storage.googleapis.com/exoplayer-test-media-1/jpg/tokyo.jpg",
"image_duration_ms": 2000
},
{
"name": "PNG",
"uri": "https://storage.googleapis.com/exoplayer-test-media-1/png/media3test.png",
"image_duration_ms": 2000
},
{
"name": "JPEG motion photo (still)",
"uri": "https://storage.googleapis.com/exoplayer-test-media-1/jpg/london_motion_photo.jpg",
"image_duration_ms": 2000
},
{
"name": "JPEG motion photo (motion)",
"uri": "https://storage.googleapis.com/exoplayer-test-media-1/jpg/london_motion_photo.jpg"
},
{
"name": "JPEG (Ultra HDR)",
"uri": "https://storage.googleapis.com/exoplayer-test-media-1/jpg/ultra_hdr.jpg",
"image_duration_ms": 2000
}
]
}

View file

@ -63,7 +63,7 @@ public class DemoDownloadService extends DownloadService {
@Override
protected Scheduler getScheduler() {
return Util.SDK_INT >= 21 ? new PlatformScheduler(this, JOB_ID) : null;
return new PlatformScheduler(this, JOB_ID);
}
@Override

View file

@ -16,12 +16,16 @@
package androidx.media3.demo.main;
import android.content.Context;
import android.net.http.HttpEngine;
import android.os.Build;
import android.os.ext.SdkExtensions;
import androidx.annotation.OptIn;
import androidx.media3.database.DatabaseProvider;
import androidx.media3.database.StandaloneDatabaseProvider;
import androidx.media3.datasource.DataSource;
import androidx.media3.datasource.DefaultDataSource;
import androidx.media3.datasource.DefaultHttpDataSource;
import androidx.media3.datasource.HttpEngineDataSource;
import androidx.media3.datasource.cache.Cache;
import androidx.media3.datasource.cache.CacheDataSource;
import androidx.media3.datasource.cache.NoOpCacheEvictor;
@ -46,25 +50,26 @@ public final class DemoUtil {
public static final String DOWNLOAD_NOTIFICATION_CHANNEL_ID = "download_channel";
/**
* Whether the demo application uses Cronet for networking. Note that Cronet does not provide
* automatic support for cookies (https://github.com/google/ExoPlayer/issues/5975).
*
* <p>If set to false, the platform's default network stack is used with a {@link CookieManager}
* configured in {@link #getHttpDataSourceFactory}.
*/
private static final boolean USE_CRONET_FOR_NETWORKING = true;
private static final String TAG = "DemoUtil";
private static final String DOWNLOAD_CONTENT_DIRECTORY = "downloads";
private static DataSource.@MonotonicNonNull Factory dataSourceFactory;
private static DataSource.@MonotonicNonNull Factory httpDataSourceFactory;
@OptIn(markerClass = androidx.media3.common.util.UnstableApi.class)
private static @MonotonicNonNull DatabaseProvider databaseProvider;
private static @MonotonicNonNull File downloadDirectory;
@OptIn(markerClass = androidx.media3.common.util.UnstableApi.class)
private static @MonotonicNonNull Cache downloadCache;
@OptIn(markerClass = androidx.media3.common.util.UnstableApi.class)
private static @MonotonicNonNull DownloadManager downloadManager;
private static @MonotonicNonNull DownloadTracker downloadTracker;
@OptIn(markerClass = androidx.media3.common.util.UnstableApi.class)
private static @MonotonicNonNull DownloadNotificationHelper downloadNotificationHelper;
/** Returns whether extension renderers should be used. */
@ -86,24 +91,30 @@ public final class DemoUtil {
.setExtensionRendererMode(extensionRendererMode);
}
@OptIn(markerClass = androidx.media3.common.util.UnstableApi.class)
public static synchronized DataSource.Factory getHttpDataSourceFactory(Context context) {
if (httpDataSourceFactory == null) {
if (USE_CRONET_FOR_NETWORKING) {
context = context.getApplicationContext();
@Nullable CronetEngine cronetEngine = CronetUtil.buildCronetEngine(context);
if (cronetEngine != null) {
httpDataSourceFactory =
new CronetDataSource.Factory(cronetEngine, Executors.newSingleThreadExecutor());
}
}
if (httpDataSourceFactory == null) {
// We don't want to use Cronet, or we failed to instantiate a CronetEngine.
CookieManager cookieManager = new CookieManager();
cookieManager.setCookiePolicy(CookiePolicy.ACCEPT_ORIGINAL_SERVER);
CookieHandler.setDefault(cookieManager);
httpDataSourceFactory = new DefaultHttpDataSource.Factory();
}
if (httpDataSourceFactory != null) {
return httpDataSourceFactory;
}
context = context.getApplicationContext();
if (Build.VERSION.SDK_INT >= 30
&& SdkExtensions.getExtensionVersion(Build.VERSION_CODES.S) >= 7) {
HttpEngine httpEngine = new HttpEngine.Builder(context).build();
httpDataSourceFactory =
new HttpEngineDataSource.Factory(httpEngine, Executors.newSingleThreadExecutor());
return httpDataSourceFactory;
}
@Nullable CronetEngine cronetEngine = CronetUtil.buildCronetEngine(context);
if (cronetEngine != null) {
httpDataSourceFactory =
new CronetDataSource.Factory(cronetEngine, Executors.newSingleThreadExecutor());
return httpDataSourceFactory;
}
// The device doesn't support HttpEngine and we failed to instantiate a CronetEngine.
CookieManager cookieManager = new CookieManager();
cookieManager.setCookiePolicy(CookiePolicy.ACCEPT_ORIGINAL_SERVER);
CookieHandler.setDefault(cookieManager);
httpDataSourceFactory = new DefaultHttpDataSource.Factory();
return httpDataSourceFactory;
}
@ -128,6 +139,7 @@ public final class DemoUtil {
return downloadNotificationHelper;
}
@OptIn(markerClass = androidx.media3.common.util.UnstableApi.class)
public static synchronized DownloadManager getDownloadManager(Context context) {
ensureDownloadManagerInitialized(context);
return downloadManager;

View file

@ -16,15 +16,16 @@
package androidx.media3.demo.main;
import static com.google.common.base.Preconditions.checkNotNull;
import static com.google.common.base.Preconditions.checkState;
import android.content.Context;
import android.content.DialogInterface;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.Handler;
import android.os.Looper;
import android.widget.Toast;
import androidx.annotation.Nullable;
import androidx.annotation.OptIn;
import androidx.annotation.RequiresApi;
import androidx.fragment.app.FragmentManager;
import androidx.media3.common.C;
import androidx.media3.common.DrmInitData;
@ -54,6 +55,9 @@ import java.io.IOException;
import java.util.HashMap;
import java.util.UUID;
import java.util.concurrent.CopyOnWriteArraySet;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
/** Tracks media that has been downloaded. */
@OptIn(markerClass = androidx.media3.common.util.UnstableApi.class)
@ -182,7 +186,7 @@ public class DownloadTracker {
trackSelectionDialog.dismiss();
}
if (widevineOfflineLicenseFetchTask != null) {
widevineOfflineLicenseFetchTask.cancel(false);
widevineOfflineLicenseFetchTask.cancel();
}
}
@ -197,12 +201,7 @@ public class DownloadTracker {
}
// The content is DRM protected. We need to acquire an offline license.
if (Util.SDK_INT < 18) {
Toast.makeText(context, R.string.error_drm_unsupported_before_api_18, Toast.LENGTH_LONG)
.show();
Log.e(TAG, "Downloading DRM protected content is not supported on API versions below 18");
return;
}
// TODO(internal b/163107948): Support cases where DrmInitData are not in the manifest.
if (!hasNonNullWidevineSchemaData(format.drmInitData)) {
Toast.makeText(context, R.string.download_start_error_offline_license, Toast.LENGTH_LONG)
@ -357,15 +356,16 @@ public class DownloadTracker {
}
/** Downloads a Widevine offline license in a background thread. */
@RequiresApi(18)
private static final class WidevineOfflineLicenseFetchTask extends AsyncTask<Void, Void, Void> {
private static final class WidevineOfflineLicenseFetchTask {
private final Format format;
private final MediaItem.DrmConfiguration drmConfiguration;
private final DataSource.Factory dataSourceFactory;
private final StartDownloadDialogHelper dialogHelper;
private final DownloadHelper downloadHelper;
private final ExecutorService executorService;
@Nullable Future<?> future;
@Nullable private byte[] keySetId;
@Nullable private DrmSession.DrmSessionException drmSessionException;
@ -375,6 +375,8 @@ public class DownloadTracker {
DataSource.Factory dataSourceFactory,
StartDownloadDialogHelper dialogHelper,
DownloadHelper downloadHelper) {
checkState(drmConfiguration.scheme.equals(C.WIDEVINE_UUID));
this.executorService = Executors.newSingleThreadExecutor();
this.format = format;
this.drmConfiguration = drmConfiguration;
this.dataSourceFactory = dataSourceFactory;
@ -382,32 +384,41 @@ public class DownloadTracker {
this.downloadHelper = downloadHelper;
}
@Override
protected Void doInBackground(Void... voids) {
OfflineLicenseHelper offlineLicenseHelper =
OfflineLicenseHelper.newWidevineInstance(
drmConfiguration.licenseUri.toString(),
drmConfiguration.forceDefaultLicenseUri,
dataSourceFactory,
drmConfiguration.licenseRequestHeaders,
new DrmSessionEventListener.EventDispatcher());
try {
keySetId = offlineLicenseHelper.downloadLicense(format);
} catch (DrmSession.DrmSessionException e) {
drmSessionException = e;
} finally {
offlineLicenseHelper.release();
public void cancel() {
if (future != null) {
future.cancel(/* mayInterruptIfRunning= */ false);
}
return null;
}
@Override
protected void onPostExecute(Void aVoid) {
if (drmSessionException != null) {
dialogHelper.onOfflineLicenseFetchedError(drmSessionException);
} else {
dialogHelper.onOfflineLicenseFetched(downloadHelper, checkNotNull(keySetId));
}
public void execute() {
future =
executorService.submit(
() -> {
OfflineLicenseHelper offlineLicenseHelper =
OfflineLicenseHelper.newWidevineInstance(
drmConfiguration.licenseUri.toString(),
drmConfiguration.forceDefaultLicenseUri,
dataSourceFactory,
drmConfiguration.licenseRequestHeaders,
new DrmSessionEventListener.EventDispatcher());
try {
keySetId = offlineLicenseHelper.downloadLicense(format);
} catch (DrmSession.DrmSessionException e) {
drmSessionException = e;
} finally {
offlineLicenseHelper.release();
new Handler(Looper.getMainLooper())
.post(
() -> {
if (drmSessionException != null) {
dialogHelper.onOfflineLicenseFetchedError(drmSessionException);
} else {
dialogHelper.onOfflineLicenseFetched(
downloadHelper, checkNotNull(keySetId));
}
});
}
});
}
}
}

View file

@ -22,11 +22,14 @@ import static com.google.common.base.Preconditions.checkState;
import android.content.Intent;
import android.net.Uri;
import androidx.annotation.Nullable;
import androidx.annotation.OptIn;
import androidx.media3.common.C;
import androidx.media3.common.MediaItem;
import androidx.media3.common.MediaItem.ClippingConfiguration;
import androidx.media3.common.MediaItem.SubtitleConfiguration;
import androidx.media3.common.MediaMetadata;
import androidx.media3.common.Player;
import androidx.media3.common.util.UnstableApi;
import androidx.media3.common.util.Util;
import com.google.common.collect.ImmutableList;
import java.util.ArrayList;
@ -53,6 +56,7 @@ public class IntentUtil {
public static final String MIME_TYPE_EXTRA = "mime_type";
public static final String CLIP_START_POSITION_MS_EXTRA = "clip_start_position_ms";
public static final String CLIP_END_POSITION_MS_EXTRA = "clip_end_position_ms";
public static final String IMAGE_DURATION_MS = "image_duration_ms";
public static final String AD_TAG_URI_EXTRA = "ad_tag_uri";
@ -66,6 +70,21 @@ public class IntentUtil {
public static final String SUBTITLE_URI_EXTRA = "subtitle_uri";
public static final String SUBTITLE_MIME_TYPE_EXTRA = "subtitle_mime_type";
public static final String SUBTITLE_LANGUAGE_EXTRA = "subtitle_language";
public static final String REPEAT_MODE_EXTRA = "repeat_mode";
public static @Player.RepeatMode int parseRepeatModeExtra(String repeatMode) {
switch (repeatMode) {
case "OFF":
return Player.REPEAT_MODE_OFF;
case "ONE":
return Player.REPEAT_MODE_ONE;
case "ALL":
return Player.REPEAT_MODE_ALL;
default:
throw new IllegalArgumentException(
"Argument " + repeatMode + " does not match any of the repeat modes: OFF|ONE|ALL");
}
}
/** Creates a list of {@link MediaItem media items} from an {@link Intent}. */
public static List<MediaItem> createMediaItemsFromIntent(Intent intent) {
@ -114,6 +133,7 @@ public class IntentUtil {
}
}
@OptIn(markerClass = UnstableApi.class) // Setting image duration.
private static MediaItem createMediaItemFromIntent(
Uri uri, Intent intent, String extrasKeySuffix) {
@Nullable String mimeType = intent.getStringExtra(MIME_TYPE_EXTRA + extrasKeySuffix);
@ -122,6 +142,7 @@ public class IntentUtil {
@Nullable
SubtitleConfiguration subtitleConfiguration =
createSubtitleConfiguration(intent, extrasKeySuffix);
long imageDurationMs = intent.getLongExtra(IMAGE_DURATION_MS + extrasKeySuffix, C.TIME_UNSET);
MediaItem.Builder builder =
new MediaItem.Builder()
.setUri(uri)
@ -134,7 +155,8 @@ public class IntentUtil {
.setEndPositionMs(
intent.getLongExtra(
CLIP_END_POSITION_MS_EXTRA + extrasKeySuffix, C.TIME_END_OF_SOURCE))
.build());
.build())
.setImageDurationMs(imageDurationMs);
if (adTagUri != null) {
builder.setAdsConfiguration(
new MediaItem.AdsConfiguration.Builder(Uri.parse(adTagUri)).build());
@ -195,6 +217,7 @@ public class IntentUtil {
return builder;
}
@OptIn(markerClass = UnstableApi.class) // Accessing image duration.
private static void addLocalConfigurationToIntent(
MediaItem.LocalConfiguration localConfiguration, Intent intent, String extrasKeySuffix) {
intent
@ -215,6 +238,9 @@ public class IntentUtil {
intent.putExtra(SUBTITLE_MIME_TYPE_EXTRA + extrasKeySuffix, subtitleConfiguration.mimeType);
intent.putExtra(SUBTITLE_LANGUAGE_EXTRA + extrasKeySuffix, subtitleConfiguration.language);
}
if (localConfiguration.imageDurationMs != C.TIME_UNSET) {
intent.putExtra(IMAGE_DURATION_MS + extrasKeySuffix, localConfiguration.imageDurationMs);
}
}
private static void addDrmConfigurationToIntent(

View file

@ -93,9 +93,6 @@ public class PlayerActivity extends AppCompatActivity
@Nullable private AdsLoader clientSideAdsLoader;
// TODO: Annotate this and serverSideAdsLoaderState below with @OptIn when it can be applied to
// fields (needs http://r.android.com/2004032 to be released into a version of
// androidx.annotation:annotation-experimental).
@Nullable private ImaServerSideAdInsertionMediaSource.AdsLoader serverSideAdsLoader;
private ImaServerSideAdInsertionMediaSource.AdsLoader.@MonotonicNonNull State
@ -262,8 +259,8 @@ public class PlayerActivity extends AppCompatActivity
* @return Whether initialization was successful.
*/
protected boolean initializePlayer() {
Intent intent = getIntent();
if (player == null) {
Intent intent = getIntent();
mediaItems = createMediaItems(intent);
if (mediaItems.isEmpty()) {
@ -293,11 +290,15 @@ public class PlayerActivity extends AppCompatActivity
}
player.setMediaItems(mediaItems, /* resetPosition= */ !haveStartPosition);
player.prepare();
String repeatModeExtra = intent.getStringExtra(IntentUtil.REPEAT_MODE_EXTRA);
if (repeatModeExtra != null) {
player.setRepeatMode(IntentUtil.parseRepeatModeExtra(repeatModeExtra));
}
updateButtonVisibility();
return true;
}
@OptIn(markerClass = UnstableApi.class) // SSAI configuration
@OptIn(markerClass = UnstableApi.class) // DRM configuration
private MediaSource.Factory createMediaSourceFactory() {
DefaultDrmSessionManagerProvider drmSessionManagerProvider =
new DefaultDrmSessionManagerProvider();
@ -330,7 +331,6 @@ public class PlayerActivity extends AppCompatActivity
playerBuilder.setRenderersFactory(renderersFactory);
}
@OptIn(markerClass = UnstableApi.class)
private void configurePlayerWithServerSideAdsLoader() {
serverSideAdsLoader.setPlayer(player);
}
@ -361,11 +361,7 @@ public class PlayerActivity extends AppCompatActivity
MediaItem.DrmConfiguration drmConfiguration = mediaItem.localConfiguration.drmConfiguration;
if (drmConfiguration != null) {
if (Build.VERSION.SDK_INT < 18) {
showToast(R.string.error_drm_unsupported_before_api_18);
finish();
return Collections.emptyList();
} else if (!FrameworkMediaDrm.isCryptoSchemeSupported(drmConfiguration.scheme)) {
if (!FrameworkMediaDrm.isCryptoSchemeSupported(drmConfiguration.scheme)) {
showToast(R.string.error_drm_unsupported_scheme);
finish();
return Collections.emptyList();
@ -403,7 +399,6 @@ public class PlayerActivity extends AppCompatActivity
}
}
@OptIn(markerClass = UnstableApi.class)
private void releaseServerSideAdsLoader() {
serverSideAdsLoaderState = serverSideAdsLoader.release();
serverSideAdsLoader = null;
@ -417,20 +412,17 @@ public class PlayerActivity extends AppCompatActivity
}
}
@OptIn(markerClass = UnstableApi.class)
private void saveServerSideAdsLoaderState(Bundle outState) {
if (serverSideAdsLoaderState != null) {
outState.putBundle(KEY_SERVER_SIDE_ADS_LOADER_STATE, serverSideAdsLoaderState.toBundle());
}
}
@OptIn(markerClass = UnstableApi.class)
private void restoreServerSideAdsLoaderState(Bundle savedInstanceState) {
Bundle adsLoaderStateBundle = savedInstanceState.getBundle(KEY_SERVER_SIDE_ADS_LOADER_STATE);
if (adsLoaderStateBundle != null) {
serverSideAdsLoaderState =
ImaServerSideAdInsertionMediaSource.AdsLoader.State.CREATOR.fromBundle(
adsLoaderStateBundle);
ImaServerSideAdInsertionMediaSource.AdsLoader.State.fromBundle(adsLoaderStateBundle);
}
}
@ -514,7 +506,7 @@ public class PlayerActivity extends AppCompatActivity
private class PlayerErrorMessageProvider implements ErrorMessageProvider<PlaybackException> {
@OptIn(markerClass = androidx.media3.common.util.UnstableApi.class)
@OptIn(markerClass = UnstableApi.class) // Using decoder exceptions
@Override
public Pair<Integer, String> getErrorMessage(PlaybackException e) {
String errorString = getString(R.string.error_generic);
@ -555,7 +547,7 @@ public class PlayerActivity extends AppCompatActivity
return mediaItems;
}
@OptIn(markerClass = androidx.media3.common.util.UnstableApi.class)
@OptIn(markerClass = UnstableApi.class) // Using Download API
private static MediaItem maybeSetDownloadProperties(
MediaItem item, @Nullable DownloadRequest downloadRequest) {
if (downloadRequest == null) {

View file

@ -26,11 +26,13 @@ import android.content.SharedPreferences;
import android.content.pm.PackageManager;
import android.content.res.AssetManager;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.Build;
import android.os.Bundle;
import android.os.Handler;
import android.os.Looper;
import android.text.TextUtils;
import android.util.JsonReader;
import android.util.Log;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
@ -43,15 +45,15 @@ import android.widget.ExpandableListView.OnChildClickListener;
import android.widget.ImageButton;
import android.widget.TextView;
import android.widget.Toast;
import androidx.annotation.DoNotInline;
import androidx.annotation.Nullable;
import androidx.annotation.OptIn;
import androidx.annotation.RequiresApi;
import androidx.appcompat.app.AppCompatActivity;
import androidx.media3.common.C;
import androidx.media3.common.MediaItem;
import androidx.media3.common.MediaItem.ClippingConfiguration;
import androidx.media3.common.MediaMetadata;
import androidx.media3.common.util.Log;
import androidx.media3.common.util.UnstableApi;
import androidx.media3.common.util.Util;
import androidx.media3.datasource.DataSource;
import androidx.media3.datasource.DataSourceInputStream;
@ -65,6 +67,7 @@ import com.google.common.collect.ImmutableMap;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collections;
@ -72,6 +75,8 @@ import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.UUID;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
/** An activity for selecting from a list of media samples. */
public class SampleChooserActivity extends AppCompatActivity
@ -114,6 +119,7 @@ public class SampleChooserActivity extends AppCompatActivity
}
}
} catch (IOException e) {
Log.e(TAG, "One or more sample lists failed to load", e);
Toast.makeText(getApplicationContext(), R.string.sample_list_load_error, Toast.LENGTH_LONG)
.show();
}
@ -254,6 +260,7 @@ public class SampleChooserActivity extends AppCompatActivity
}
}
@OptIn(markerClass = androidx.media3.common.util.UnstableApi.class)
private void toggleDownload(MediaItem mediaItem) {
RenderersFactory renderersFactory =
DemoUtil.buildRenderersFactory(
@ -270,6 +277,10 @@ public class SampleChooserActivity extends AppCompatActivity
if (localConfiguration.adsConfiguration != null) {
return R.string.download_ads_unsupported;
}
@Nullable MediaItem.DrmConfiguration drmConfiguration = localConfiguration.drmConfiguration;
if (drmConfiguration != null && !drmConfiguration.scheme.equals(C.WIDEVINE_UUID)) {
return R.string.download_only_widevine_drm_supported;
}
String scheme = localConfiguration.uri.getScheme();
if (!("http".equals(scheme) || "https".equals(scheme))) {
return R.string.download_scheme_unsupported;
@ -282,34 +293,43 @@ public class SampleChooserActivity extends AppCompatActivity
return menuItem != null && menuItem.isChecked();
}
private final class SampleListLoader extends AsyncTask<String, Void, List<PlaylistGroup>> {
private final class SampleListLoader {
private final ExecutorService executorService;
private boolean sawError;
@OptIn(markerClass = androidx.media3.common.util.UnstableApi.class)
@Override
protected List<PlaylistGroup> doInBackground(String... uris) {
List<PlaylistGroup> result = new ArrayList<>();
Context context = getApplicationContext();
DataSource dataSource = DemoUtil.getDataSourceFactory(context).createDataSource();
for (String uri : uris) {
DataSpec dataSpec = new DataSpec(Uri.parse(uri));
InputStream inputStream = new DataSourceInputStream(dataSource, dataSpec);
try {
readPlaylistGroups(new JsonReader(new InputStreamReader(inputStream, "UTF-8")), result);
} catch (Exception e) {
Log.e(TAG, "Error loading sample list: " + uri, e);
sawError = true;
} finally {
DataSourceUtil.closeQuietly(dataSource);
}
}
return result;
public SampleListLoader() {
executorService = Executors.newSingleThreadExecutor();
}
@Override
protected void onPostExecute(List<PlaylistGroup> result) {
onPlaylistGroups(result, sawError);
@OptIn(markerClass = androidx.media3.common.util.UnstableApi.class)
public void execute(String... uris) {
executorService.execute(
() -> {
List<PlaylistGroup> result = new ArrayList<>();
Context context = getApplicationContext();
DataSource dataSource = DemoUtil.getDataSourceFactory(context).createDataSource();
for (String uri : uris) {
DataSpec dataSpec = new DataSpec(Uri.parse(uri));
InputStream inputStream = new DataSourceInputStream(dataSource, dataSpec);
try {
readPlaylistGroups(
new JsonReader(new InputStreamReader(inputStream, StandardCharsets.UTF_8)),
result);
} catch (Exception e) {
Log.e(TAG, "Error loading sample list: " + uri, e);
sawError = true;
} finally {
DataSourceUtil.closeQuietly(dataSource);
}
}
new Handler(Looper.getMainLooper())
.post(
() -> {
onPlaylistGroups(result, sawError);
});
});
}
private void readPlaylistGroups(JsonReader reader, List<PlaylistGroup> groups)
@ -353,6 +373,7 @@ public class SampleChooserActivity extends AppCompatActivity
group.playlists.addAll(playlistHolders);
}
@OptIn(markerClass = UnstableApi.class) // Setting image duration.
private PlaylistHolder readEntry(JsonReader reader, boolean insidePlaylist) throws IOException {
Uri uri = null;
String extension = null;
@ -390,6 +411,9 @@ public class SampleChooserActivity extends AppCompatActivity
case "clip_end_position_ms":
clippingConfiguration.setEndPositionMs(reader.nextLong());
break;
case "image_duration_ms":
mediaItem.setImageDurationMs(reader.nextLong());
break;
case "ad_tag_uri":
mediaItem.setAdsConfiguration(
new MediaItem.AdsConfiguration.Builder(Uri.parse(reader.nextString())).build());
@ -642,7 +666,6 @@ public class SampleChooserActivity extends AppCompatActivity
@RequiresApi(33)
private static class Api33 {
@DoNotInline
public static String getPostNotificationPermissionString() {
return Manifest.permission.POST_NOTIFICATIONS;
}

View file

@ -67,7 +67,8 @@ public final class TrackSelectionDialog extends DialogFragment {
}
public static final ImmutableList<Integer> SUPPORTED_TRACK_TYPES =
ImmutableList.of(C.TRACK_TYPE_VIDEO, C.TRACK_TYPE_AUDIO, C.TRACK_TYPE_TEXT);
ImmutableList.of(
C.TRACK_TYPE_VIDEO, C.TRACK_TYPE_AUDIO, C.TRACK_TYPE_TEXT, C.TRACK_TYPE_IMAGE);
private final SparseArray<TrackSelectionViewFragment> tabFragments;
private final ArrayList<Integer> tabTrackTypes;
@ -266,11 +267,13 @@ public final class TrackSelectionDialog extends DialogFragment {
private static String getTrackTypeString(Resources resources, @C.TrackType int trackType) {
switch (trackType) {
case C.TRACK_TYPE_VIDEO:
return resources.getString(R.string.exo_track_selection_title_video);
return resources.getString(R.string.track_selection_title_video);
case C.TRACK_TYPE_AUDIO:
return resources.getString(R.string.exo_track_selection_title_audio);
return resources.getString(R.string.track_selection_title_audio);
case C.TRACK_TYPE_TEXT:
return resources.getString(R.string.exo_track_selection_title_text);
return resources.getString(R.string.track_selection_title_text);
case C.TRACK_TYPE_IMAGE:
return resources.getString(R.string.track_selection_title_image);
default:
throw new IllegalArgumentException();
}

View file

@ -25,8 +25,6 @@
<string name="error_generic">Playback failed</string>
<string name="error_drm_unsupported_before_api_18">DRM content not supported on API levels below 18</string>
<string name="error_drm_unsupported_scheme">This device does not support the required DRM scheme</string>
<string name="error_no_decoder">This device does not provide a decoder for <xliff:g id="mime_type">%1$s</xliff:g></string>
@ -59,6 +57,16 @@
<string name="download_ads_unsupported">IMA does not support offline ads</string>
<string name="download_only_widevine_drm_supported">This demo app only supports downloading unencrypted or Widevine DRM content</string>
<string name="prefer_extension_decoders">Prefer extension decoders</string>
<string name="track_selection_title_video">Video</string>
<string name="track_selection_title_audio">Audio</string>
<string name="track_selection_title_text">Text</string>
<string name="track_selection_title_image">Image</string>
</resources>

View file

@ -18,7 +18,7 @@ apply plugin: 'kotlin-android'
android {
namespace 'androidx.media3.demo.session'
compileSdkVersion project.ext.compileSdkVersion
compileSdk project.ext.compileSdkVersion
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
@ -34,7 +34,6 @@ android {
versionCode project.ext.releaseVersionCode
minSdkVersion project.ext.minSdkVersion
targetSdkVersion project.ext.appTargetSdkVersion
multiDexEnabled true
}
buildTypes {
@ -60,14 +59,14 @@ android {
dependencies {
// For detecting and debugging leaks only. LeakCanary is not needed for demo app to work.
debugImplementation 'com.squareup.leakcanary:leakcanary-android:2.10'
debugImplementation 'com.squareup.leakcanary:leakcanary-android:' + leakCanaryVersion
implementation 'androidx.core:core-ktx:' + androidxCoreVersion
implementation 'androidx.lifecycle:lifecycle-common:' + androidxLifecycleVersion
implementation 'androidx.lifecycle:lifecycle-runtime-ktx:' + androidxLifecycleVersion
implementation 'androidx.appcompat:appcompat:' + androidxAppCompatVersion
implementation 'androidx.multidex:multidex:' + androidxMultidexVersion
implementation 'com.google.android.material:material:' + androidxMaterialVersion
implementation project(modulePrefix + 'lib-exoplayer')
implementation project(modulePrefix + 'lib-exoplayer-dash')
implementation project(modulePrefix + 'lib-exoplayer-hls')
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-guava:' + kotlinxCoroutinesVersion
implementation project(modulePrefix + 'lib-ui')
implementation project(modulePrefix + 'lib-session')
implementation project(modulePrefix + 'demo-session-service')
}

View file

@ -14,7 +14,6 @@
limitations under the License.
-->
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
package="androidx.media3.demo.session">
<uses-sdk/>
@ -23,12 +22,15 @@
<uses-permission android:name="android.permission.FOREGROUND_SERVICE_MEDIA_PLAYBACK" />
<application
android:name="androidx.multidex.MultiDexApplication"
android:allowBackup="false"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:theme="@style/Theme.Media3Demo"
tools:replace="android:name">
android:theme="@style/Theme.Media3Demo">
<!-- Declare that this session demo supports Android Auto. -->
<meta-data
android:name="com.google.android.gms.car.application"
android:resource="@xml/auto_app_desc" />
<activity
android:name=".MainActivity"
@ -54,8 +56,9 @@
android:foregroundServiceType="mediaPlayback"
android:exported="true">
<intent-filter>
<action android:name="androidx.media3.session.MediaSessionService"/>
<action android:name="androidx.media3.session.MediaLibraryService"/>
<action android:name="android.media.browse.MediaBrowserService"/>
<action android:name="android.media.action.MEDIA_PLAY_FROM_SEARCH"/>
</intent-filter>
</service>

View file

@ -15,8 +15,11 @@
*/
package androidx.media3.demo.session
import android.Manifest
import android.content.ComponentName
import android.content.Context
import android.content.pm.PackageManager
import android.os.Build
import android.os.Bundle
import android.view.LayoutInflater
import android.view.MenuItem
@ -25,6 +28,7 @@ import android.view.ViewGroup
import android.widget.ArrayAdapter
import android.widget.ListView
import android.widget.TextView
import android.widget.Toast
import androidx.activity.OnBackPressedCallback
import androidx.appcompat.app.AppCompatActivity
import androidx.core.content.ContextCompat
@ -81,6 +85,14 @@ class MainActivity : AppCompatActivity() {
}
}
)
if (
Build.VERSION.SDK_INT >= 33 &&
checkSelfPermission(Manifest.permission.POST_NOTIFICATIONS) !=
PackageManager.PERMISSION_GRANTED
) {
requestPermissions(arrayOf(Manifest.permission.POST_NOTIFICATIONS), /* requestCode= */ 0)
}
}
override fun onOptionsItemSelected(item: MenuItem): Boolean {
@ -101,6 +113,23 @@ class MainActivity : AppCompatActivity() {
super.onStop()
}
override fun onRequestPermissionsResult(
requestCode: Int,
permissions: Array<out String>,
grantResults: IntArray
) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults)
if (grantResults.isEmpty()) {
// Empty results are triggered if a permission is requested while another request was already
// pending and can be safely ignored in this case.
return
}
if (grantResults[0] != PackageManager.PERMISSION_GRANTED) {
Toast.makeText(applicationContext, R.string.notification_permission_denied, Toast.LENGTH_LONG)
.show()
}
}
private fun initializeBrowser() {
browserFuture =
MediaBrowser.Builder(

View file

@ -43,7 +43,7 @@ import com.google.common.util.concurrent.ListenableFuture
class PlayableFolderActivity : AppCompatActivity() {
private lateinit var browserFuture: ListenableFuture<MediaBrowser>
private val browser: MediaBrowser?
get() = if (browserFuture.isDone) browserFuture.get() else null
get() = if (browserFuture.isDone && !browserFuture.isCancelled) browserFuture.get() else null
private lateinit var mediaList: ListView
private lateinit var mediaListAdapter: PlayableMediaItemArrayAdapter
@ -88,7 +88,7 @@ class PlayableFolderActivity : AppCompatActivity() {
browser.shuffleModeEnabled = true
browser.prepare()
browser.play()
browser?.sessionActivity?.send()
browser.sessionActivity?.send()
}
findViewById<Button>(R.id.play_button).setOnClickListener {

View file

@ -1,247 +1,19 @@
/*
* Copyright 2021 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 androidx.media3.demo.session
import android.annotation.SuppressLint
import android.app.NotificationChannel
import android.app.NotificationManager
import android.app.PendingIntent
import android.app.PendingIntent.*
import android.app.TaskStackBuilder
import android.app.PendingIntent.FLAG_UPDATE_CURRENT
import android.app.PendingIntent.getActivity
import android.content.Intent
import android.os.Build
import android.os.Bundle
import androidx.annotation.OptIn
import androidx.core.app.NotificationCompat
import androidx.core.app.NotificationManagerCompat
import androidx.media3.common.AudioAttributes
import androidx.media3.common.MediaItem
import androidx.media3.common.util.UnstableApi
import androidx.media3.datasource.DataSourceBitmapLoader
import androidx.media3.exoplayer.ExoPlayer
import androidx.media3.session.*
import androidx.media3.session.LibraryResult.RESULT_ERROR_NOT_SUPPORTED
import androidx.media3.session.MediaSession.ConnectionResult
import androidx.media3.session.MediaSession.ControllerInfo
import com.google.common.collect.ImmutableList
import com.google.common.util.concurrent.Futures
import com.google.common.util.concurrent.ListenableFuture
import androidx.core.app.TaskStackBuilder
class PlaybackService : MediaLibraryService() {
private val librarySessionCallback = CustomMediaLibrarySessionCallback()
private lateinit var player: ExoPlayer
private lateinit var mediaLibrarySession: MediaLibrarySession
private lateinit var customCommands: List<CommandButton>
class PlaybackService : DemoPlaybackService() {
companion object {
private const val SEARCH_QUERY_PREFIX_COMPAT = "androidx://media3-session/playFromSearch"
private const val SEARCH_QUERY_PREFIX = "androidx://media3-session/setMediaUri"
private const val CUSTOM_COMMAND_TOGGLE_SHUFFLE_MODE_ON =
"android.media3.session.demo.SHUFFLE_ON"
private const val CUSTOM_COMMAND_TOGGLE_SHUFFLE_MODE_OFF =
"android.media3.session.demo.SHUFFLE_OFF"
private const val NOTIFICATION_ID = 123
private const val CHANNEL_ID = "demo_session_notification_channel_id"
private val immutableFlag = if (Build.VERSION.SDK_INT >= 23) FLAG_IMMUTABLE else 0
private val immutableFlag = if (Build.VERSION.SDK_INT >= 23) PendingIntent.FLAG_IMMUTABLE else 0
}
@OptIn(UnstableApi::class) // MediaSessionService.setListener
override fun onCreate() {
super.onCreate()
customCommands =
listOf(
getShuffleCommandButton(
SessionCommand(CUSTOM_COMMAND_TOGGLE_SHUFFLE_MODE_ON, Bundle.EMPTY)
),
getShuffleCommandButton(
SessionCommand(CUSTOM_COMMAND_TOGGLE_SHUFFLE_MODE_OFF, Bundle.EMPTY)
)
)
initializeSessionAndPlayer()
setListener(MediaSessionServiceListener())
}
override fun onGetSession(controllerInfo: ControllerInfo): MediaLibrarySession {
return mediaLibrarySession
}
override fun onTaskRemoved(rootIntent: Intent?) {
if (!player.playWhenReady || player.mediaItemCount == 0) {
stopSelf()
}
}
// MediaSession.setSessionActivity
// MediaSessionService.clearListener
@OptIn(UnstableApi::class)
override fun onDestroy() {
mediaLibrarySession.setSessionActivity(getBackStackedActivity())
mediaLibrarySession.release()
player.release()
clearListener()
super.onDestroy()
}
private inner class CustomMediaLibrarySessionCallback : MediaLibrarySession.Callback {
// ConnectionResult.DEFAULT_SESSION_AND_LIBRARY_COMMANDS
// ConnectionResult.AcceptedResultBuilder
@OptIn(UnstableApi::class)
override fun onConnect(session: MediaSession, controller: ControllerInfo): ConnectionResult {
val availableSessionCommands =
ConnectionResult.DEFAULT_SESSION_AND_LIBRARY_COMMANDS.buildUpon()
for (commandButton in customCommands) {
// Add custom command to available session commands.
commandButton.sessionCommand?.let { availableSessionCommands.add(it) }
}
return ConnectionResult.AcceptedResultBuilder(session)
.setAvailableSessionCommands(availableSessionCommands.build())
.build()
}
override fun onCustomCommand(
session: MediaSession,
controller: ControllerInfo,
customCommand: SessionCommand,
args: Bundle
): ListenableFuture<SessionResult> {
if (CUSTOM_COMMAND_TOGGLE_SHUFFLE_MODE_ON == customCommand.customAction) {
// Enable shuffling.
player.shuffleModeEnabled = true
// Change the custom layout to contain the `Disable shuffling` command.
session.setCustomLayout(ImmutableList.of(customCommands[1]))
} else if (CUSTOM_COMMAND_TOGGLE_SHUFFLE_MODE_OFF == customCommand.customAction) {
// Disable shuffling.
player.shuffleModeEnabled = false
// Change the custom layout to contain the `Enable shuffling` command.
session.setCustomLayout(ImmutableList.of(customCommands[0]))
}
return Futures.immediateFuture(SessionResult(SessionResult.RESULT_SUCCESS))
}
override fun onGetLibraryRoot(
session: MediaLibrarySession,
browser: ControllerInfo,
params: LibraryParams?
): ListenableFuture<LibraryResult<MediaItem>> {
if (params != null && params.isRecent) {
// The service currently does not support playback resumption. Tell System UI by returning
// an error of type 'RESULT_ERROR_NOT_SUPPORTED' for a `params.isRecent` request. See
// https://github.com/androidx/media/issues/355
return Futures.immediateFuture(LibraryResult.ofError(RESULT_ERROR_NOT_SUPPORTED))
}
return Futures.immediateFuture(LibraryResult.ofItem(MediaItemTree.getRootItem(), params))
}
override fun onGetItem(
session: MediaLibrarySession,
browser: ControllerInfo,
mediaId: String
): ListenableFuture<LibraryResult<MediaItem>> {
val item =
MediaItemTree.getItem(mediaId)
?: return Futures.immediateFuture(
LibraryResult.ofError(LibraryResult.RESULT_ERROR_BAD_VALUE)
)
return Futures.immediateFuture(LibraryResult.ofItem(item, /* params= */ null))
}
override fun onSubscribe(
session: MediaLibrarySession,
browser: ControllerInfo,
parentId: String,
params: LibraryParams?
): ListenableFuture<LibraryResult<Void>> {
val children =
MediaItemTree.getChildren(parentId)
?: return Futures.immediateFuture(
LibraryResult.ofError(LibraryResult.RESULT_ERROR_BAD_VALUE)
)
session.notifyChildrenChanged(browser, parentId, children.size, params)
return Futures.immediateFuture(LibraryResult.ofVoid())
}
override fun onGetChildren(
session: MediaLibrarySession,
browser: ControllerInfo,
parentId: String,
page: Int,
pageSize: Int,
params: LibraryParams?
): ListenableFuture<LibraryResult<ImmutableList<MediaItem>>> {
val children =
MediaItemTree.getChildren(parentId)
?: return Futures.immediateFuture(
LibraryResult.ofError(LibraryResult.RESULT_ERROR_BAD_VALUE)
)
return Futures.immediateFuture(LibraryResult.ofItemList(children, params))
}
override fun onAddMediaItems(
mediaSession: MediaSession,
controller: MediaSession.ControllerInfo,
mediaItems: List<MediaItem>
): ListenableFuture<List<MediaItem>> {
val updatedMediaItems: List<MediaItem> =
mediaItems.map { mediaItem ->
if (mediaItem.requestMetadata.searchQuery != null)
getMediaItemFromSearchQuery(mediaItem.requestMetadata.searchQuery!!)
else MediaItemTree.getItem(mediaItem.mediaId) ?: mediaItem
}
return Futures.immediateFuture(updatedMediaItems)
}
private fun getMediaItemFromSearchQuery(query: String): MediaItem {
// Only accept query with pattern "play [Title]" or "[Title]"
// Where [Title]: must be exactly matched
// If no media with exact name found, play a random media instead
val mediaTitle =
if (query.startsWith("play ", ignoreCase = true)) {
query.drop(5)
} else {
query
}
return MediaItemTree.getItemFromTitle(mediaTitle) ?: MediaItemTree.getRandomItem()
}
}
private fun initializeSessionAndPlayer() {
player =
ExoPlayer.Builder(this)
.setAudioAttributes(AudioAttributes.DEFAULT, /* handleAudioFocus= */ true)
.build()
MediaItemTree.initialize(assets)
// MediaLibrarySession.Builder.setCustomLayout
// MediaLibrarySession.Builder.setBitmapLoader
// CacheBitmapLoader
// DataSourceBitmapLoader
@OptIn(UnstableApi::class)
mediaLibrarySession =
MediaLibrarySession.Builder(this, player, librarySessionCallback)
.setSessionActivity(getSingleTopActivity())
.setCustomLayout(ImmutableList.of(customCommands[0]))
.setBitmapLoader(CacheBitmapLoader(DataSourceBitmapLoader(/* context= */ this)))
.build()
}
private fun getSingleTopActivity(): PendingIntent {
override fun getSingleTopActivity(): PendingIntent? {
return getActivity(
this,
0,
@ -250,77 +22,11 @@ class PlaybackService : MediaLibraryService() {
)
}
private fun getBackStackedActivity(): PendingIntent {
override fun getBackStackedActivity(): PendingIntent? {
return TaskStackBuilder.create(this).run {
addNextIntent(Intent(this@PlaybackService, MainActivity::class.java))
addNextIntent(Intent(this@PlaybackService, PlayerActivity::class.java))
getPendingIntent(0, immutableFlag or FLAG_UPDATE_CURRENT)
}
}
private fun getShuffleCommandButton(sessionCommand: SessionCommand): CommandButton {
val isOn = sessionCommand.customAction == CUSTOM_COMMAND_TOGGLE_SHUFFLE_MODE_ON
return CommandButton.Builder()
.setDisplayName(
getString(
if (isOn) R.string.exo_controls_shuffle_on_description
else R.string.exo_controls_shuffle_off_description
)
)
.setSessionCommand(sessionCommand)
.setIconResId(if (isOn) R.drawable.exo_icon_shuffle_off else R.drawable.exo_icon_shuffle_on)
.build()
}
private fun ignoreFuture(customLayout: ListenableFuture<SessionResult>) {
/* Do nothing. */
}
@OptIn(UnstableApi::class) // MediaSessionService.Listener
private inner class MediaSessionServiceListener : Listener {
/**
* This method is only required to be implemented on Android 12 or above when an attempt is made
* by a media controller to resume playback when the {@link MediaSessionService} is in the
* background.
*/
@SuppressLint("MissingPermission") // TODO: b/280766358 - Request this permission at runtime.
override fun onForegroundServiceStartNotAllowedException() {
val notificationManagerCompat = NotificationManagerCompat.from(this@PlaybackService)
ensureNotificationChannel(notificationManagerCompat)
val pendingIntent =
TaskStackBuilder.create(this@PlaybackService).run {
addNextIntent(Intent(this@PlaybackService, MainActivity::class.java))
getPendingIntent(0, immutableFlag or FLAG_UPDATE_CURRENT)
}
val builder =
NotificationCompat.Builder(this@PlaybackService, CHANNEL_ID)
.setContentIntent(pendingIntent)
.setSmallIcon(R.drawable.media3_notification_small_icon)
.setContentTitle(getString(R.string.notification_content_title))
.setStyle(
NotificationCompat.BigTextStyle().bigText(getString(R.string.notification_content_text))
)
.setPriority(NotificationCompat.PRIORITY_DEFAULT)
.setAutoCancel(true)
notificationManagerCompat.notify(NOTIFICATION_ID, builder.build())
}
}
private fun ensureNotificationChannel(notificationManagerCompat: NotificationManagerCompat) {
if (
Build.VERSION.SDK_INT < 26 ||
notificationManagerCompat.getNotificationChannel(CHANNEL_ID) != null
) {
return
}
val channel =
NotificationChannel(
CHANNEL_ID,
getString(R.string.notification_channel_name),
NotificationManager.IMPORTANCE_DEFAULT
)
notificationManagerCompat.createNotificationChannel(channel)
}
}

View file

@ -18,6 +18,7 @@ package androidx.media3.demo.session
import android.content.ComponentName
import android.content.Context
import android.os.Bundle
import android.util.Log
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
@ -28,22 +29,30 @@ import android.widget.TextView
import androidx.annotation.OptIn
import androidx.appcompat.app.AppCompatActivity
import androidx.core.content.ContextCompat
import androidx.lifecycle.Lifecycle
import androidx.lifecycle.lifecycleScope
import androidx.lifecycle.repeatOnLifecycle
import androidx.media3.common.C.TRACK_TYPE_TEXT
import androidx.media3.common.MediaItem
import androidx.media3.common.MediaMetadata
import androidx.media3.common.Player
import androidx.media3.common.Tracks
import androidx.media3.common.Player.EVENT_MEDIA_ITEM_TRANSITION
import androidx.media3.common.Player.EVENT_MEDIA_METADATA_CHANGED
import androidx.media3.common.Player.EVENT_TIMELINE_CHANGED
import androidx.media3.common.Player.EVENT_TRACKS_CHANGED
import androidx.media3.common.util.UnstableApi
import androidx.media3.session.MediaController
import androidx.media3.session.SessionToken
import androidx.media3.ui.PlayerView
import com.google.common.util.concurrent.ListenableFuture
import com.google.common.util.concurrent.MoreExecutors
import kotlinx.coroutines.awaitCancellation
import kotlinx.coroutines.guava.await
import kotlinx.coroutines.launch
private const val TAG = "PlayerActivity"
class PlayerActivity : AppCompatActivity() {
private lateinit var controllerFuture: ListenableFuture<MediaController>
private val controller: MediaController?
get() = if (controllerFuture.isDone) controllerFuture.get() else null
private lateinit var controller: MediaController
private lateinit var playerView: PlayerView
private lateinit var mediaItemListView: ListView
@ -51,8 +60,21 @@ class PlayerActivity : AppCompatActivity() {
private val mediaItemList: MutableList<MediaItem> = mutableListOf()
private var lastMediaItemId: String? = null
@OptIn(UnstableApi::class) // PlayerView.hideController
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
lifecycleScope.launch {
lifecycle.repeatOnLifecycle(Lifecycle.State.STARTED) {
try {
initializeController()
awaitCancellation()
} finally {
playerView.player = null
releaseController()
}
}
}
setContentView(R.layout.activity_player)
playerView = findViewById(R.id.player_view)
@ -61,10 +83,8 @@ class PlayerActivity : AppCompatActivity() {
mediaItemListView.adapter = mediaItemListAdapter
mediaItemListView.setOnItemClickListener { _, _, position, _ ->
run {
val controller = this.controller ?: return@run
if (controller.currentMediaItemIndex == position) {
controller.playWhenReady = !controller.playWhenReady
@OptIn(UnstableApi::class) // PlayerView.hideController
if (controller.playWhenReady) {
playerView.hideController()
}
@ -76,25 +96,15 @@ class PlayerActivity : AppCompatActivity() {
}
}
override fun onStart() {
super.onStart()
initializeController()
}
override fun onStop() {
super.onStop()
playerView.player = null
releaseController()
}
private fun initializeController() {
private suspend fun initializeController() {
controllerFuture =
MediaController.Builder(
this,
SessionToken(this, ComponentName(this, PlaybackService::class.java))
SessionToken(this, ComponentName(this, PlaybackService::class.java)),
)
.buildAsync()
controllerFuture.addListener({ setController() }, MoreExecutors.directExecutor())
updateMediaMetadataUI()
setController()
}
private fun releaseController() {
@ -102,40 +112,58 @@ class PlayerActivity : AppCompatActivity() {
}
@OptIn(UnstableApi::class) // PlayerView.setShowSubtitleButton
private fun setController() {
val controller = this.controller ?: return
private suspend fun setController() {
try {
controller = controllerFuture.await()
} catch (t: Throwable) {
Log.w(TAG, "Failed to connect to MediaController", t)
return
}
playerView.player = controller
updateCurrentPlaylistUI()
updateMediaMetadataUI(controller.mediaMetadata)
updateMediaMetadataUI()
playerView.setShowSubtitleButton(controller.currentTracks.isTypeSupported(TRACK_TYPE_TEXT))
controller.addListener(
object : Player.Listener {
override fun onMediaItemTransition(mediaItem: MediaItem?, reason: Int) {
updateMediaMetadataUI(mediaItem?.mediaMetadata ?: MediaMetadata.EMPTY)
}
override fun onTracksChanged(tracks: Tracks) {
playerView.setShowSubtitleButton(tracks.isTypeSupported(TRACK_TYPE_TEXT))
override fun onEvents(player: Player, events: Player.Events) {
if (events.contains(EVENT_TRACKS_CHANGED)) {
playerView.setShowSubtitleButton(player.currentTracks.isTypeSupported(TRACK_TYPE_TEXT))
}
if (events.contains(EVENT_TIMELINE_CHANGED)) {
updateCurrentPlaylistUI()
}
if (events.contains(EVENT_MEDIA_METADATA_CHANGED)) {
updateMediaMetadataUI()
}
if (events.contains(EVENT_MEDIA_ITEM_TRANSITION)) {
// Trigger adapter update to change highlight of current item.
mediaItemListAdapter.notifyDataSetChanged()
}
}
}
)
}
private fun updateMediaMetadataUI(mediaMetadata: MediaMetadata) {
private fun updateMediaMetadataUI() {
if (!::controller.isInitialized || controller.mediaItemCount == 0) {
findViewById<TextView>(R.id.media_title).text = getString(R.string.waiting_for_metadata)
findViewById<TextView>(R.id.media_artist).text = ""
return
}
val mediaMetadata = controller.mediaMetadata
val title: CharSequence = mediaMetadata.title ?: ""
findViewById<TextView>(R.id.media_title).text = title
findViewById<TextView>(R.id.media_artist).text = mediaMetadata.artist
// Trick to update playlist UI
mediaItemListAdapter.notifyDataSetChanged()
}
private fun updateCurrentPlaylistUI() {
val controller = this.controller ?: return
if (!::controller.isInitialized) {
return
}
mediaItemList.clear()
for (i in 0 until controller.mediaItemCount) {
mediaItemList.add(controller.getMediaItemAt(i))
@ -146,7 +174,7 @@ class PlayerActivity : AppCompatActivity() {
private inner class MediaItemListAdapter(
context: Context,
viewID: Int,
mediaItemList: List<MediaItem>
mediaItemList: List<MediaItem>,
) : ArrayAdapter<MediaItem>(context, viewID, mediaItemList) {
override fun getView(position: Int, convertView: View?, parent: ViewGroup): View {
val mediaItem = getItem(position)!!
@ -156,7 +184,7 @@ class PlayerActivity : AppCompatActivity() {
returnConvertView.findViewById<TextView>(R.id.media_item).text = mediaItem.mediaMetadata.title
val deleteButton = returnConvertView.findViewById<Button>(R.id.delete_button)
if (position == controller?.currentMediaItemIndex) {
if (::controller.isInitialized && position == controller.currentMediaItemIndex) {
// Styles for the current media item list item.
returnConvertView.setBackgroundColor(
ContextCompat.getColor(context, R.color.playlist_item_background)
@ -175,7 +203,6 @@ class PlayerActivity : AppCompatActivity() {
.setTextColor(ContextCompat.getColor(context, R.color.white))
deleteButton.visibility = View.VISIBLE
deleteButton.setOnClickListener {
val controller = this@PlayerActivity.controller ?: return@setOnClickListener
controller.removeMediaItem(position)
updateCurrentPlaylistUI()
}

View file

@ -22,21 +22,16 @@
android:background="@color/player_background"
tools:context=".PlayerActivity">
<androidx.media3.ui.AspectRatioFrameLayout
android:layout_height="300dp"
<androidx.media3.ui.PlayerView
android:id="@+id/player_view"
android:background="@color/player_background"
android:layout_width="match_parent"
>
<androidx.media3.ui.PlayerView
android:id="@+id/player_view"
android:background="@color/player_background"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:artwork_display_mode="fill"
app:default_artwork="@drawable/artwork_placeholder"
app:repeat_toggle_modes="one|all"
app:show_shuffle_button="true"
app:shutter_background_color="@color/player_background" />
</androidx.media3.ui.AspectRatioFrameLayout>
android:layout_height="300dp"
app:artwork_display_mode="fill"
app:default_artwork="@drawable/artwork_placeholder"
app:repeat_toggle_modes="one|all"
app:show_shuffle_button="true"
app:shutter_background_color="@color/player_background" />
<TextView
android:id="@+id/media_artist"

View file

@ -13,7 +13,7 @@
See the License for the specific language governing permissions and
limitations under the License.
-->
<resources xmlns:tools="http://schemas.android.com/tools">
<resources>
<!-- Base application theme. -->
<style name="Theme.Media3Demo" parent="Theme.MaterialComponents.DayNight.DarkActionBar">
<!-- Primary brand color. -->
@ -25,9 +25,7 @@
<item name="colorSecondaryVariant">@color/teal_200</item>
<item name="colorOnSecondary">@color/black</item>
<!-- Status bar color. -->
<item name="android:statusBarColor" tools:targetApi="l">
?attr/colorPrimaryVariant
</item>
<item name="android:statusBarColor">?attr/colorPrimaryVariant</item>
<!-- Customize your theme here. -->
</style>
</resources>

View file

@ -16,17 +16,11 @@
<resources>
<string name="app_name">Media3 Session Demo</string>
<string name="current_playlist_name">Current playlist</string>
<string name="open_player_content_description">Click to view your play list</string>
<string name="open_player_content_description">Click to view your playlist</string>
<string name="added_media_item_format">Added %1$s to playlist</string>
<string name="shuffle">Shuffle</string>
<string name="repeat">Repeat</string>
<string name="play_button">Play</string>
<string name="no_item_prompt">
"! No media in the play list !\nPlease try to add more from browser"
</string>
<string name="notification_content_title">Playback cannot be resumed</string>
<string name="notification_content_text">Press on the play button on the media notification if it
is still present, otherwise please open the app to start the playback and re-connect the session
to the controller</string>
<string name="notification_channel_name">Playback cannot be resumed</string>
<string name="waiting_for_metadata">Connecting…</string>
<string name="notification_permission_denied">
"Without notification access the app can't warn about failed background operations"</string>
</resources>

View file

@ -13,7 +13,7 @@
See the License for the specific language governing permissions and
limitations under the License.
-->
<resources xmlns:tools="http://schemas.android.com/tools">
<resources>
<!-- Base application theme. -->
<style name="Theme.Media3Demo" parent="Theme.MaterialComponents.DayNight.DarkActionBar">
<!-- Primary brand color. -->
@ -25,9 +25,7 @@
<item name="colorSecondaryVariant">@color/teal_700</item>
<item name="colorOnSecondary">@color/black</item>
<!-- Status bar color. -->
<item name="android:statusBarColor" tools:targetApi="l">
?attr/colorPrimaryVariant
</item>
<item name="android:statusBarColor">?attr/colorPrimaryVariant</item>
<!-- Customize your theme here. -->
</style>
</resources>

View file

@ -0,0 +1,18 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2023 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.
-->
<automotiveApp>
<uses name="media" />
</automotiveApp>

View file

@ -0,0 +1,7 @@
# Media3 Automotive session demo
This app demonstrates use of the `MediaLibraryService` for
[Android Automotive](https://developer.android.com/training/cars/media/automotive-os).
See the [demos README](../README.md) for instructions on how to build and run
this demo.

View file

@ -0,0 +1,65 @@
// Copyright 2023 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.
apply from: '../../constants.gradle'
apply plugin: 'com.android.application'
apply plugin: 'kotlin-android'
android {
namespace 'androidx.media3.demo.session.automotive'
compileSdk project.ext.compileSdkVersion
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
kotlinOptions {
jvmTarget = '1.8'
}
defaultConfig {
versionName project.ext.releaseVersion
versionCode project.ext.releaseVersionCode
minSdkVersion project.ext.automotiveMinSdkVersion
targetSdkVersion project.ext.appTargetSdkVersion
}
buildTypes {
release {
shrinkResources true
minifyEnabled true
proguardFiles = [
getDefaultProguardFile('proguard-android-optimize.txt')
]
signingConfig signingConfigs.debug
}
debug {
jniDebuggable = true
}
}
lintOptions {
// The demo app isn't indexed, and doesn't have translations.
disable 'GoogleAppIndexingWarning','MissingTranslation'
}
}
dependencies {
implementation 'androidx.core:core-ktx:' + androidxCoreVersion
implementation 'androidx.appcompat:appcompat:' + androidxAppCompatVersion
implementation 'com.google.android.material:material:' + androidxMaterialVersion
implementation project(modulePrefix + 'lib-session')
implementation project(modulePrefix + 'demo-session-service')
}

View file

@ -0,0 +1,69 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2023 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.
-->
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="androidx.media3.demo.session.automotive">
<uses-sdk/>
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.FOREGROUND_SERVICE" />
<uses-permission android:name="android.permission.FOREGROUND_SERVICE_MEDIA_PLAYBACK" />
<uses-feature
android:name="android.hardware.type.automotive"
android:required="true" />
<uses-feature
android:name="android.hardware.wifi"
android:required="false" />
<uses-feature
android:name="android.hardware.screen.portrait"
android:required="false" />
<uses-feature
android:name="android.hardware.screen.landscape"
android:required="false" />
<meta-data android:name="com.android.automotive"
android:resource="@xml/automotive_app_desc"/>
<application
android:allowBackup="false"
android:taskAffinity=""
android:appCategory="audio"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name">
<meta-data
android:name="androidx.car.app.TintableAttributionIcon"
android:resource="@mipmap/ic_launcher" />
<service
android:name=".AutomotiveService"
android:foregroundServiceType="mediaPlayback"
android:exported="true">
<intent-filter>
<action android:name="androidx.media3.session.MediaLibraryService"/>
<action android:name="android.media.browse.MediaBrowserService"/>
</intent-filter>
</service>
<!-- Artwork provider for content:// URIs -->
<provider
android:name="BitmapContentProvider"
android:authorities="androidx.media3"
android:exported="true" />
</application>
</manifest>

Binary file not shown.

After

Width:  |  Height:  |  Size: 353 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 215 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 41 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 278 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 240 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 425 KiB

View file

@ -0,0 +1,472 @@
{
"media": [
{
"id": "wake_up_01",
"title": "Intro - The Way Of Waking Up (feat. Alan Watts)",
"album": "Wake Up",
"artist": "The Kyoto Connection",
"genre": "Electronic",
"source": "https://storage.googleapis.com/uamp/The_Kyoto_Connection_-_Wake_Up/01_-_Intro_-_The_Way_Of_Waking_Up_feat_Alan_Watts.mp3",
"image": "content://androidx.media3/artwork/album_kyoto_connection.png",
"trackNumber": 1,
"totalTrackCount": 13,
"duration": 90,
"site": "http://freemusicarchive.org/music/The_Kyoto_Connection/Wake_Up_1957/"
},
{
"id": "wake_up_02",
"title": "Geisha",
"album": "Wake Up",
"artist": "The Kyoto Connection",
"genre": "Electronic",
"source": "https://storage.googleapis.com/uamp/The_Kyoto_Connection_-_Wake_Up/02_-_Geisha.mp3",
"image": "content://androidx.media3/artwork/album_kyoto_connection.png",
"trackNumber": 2,
"totalTrackCount": 13,
"duration": 267,
"site": "http://freemusicarchive.org/music/The_Kyoto_Connection/Wake_Up_1957/"
},
{
"id": "wake_up_03",
"title": "Voyage I - Waterfall",
"album": "Wake Up",
"artist": "The Kyoto Connection",
"genre": "Electronic",
"source": "https://storage.googleapis.com/uamp/The_Kyoto_Connection_-_Wake_Up/03_-_Voyage_I_-_Waterfall.mp3",
"image": "content://androidx.media3/artwork/album_kyoto_connection.png",
"trackNumber": 3,
"totalTrackCount": 13,
"duration": 264,
"site": "http://freemusicarchive.org/music/The_Kyoto_Connection/Wake_Up_1957/"
},
{
"id": "wake_up_04",
"title": "The Music In You",
"album": "Wake Up",
"artist": "The Kyoto Connection",
"genre": "Electronic",
"source": "https://storage.googleapis.com/uamp/The_Kyoto_Connection_-_Wake_Up/04_-_The_Music_In_You.mp3",
"image": "content://androidx.media3/artwork/album_kyoto_connection.png",
"trackNumber": 4,
"totalTrackCount": 13,
"duration": 223,
"site": "http://freemusicarchive.org/music/The_Kyoto_Connection/Wake_Up_1957/"
},
{
"id": "wake_up_05",
"title": "The Calm Before The Storm",
"album": "Wake Up",
"artist": "The Kyoto Connection",
"genre": "Electronic",
"source": "https://storage.googleapis.com/uamp/The_Kyoto_Connection_-_Wake_Up/05_-_The_Calm_Before_The_Storm.mp3",
"image": "content://androidx.media3/artwork/album_kyoto_connection.png",
"trackNumber": 5,
"totalTrackCount": 13,
"duration": 229,
"site": "http://freemusicarchive.org/music/The_Kyoto_Connection/Wake_Up_1957/"
},
{
"id": "wake_up_06",
"title": "No Pain, No Gain",
"album": "Wake Up",
"artist": "The Kyoto Connection",
"genre": "Electronic",
"source": "https://storage.googleapis.com/uamp/The_Kyoto_Connection_-_Wake_Up/06_-_No_Pain_No_Gain.mp3",
"image": "content://androidx.media3/artwork/album_kyoto_connection.png",
"trackNumber": 6,
"totalTrackCount": 13,
"duration": 304,
"site": "http://freemusicarchive.org/music/The_Kyoto_Connection/Wake_Up_1957/"
},
{
"id": "wake_up_07",
"title": "Voyage II - Satori",
"album": "Wake Up",
"artist": "The Kyoto Connection",
"genre": "Electronic",
"source": "https://storage.googleapis.com/uamp/The_Kyoto_Connection_-_Wake_Up/07_-_Voyage_II_-_Satori.mp3",
"image": "content://androidx.media3/artwork/album_kyoto_connection.png",
"trackNumber": 7,
"totalTrackCount": 13,
"duration": 256,
"site": "http://freemusicarchive.org/music/The_Kyoto_Connection/Wake_Up_1957/"
},
{
"id": "wake_up_08",
"title": "Reveal the Magic",
"album": "Wake Up",
"artist": "The Kyoto Connection",
"genre": "Electronic",
"source": "https://storage.googleapis.com/uamp/The_Kyoto_Connection_-_Wake_Up/08_-_Reveal_the_Magic.mp3",
"image": "content://androidx.media3/artwork/album_kyoto_connection.png",
"trackNumber": 8,
"totalTrackCount": 13,
"duration": 293,
"site": "http://freemusicarchive.org/music/The_Kyoto_Connection/Wake_Up_1957/"
},
{
"id": "wake_up_09",
"title": "Hachiko (The Faithtful Dog)",
"album": "Wake Up",
"artist": "The Kyoto Connection",
"genre": "Electronic",
"source": "https://storage.googleapis.com/uamp/The_Kyoto_Connection_-_Wake_Up/09_-_Hachiko_The_Faithtful_Dog.mp3",
"image": "content://androidx.media3/artwork/album_kyoto_connection.png",
"trackNumber": 9,
"totalTrackCount": 13,
"duration": 185,
"site": "http://freemusicarchive.org/music/The_Kyoto_Connection/Wake_Up_1957/"
},
{
"id": "wake_up_10",
"title": "Wake Up",
"album": "Wake Up",
"artist": "The Kyoto Connection",
"genre": "Electronic",
"source": "https://storage.googleapis.com/uamp/The_Kyoto_Connection_-_Wake_Up/10_-_Wake_Up.mp3",
"image": "content://androidx.media3/artwork/album_kyoto_connection.png",
"trackNumber": 10,
"totalTrackCount": 13,
"duration": 251,
"site": "http://freemusicarchive.org/music/The_Kyoto_Connection/Wake_Up_1957/"
},
{
"id": "wake_up_11",
"title": "Voyage III - The Space Between Us",
"album": "Wake Up",
"artist": "The Kyoto Connection",
"genre": "Electronic",
"source": "https://storage.googleapis.com/uamp/The_Kyoto_Connection_-_Wake_Up/11_-_Voyage_III_-_The_Space_Between_Us.mp3",
"image": "content://androidx.media3/artwork/album_kyoto_connection.png",
"trackNumber": 11,
"totalTrackCount": 13,
"duration": 290,
"site": "http://freemusicarchive.org/music/The_Kyoto_Connection/Wake_Up_1957/"
},
{
"id": "wake_up_12",
"title": "Ume No Kaori (feat. Sunawai)",
"album": "Wake Up",
"artist": "The Kyoto Connection",
"genre": "Electronic",
"source": "https://storage.googleapis.com/uamp/The_Kyoto_Connection_-_Wake_Up/12_-_Ume_No_Kaori_feat_Sunawai.mp3",
"image": "content://androidx.media3/artwork/album_kyoto_connection.png",
"trackNumber": 12,
"totalTrackCount": 13,
"duration": 334,
"site": "http://freemusicarchive.org/music/The_Kyoto_Connection/Wake_Up_1957/"
},
{
"id": "wake_up_13",
"title": "Outro - Totally Here and Now (feat. Alan Watts)",
"album": "Wake Up",
"artist": "The Kyoto Connection",
"genre": "Electronic",
"source": "https://storage.googleapis.com/uamp/The_Kyoto_Connection_-_Wake_Up/13_-_Outro_-_Totally_Here_and_Now_feat_Alan_Watts.mp3",
"image": "content://androidx.media3/artwork/album_kyoto_connection.png",
"trackNumber": 13,
"totalTrackCount": 13,
"duration": 242,
"site": "http://freemusicarchive.org/music/The_Kyoto_Connection/Wake_Up_1957/"
},
{
"id": "irsens_tale_01",
"title": "Intro (.udonthear)",
"album": "Irsen's Tale",
"artist": "Kai Engel",
"genre": "Ambient",
"source": "https://storage.googleapis.com/uamp/Kai_Engel_-_Irsens_Tale/01_-_Intro_udonthear.mp3",
"image": "content://androidx.media3/artwork/album_kai_engel.png",
"trackNumber": 1,
"totalTrackCount": 9,
"duration": 63,
"site": "http://freemusicarchive.org/music/Kai_Engel/Irsens_Tale/"
},
{
"id": "irsens_tale_02",
"title": "Leaving",
"album": "Irsen's Tale",
"artist": "Kai Engel",
"genre": "Ambient",
"source": "https://storage.googleapis.com/uamp/Kai_Engel_-_Irsens_Tale/02_-_Leaving.mp3",
"image": "content://androidx.media3/artwork/album_kai_engel.png",
"trackNumber": 2,
"totalTrackCount": 9,
"duration": 170,
"site": "http://freemusicarchive.org/music/Kai_Engel/Irsens_Tale/"
},
{
"id": "irsens_tale_03",
"title": "Irsen's Tale",
"album": "Irsen's Tale",
"artist": "Kai Engel",
"genre": "Ambient",
"source": "https://storage.googleapis.com/uamp/Kai_Engel_-_Irsens_Tale/03_-_Irsens_Tale.mp3",
"image": "content://androidx.media3/artwork/album_kai_engel.png",
"trackNumber": 3,
"totalTrackCount": 9,
"duration": 164,
"site": "http://freemusicarchive.org/music/Kai_Engel/Irsens_Tale/"
},
{
"id": "irsens_tale_04",
"title": "Moonlight Reprise",
"album": "Irsen's Tale",
"artist": "Kai Engel",
"genre": "Ambient",
"source": "https://storage.googleapis.com/uamp/Kai_Engel_-_Irsens_Tale/04_-_Moonlight_Reprise.mp3",
"image": "content://androidx.media3/artwork/album_kai_engel.png",
"trackNumber": 4,
"totalTrackCount": 9,
"duration": 181,
"site": "http://freemusicarchive.org/music/Kai_Engel/Irsens_Tale/"
},
{
"id": "irsens_tale_05",
"title": "Nothing Lasts Forever",
"album": "Irsen's Tale",
"artist": "Kai Engel",
"genre": "Ambient",
"source": "https://storage.googleapis.com/uamp/Kai_Engel_-_Irsens_Tale/05_-_Nothing_Lasts_Forever.mp3",
"image": "content://androidx.media3/artwork/album_kai_engel.png",
"trackNumber": 5,
"totalTrackCount": 9,
"duration": 132,
"site": "http://freemusicarchive.org/music/Kai_Engel/Irsens_Tale/"
},
{
"id": "irsens_tale_06",
"title": "The Moments of Our Mornings",
"album": "Irsen's Tale",
"artist": "Kai Engel",
"genre": "Ambient",
"source": "https://storage.googleapis.com/uamp/Kai_Engel_-_Irsens_Tale/06_-_The_Moments_of_Our_Mornings.mp3",
"image": "content://androidx.media3/artwork/album_kai_engel.png",
"trackNumber": 6,
"totalTrackCount": 9,
"duration": 104,
"site": "http://freemusicarchive.org/music/Kai_Engel/Irsens_Tale/"
},
{
"id": "irsens_tale_07",
"title": "Laceration",
"album": "Irsen's Tale",
"artist": "Kai Engel",
"genre": "Ambient",
"source": "https://storage.googleapis.com/uamp/Kai_Engel_-_Irsens_Tale/07_-_Laceration.mp3",
"image": "content://androidx.media3/artwork/album_kai_engel.png",
"trackNumber": 7,
"totalTrackCount": 9,
"duration": 173,
"site": "http://freemusicarchive.org/music/Kai_Engel/Irsens_Tale/"
},
{
"id": "irsens_tale_08",
"title": "Memories",
"album": "Irsen's Tale",
"artist": "Kai Engel",
"genre": "Ambient",
"source": "https://storage.googleapis.com/uamp/Kai_Engel_-_Irsens_Tale/08_-_Memories.mp3",
"image": "content://androidx.media3/artwork/album_kai_engel.png",
"trackNumber": 8,
"totalTrackCount": 9,
"duration": 213,
"site": "http://freemusicarchive.org/music/Kai_Engel/Irsens_Tale/"
},
{
"id": "irsens_tale_09",
"title": "Outro",
"album": "Irsen's Tale",
"artist": "Kai Engel",
"genre": "Ambient",
"source": "https://storage.googleapis.com/uamp/Kai_Engel_-_Irsens_Tale/09_-_Outro.mp3",
"image": "content://androidx.media3/artwork/album_kai_engel.png",
"trackNumber": 9,
"totalTrackCount": 9,
"duration": 65,
"site": "http://freemusicarchive.org/music/Kai_Engel/Irsens_Tale/"
},
{
"id": "jazz_in_paris",
"title": "Jazz in Paris",
"album": "Jazz & Blues",
"artist": "Media Right Productions",
"genre": "Jazz & Blues",
"source": "https://storage.googleapis.com/automotive-media/Jazz_In_Paris.mp3",
"image": "content://androidx.media3/artwork/album_sea.png",
"trackNumber": 1,
"totalTrackCount": 6,
"duration": 103,
"site": "https://www.youtube.com/audiolibrary/music"
},
{
"id": "the_messenger",
"title": "The Messenger",
"album": "Jazz & Blues",
"artist": "Silent Partner",
"genre": "Jazz & Blues",
"source": "https://storage.googleapis.com/automotive-media/The_Messenger.mp3",
"image": "content://androidx.media3/artwork/album_sea.png",
"trackNumber": 2,
"totalTrackCount": 6,
"duration": 132,
"site": "https://www.youtube.com/audiolibrary/music"
},
{
"id": "talkies",
"title": "Talkies",
"album": "Jazz & Blues",
"artist": "Huma-Huma",
"genre": "Jazz & Blues",
"source": "https://storage.googleapis.com/automotive-media/Talkies.mp3",
"image": "content://androidx.media3/artwork/album_sea.png",
"trackNumber": 3,
"totalTrackCount": 6,
"duration": 162,
"site": "https://www.youtube.com/audiolibrary/music"
},
{
"id": "on_the_bach",
"title": "On the Bach",
"album": "Cinematic",
"artist": "Jingle Punks",
"genre": "Cinematic",
"source": "https://storage.googleapis.com/automotive-media/On_the_Bach.mp3",
"image": "content://androidx.media3/artwork/album_drinks.png",
"trackNumber": 4,
"totalTrackCount": 6,
"duration": 66,
"site": "https://www.youtube.com/audiolibrary/music"
},
{
"id": "the_story_unfolds",
"title": "The Story Unfolds",
"album": "Cinematic",
"artist": "Jingle Punks",
"genre": "Cinematic",
"source": "https://storage.googleapis.com/automotive-media/The_Story_Unfolds.mp3",
"image": "content://androidx.media3/artwork/album_drinks.png",
"trackNumber": 5,
"totalTrackCount": 6,
"duration": 91,
"site": "https://www.youtube.com/audiolibrary/music"
},
{
"id": "drop_and_roll",
"title": "Drop and Roll",
"album": "Youtube Audio Library Rock",
"artist": "Silent Partner",
"genre": "Rock",
"source": "https://storage.googleapis.com/automotive-media/Drop_and_Roll.mp3",
"image": "content://androidx.media3/artwork/album_road.png",
"trackNumber": 1,
"totalTrackCount": 7,
"duration": 121,
"site": "https://www.youtube.com/audiolibrary/music"
},
{
"id": "motocross",
"title": "Motocross",
"album": "Youtube Audio Library Rock",
"artist": "Topher Mohr and Alex Elena",
"genre": "Rock",
"source": "https://storage.googleapis.com/automotive-media/Motocross.mp3",
"image": "content://androidx.media3/artwork/album_road.png",
"trackNumber": 2,
"totalTrackCount": 7,
"duration": 182,
"site": "https://www.youtube.com/audiolibrary/music"
},
{
"id": "wish_youd_come_true",
"title": "Wish You'd Come True",
"album": "Youtube Audio Library Rock",
"artist": "The 126ers",
"genre": "Rock",
"source": "https://storage.googleapis.com/automotive-media/Wish_You_d_Come_True.mp3",
"image": "content://androidx.media3/artwork/album_road.png",
"trackNumber": 3,
"totalTrackCount": 7,
"duration": 169,
"site": "https://www.youtube.com/audiolibrary/music"
},
{
"id": "awakening",
"title": "Awakening",
"album": "Youtube Audio Library Rock",
"artist": "Silent Partner",
"genre": "Rock",
"source": "https://storage.googleapis.com/automotive-media/Awakening.mp3",
"image": "content://androidx.media3/artwork/album_road.png",
"trackNumber": 4,
"totalTrackCount": 7,
"duration": 220,
"site": "https://www.youtube.com/audiolibrary/music"
},
{
"id": "home",
"title": "Home",
"album": "Youtube Audio Library Rock",
"artist": "Letter Box",
"genre": "Rock",
"source": "https://storage.googleapis.com/automotive-media/Home.mp3",
"image": "content://androidx.media3/artwork/album_road.png",
"trackNumber": 5,
"totalTrackCount": 7,
"duration": 213,
"site": "https://www.youtube.com/audiolibrary/music"
},
{
"id": "tell_the_angels",
"title": "Tell The Angels",
"album": "Youtube Audio Library Rock 2",
"artist": "Letter Box",
"genre": "Rock",
"source": "https://storage.googleapis.com/automotive-media/Tell_The_Angels.mp3",
"image": "content://androidx.media3/artwork/album_skyline.png",
"trackNumber": 6,
"totalTrackCount": 7,
"duration": 208,
"site": "https://www.youtube.com/audiolibrary/music"
},
{
"id": "hey_sailor",
"title": "Hey Sailor",
"album": "Youtube Audio Library Rock 2",
"artist": "Letter Box",
"genre": "Rock",
"source": "https://storage.googleapis.com/automotive-media/Hey_Sailor.mp3",
"image": "content://androidx.media3/artwork/album_skyline.png",
"trackNumber": 7,
"totalTrackCount": 7,
"duration": 193,
"site": "https://www.youtube.com/audiolibrary/music"
},
{
"id": "keys_to_the_kingdom",
"title": "Keys To The Kingdom",
"album": "Youtube Audio Library Rock 2",
"artist": "The 126ers",
"genre": "Rock",
"source": "https://storage.googleapis.com/automotive-media/Keys_To_The_Kingdom.mp3",
"image": "content://androidx.media3/artwork/album_skyline.png",
"trackNumber": 1,
"totalTrackCount": 2,
"duration": 221,
"site": "https://www.youtube.com/audiolibrary/music"
},
{
"id": "the_coldest_shoulder",
"title": "The Coldest Shoulder",
"album": "Youtube Audio Library Rock 2",
"artist": "The 126ers",
"genre": "Rock",
"source": "https://storage.googleapis.com/automotive-media/The_Coldest_Shoulder.mp3",
"image": "content://androidx.media3/artwork/album_skyline.png",
"trackNumber": 2,
"totalTrackCount": 2,
"duration": 160,
"site": "https://www.youtube.com/audiolibrary/music"
}
]
}

View file

@ -0,0 +1,59 @@
/*
* Copyright 2023 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 androidx.media3.demo.session.automotive
import androidx.annotation.OptIn
import androidx.media3.common.MediaItem
import androidx.media3.common.util.UnstableApi
import androidx.media3.demo.session.DemoMediaLibrarySessionCallback
import androidx.media3.demo.session.DemoPlaybackService
import androidx.media3.session.LibraryResult
import androidx.media3.session.MediaConstants
import androidx.media3.session.MediaSession.ControllerInfo
import com.google.common.util.concurrent.ListenableFuture
class AutomotiveService : DemoPlaybackService() {
override fun createLibrarySessionCallback(): MediaLibrarySession.Callback {
return object : DemoMediaLibrarySessionCallback(this@AutomotiveService) {
@OptIn(UnstableApi::class)
override fun onGetLibraryRoot(
session: MediaLibrarySession,
browser: ControllerInfo,
params: LibraryParams?
): ListenableFuture<LibraryResult<MediaItem>> {
var responseParams = params
if (session.isAutomotiveController(browser)) {
// See https://developer.android.com/training/cars/media#apply_content_style
val rootHintParams = params ?: LibraryParams.Builder().build()
rootHintParams.extras.putInt(
MediaConstants.EXTRAS_KEY_CONTENT_STYLE_BROWSABLE,
MediaConstants.EXTRAS_VALUE_CONTENT_STYLE_GRID_ITEM
)
rootHintParams.extras.putInt(
MediaConstants.EXTRAS_KEY_CONTENT_STYLE_PLAYABLE,
MediaConstants.EXTRAS_VALUE_CONTENT_STYLE_LIST_ITEM
)
// Tweaked params are propagated to Automotive browsers as root hints.
responseParams = rootHintParams
}
// Use super to return the common library root with the tweaked params sent to the browser.
return super.onGetLibraryRoot(session, browser, responseParams)
}
}
}
}

View file

@ -0,0 +1,89 @@
/*
* Copyright 2023 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 androidx.media3.demo.session.automotive
import android.content.ContentProvider
import android.content.ContentValues
import android.content.Context
import android.database.Cursor
import android.net.Uri
import android.os.ParcelFileDescriptor
import java.io.File
/**
* Provides artwork for content URIs.
*
* <p>A bitmap file in the asset folder with path 'artwork/album1.png' can be referenced as artwork
* URI with 'content://androidx.media3/artwork/album1.png'. 'androidx.media3' is the authority
* declared for the content provider in 'AndroidManifest.xml'.
*
* <p>For demo use only.
*/
class BitmapContentProvider : ContentProvider() {
override fun onCreate() = true
override fun openFile(uri: Uri, mode: String): ParcelFileDescriptor? {
context?.let { ctx ->
getAssetPath(uri)?.let {
return ParcelFileDescriptor.open(
copyAssetFileToCacheDirectory(ctx, it),
ParcelFileDescriptor.MODE_READ_ONLY
)
}
}
return super.openFile(uri, mode)
}
private fun getAssetPath(contentUri: Uri): String? {
contentUri.path?.let {
return it.substring(1)
}
return null
}
private fun copyAssetFileToCacheDirectory(context: Context, assetPath: String): File {
val publicFile = File(context.cacheDir, assetPath.replace("/", "_"))
if (!publicFile.exists()) {
context.assets.open(assetPath).copyTo(publicFile.outputStream())
}
return publicFile
}
// No-op implementations of abstract ContentProvider methods.
override fun insert(uri: Uri, values: ContentValues?): Uri? = null
override fun query(
uri: Uri,
projection: Array<String>?,
selection: String?,
selectionArgs: Array<String>?,
sortOrder: String?
): Cursor? = null
override fun update(
uri: Uri,
values: ContentValues?,
selection: String?,
selectionArgs: Array<String>?
) = 0
override fun delete(uri: Uri, selection: String?, selectionArgs: Array<String>?) = 0
override fun getType(uri: Uri): String? = null
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

View file

@ -0,0 +1,18 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2023 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.
-->
<resources>
<string name="app_name">Media3 Automotive Demo</string>
</resources>

View file

@ -0,0 +1,18 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2023 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.
-->
<automotiveApp>
<uses name="media"/>
</automotiveApp>

View file

@ -0,0 +1,8 @@
# Demo `MediaLibraryService` implementation
A library module with a demo implementation of `MediaLibraryService` and
`MediaLibrarySession.Callback`.
See the `PlaybackService` of the [session demo](../session/README.md) how to use
it. Override `assets/cataglog.json` by creating such a file in the same format
in your application module that the service will use.

View file

@ -0,0 +1,61 @@
// Copyright 2023 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.
apply from: "$gradle.ext.androidxMediaSettingsDir/common_library_config.gradle"
apply plugin: 'kotlin-android'
android {
namespace 'androidx.media3.demo.session.service'
compileSdk project.ext.compileSdkVersion
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
kotlinOptions {
jvmTarget = '1.8'
}
defaultConfig {
versionName project.ext.releaseVersion
versionCode project.ext.releaseVersionCode
minSdkVersion project.ext.minSdkVersion
targetSdkVersion project.ext.appTargetSdkVersion
}
buildTypes {
release {
signingConfig signingConfigs.debug
}
debug {
jniDebuggable = true
}
}
lintOptions {
// The demo service module isn't indexed, and doesn't have translations.
disable 'GoogleAppIndexingWarning','MissingTranslation'
}
}
dependencies {
implementation 'androidx.core:core-ktx:' + androidxCoreVersion
implementation 'androidx.appcompat:appcompat:' + androidxAppCompatVersion
implementation project(modulePrefix + 'lib-exoplayer')
implementation project(modulePrefix + 'lib-exoplayer-dash')
implementation project(modulePrefix + 'lib-exoplayer-hls')
implementation project(modulePrefix + 'lib-ui')
implementation project(modulePrefix + 'lib-session')
}

View file

@ -0,0 +1,20 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright 2023 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.
-->
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="androidx.media3.demo.session.service">
<uses-sdk />
<uses-permission android:name="android.permission.POST_NOTIFICATIONS"/>
</manifest>

Some files were not shown because too many files have changed in this diff Show more