From 518fe3771acbf1e9d8c12324cfa94da4d3458686 Mon Sep 17 00:00:00 2001 From: huangdarwin Date: Mon, 20 Feb 2023 16:40:16 +0000 Subject: [PATCH] HDR: Fix ForceInterpretHdrVideoAsSdrTest, and expand to all APIs. Previously, this was limited to API 29. Expand this to all API versions. Also, update the test to: (1) skip based on SDR format input instead of HDR format input (2) Check the exception message in order to disambiguate between the decoder tone mapping error, and general video format support error. PiperOrigin-RevId: 511002218 --- .../mh/ForceInterpretHdrVideoAsSdrTest.java | 67 +++++++++++++++---- .../ExoAssetLoaderBaseRenderer.java | 2 +- .../ExoAssetLoaderVideoRenderer.java | 12 +--- .../transformer/TransformationRequest.java | 4 +- 4 files changed, 57 insertions(+), 28 deletions(-) diff --git a/libraries/transformer/src/androidTest/java/androidx/media3/transformer/mh/ForceInterpretHdrVideoAsSdrTest.java b/libraries/transformer/src/androidTest/java/androidx/media3/transformer/mh/ForceInterpretHdrVideoAsSdrTest.java index c279bc16c6..d57ae6d621 100644 --- a/libraries/transformer/src/androidTest/java/androidx/media3/transformer/mh/ForceInterpretHdrVideoAsSdrTest.java +++ b/libraries/transformer/src/androidTest/java/androidx/media3/transformer/mh/ForceInterpretHdrVideoAsSdrTest.java @@ -15,18 +15,22 @@ */ package androidx.media3.transformer.mh; +import static androidx.media3.common.util.Util.SDK_INT; import static androidx.media3.transformer.AndroidTestUtil.MP4_ASSET_1080P_4_SECOND_HDR10; import static androidx.media3.transformer.AndroidTestUtil.MP4_ASSET_1080P_4_SECOND_HDR10_FORMAT; import static androidx.media3.transformer.AndroidTestUtil.MP4_ASSET_1080P_5_SECOND_HLG10; import static androidx.media3.transformer.AndroidTestUtil.MP4_ASSET_1080P_5_SECOND_HLG10_FORMAT; +import static androidx.media3.transformer.AndroidTestUtil.recordTestSkipped; +import static androidx.media3.transformer.AndroidTestUtil.skipAndLogIfFormatsUnsupported; import static androidx.media3.transformer.mh.FileUtil.maybeAssertFileHasColorTransfer; import android.content.Context; import android.net.Uri; +import android.util.Log; import androidx.media3.common.C; +import androidx.media3.common.ColorInfo; +import androidx.media3.common.Format; import androidx.media3.common.MediaItem; -import androidx.media3.common.util.Log; -import androidx.media3.transformer.AndroidTestUtil; import androidx.media3.transformer.ExportException; import androidx.media3.transformer.ExportTestResult; import androidx.media3.transformer.TransformationRequest; @@ -51,11 +55,21 @@ public class ForceInterpretHdrVideoAsSdrTest { String testId = "forceInterpretHdrVideoAsSdrTest_hdr10File_transformsOrThrows"; Context context = ApplicationProvider.getApplicationContext(); - if (AndroidTestUtil.skipAndLogIfFormatsUnsupported( - context, - testId, - /* inputFormat= */ MP4_ASSET_1080P_4_SECOND_HDR10_FORMAT, - /* outputFormat= */ null)) { + if (SDK_INT < 29) { + // TODO(b/269759013): Fix failures under API 29 to expand confidence on all API versions. + recordTestSkipped( + context, testId, /* reason= */ "Under API 29, this API is considered best-effort."); + return; + } + + // Force interpret HDR as SDR signals SDR input to the decoder, even if the actual input is HDR. + Format decoderInputFormat = + MP4_ASSET_1080P_4_SECOND_HDR10_FORMAT + .buildUpon() + .setColorInfo(ColorInfo.SDR_BT709_LIMITED) + .build(); + if (skipAndLogIfFormatsUnsupported( + context, testId, decoderInputFormat, /* outputFormat= */ null)) { return; } @@ -76,7 +90,9 @@ public class ForceInterpretHdrVideoAsSdrTest { maybeAssertFileHasColorTransfer(exportTestResult.filePath, C.COLOR_TRANSFER_SDR); Log.i(TAG, "Transformed."); } catch (ExportException exception) { - if (exception.errorCode != ExportException.ERROR_CODE_DECODING_FORMAT_UNSUPPORTED) { + String message = getMessageOrEmptyString(exception); + Log.i(TAG, "Exception: " + message); + if (!message.equals("The requested video decoding format is not supported.")) { throw exception; } } @@ -87,11 +103,21 @@ public class ForceInterpretHdrVideoAsSdrTest { String testId = "forceInterpretHdrVideoAsSdrTest_hlg10File_transformsOrThrows"; Context context = ApplicationProvider.getApplicationContext(); - if (AndroidTestUtil.skipAndLogIfFormatsUnsupported( - context, - testId, - /* inputFormat= */ MP4_ASSET_1080P_5_SECOND_HLG10_FORMAT, - /* outputFormat= */ null)) { + if (SDK_INT < 29) { + // TODO(b/269759013): Fix failures under API 29 to expand confidence on all API versions. + recordTestSkipped( + context, testId, /* reason= */ "Under API 29, this API is considered best-effort."); + return; + } + + // Force interpret HDR as SDR signals SDR input to the decoder, even if the actual input is HDR. + Format decoderInputFormat = + MP4_ASSET_1080P_5_SECOND_HLG10_FORMAT + .buildUpon() + .setColorInfo(ColorInfo.SDR_BT709_LIMITED) + .build(); + if (skipAndLogIfFormatsUnsupported( + context, testId, decoderInputFormat, /* outputFormat= */ null)) { return; } @@ -112,9 +138,22 @@ public class ForceInterpretHdrVideoAsSdrTest { maybeAssertFileHasColorTransfer(exportTestResult.filePath, C.COLOR_TRANSFER_SDR); Log.i(TAG, "Transformed."); } catch (ExportException exception) { - if (exception.errorCode != ExportException.ERROR_CODE_DECODING_FORMAT_UNSUPPORTED) { + String message = getMessageOrEmptyString(exception); + Log.i(TAG, "Exception: " + message); + if (!message.equals("The requested video decoding format is not supported.")) { throw exception; } } } + + private String getMessageOrEmptyString(Exception exception) { + if (exception.getCause() == null) { + return ""; + } + String message = exception.getCause().getMessage(); + if (message == null) { + return ""; + } + return message; + } } diff --git a/libraries/transformer/src/main/java/androidx/media3/transformer/ExoAssetLoaderBaseRenderer.java b/libraries/transformer/src/main/java/androidx/media3/transformer/ExoAssetLoaderBaseRenderer.java index da00c98a12..a55fcef32b 100644 --- a/libraries/transformer/src/main/java/androidx/media3/transformer/ExoAssetLoaderBaseRenderer.java +++ b/libraries/transformer/src/main/java/androidx/media3/transformer/ExoAssetLoaderBaseRenderer.java @@ -136,7 +136,7 @@ import org.checkerframework.checker.nullness.qual.RequiresNonNull; } /** Overrides the {@code inputFormat}. */ - protected Format overrideFormat(Format inputFormat) throws ExportException { + protected Format overrideFormat(Format inputFormat) { return inputFormat; } diff --git a/libraries/transformer/src/main/java/androidx/media3/transformer/ExoAssetLoaderVideoRenderer.java b/libraries/transformer/src/main/java/androidx/media3/transformer/ExoAssetLoaderVideoRenderer.java index a9f7db53f6..45961e1239 100644 --- a/libraries/transformer/src/main/java/androidx/media3/transformer/ExoAssetLoaderVideoRenderer.java +++ b/libraries/transformer/src/main/java/androidx/media3/transformer/ExoAssetLoaderVideoRenderer.java @@ -16,7 +16,6 @@ package androidx.media3.transformer; import static androidx.media3.common.util.Assertions.checkNotNull; -import static androidx.media3.common.util.Util.SDK_INT; import android.media.MediaCodec; import androidx.annotation.Nullable; @@ -61,17 +60,8 @@ import org.checkerframework.checker.nullness.qual.RequiresNonNull; } @Override - protected Format overrideFormat(Format inputFormat) throws ExportException { + protected Format overrideFormat(Format inputFormat) { if (forceInterpretHdrAsSdr && ColorInfo.isTransferHdr(inputFormat.colorInfo)) { - if (SDK_INT < 29) { - throw ExportException.createForCodec( - new IllegalArgumentException( - "Interpreting HDR video as SDR is not supported on this device."), - ExportException.ERROR_CODE_DECODING_FORMAT_UNSUPPORTED, - /* isVideo= */ true, - /* isDecoder= */ true, - inputFormat); - } return inputFormat.buildUpon().setColorInfo(ColorInfo.SDR_BT709_LIMITED).build(); } return inputFormat; diff --git a/libraries/transformer/src/main/java/androidx/media3/transformer/TransformationRequest.java b/libraries/transformer/src/main/java/androidx/media3/transformer/TransformationRequest.java index 53d763c53a..aa36d97d14 100644 --- a/libraries/transformer/src/main/java/androidx/media3/transformer/TransformationRequest.java +++ b/libraries/transformer/src/main/java/androidx/media3/transformer/TransformationRequest.java @@ -90,13 +90,13 @@ public final class TransformationRequest { /** * Interpret HDR input as SDR, likely with a washed out look. * - *

Supported on API 29+. - * *

This is much more widely supported than {@link #HDR_MODE_KEEP_HDR} and {@link * #HDR_MODE_TONE_MAP_HDR_TO_SDR_USING_MEDIACODEC}. However, as HDR transfer functions and * metadata will be ignored, contents will be displayed incorrectly, likely with a washed out * look. * + *

Using this API may lead to codec errors before API 29, per b/269759013. + * *

Use of this flag may result in {@code ERROR_CODE_DECODING_FORMAT_UNSUPPORTED}. * *

This field is experimental, and will be renamed or removed in a future release.