mirror of
https://github.com/androidx/media.git
synced 2025-04-30 06:46:50 +08:00
Move createCodecProfileLevel() to MediaCodecUtil and simplify usages
This is a non-functional change. PiperOrigin-RevId: 736534306
This commit is contained in:
parent
816d5cb86b
commit
d777a11840
@ -30,6 +30,7 @@ import static androidx.media3.exoplayer.DecoderReuseEvaluation.REUSE_RESULT_YES_
|
||||
import static androidx.media3.exoplayer.DecoderReuseEvaluation.REUSE_RESULT_YES_WITH_RECONFIGURATION;
|
||||
import static androidx.media3.exoplayer.mediacodec.MediaCodecPerformancePointCoverageProvider.COVERAGE_RESULT_NO;
|
||||
import static androidx.media3.exoplayer.mediacodec.MediaCodecPerformancePointCoverageProvider.COVERAGE_RESULT_YES;
|
||||
import static androidx.media3.exoplayer.mediacodec.MediaCodecUtil.createCodecProfileLevel;
|
||||
|
||||
import android.graphics.Point;
|
||||
import android.media.MediaCodec;
|
||||
@ -775,12 +776,8 @@ public final class MediaCodecInfo {
|
||||
level = CodecProfileLevel.VP9Level1;
|
||||
}
|
||||
|
||||
CodecProfileLevel profileLevel = new CodecProfileLevel();
|
||||
// Since this method is for legacy devices only, assume that only profile 0 is supported.
|
||||
profileLevel.profile = CodecProfileLevel.VP9Profile0;
|
||||
profileLevel.level = level;
|
||||
|
||||
return new CodecProfileLevel[] {profileLevel};
|
||||
return new CodecProfileLevel[] {createCodecProfileLevel(CodecProfileLevel.VP9Profile0, level)};
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -322,6 +322,18 @@ public final class MediaCodecUtil {
|
||||
return maxH264DecodableFrameSize;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a {@link CodecProfileLevel} configured with the provided {@code profile} and {@code
|
||||
* level}.
|
||||
*/
|
||||
@UnstableApi
|
||||
public static CodecProfileLevel createCodecProfileLevel(int profile, int level) {
|
||||
CodecProfileLevel profileLevel = new CodecProfileLevel();
|
||||
profileLevel.profile = profile;
|
||||
profileLevel.level = level;
|
||||
return profileLevel;
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated Use {@link CodecSpecificDataUtil#getCodecProfileAndLevel(Format)}.
|
||||
*/
|
||||
|
@ -16,8 +16,18 @@
|
||||
package androidx.media3.exoplayer.video;
|
||||
|
||||
import static android.media.MediaCodec.INFO_TRY_AGAIN_LATER;
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.AVCLevel42;
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.AVCProfileBaseline;
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.AVCProfileHigh;
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.DolbyVisionLevelFhd30;
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.DolbyVisionProfileDvheDtr;
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.HEVCHighTierLevel51;
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.HEVCMainTierLevel41;
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.HEVCProfileMain;
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.HEVCProfileMain10;
|
||||
import static android.view.Display.DEFAULT_DISPLAY;
|
||||
import static androidx.media3.common.util.Util.msToUs;
|
||||
import static androidx.media3.exoplayer.mediacodec.MediaCodecUtil.createCodecProfileLevel;
|
||||
import static androidx.media3.test.utils.FakeSampleStream.FakeSampleStreamItem.END_OF_STREAM_ITEM;
|
||||
import static androidx.media3.test.utils.FakeSampleStream.FakeSampleStreamItem.format;
|
||||
import static androidx.media3.test.utils.FakeSampleStream.FakeSampleStreamItem.oneByteSample;
|
||||
@ -139,8 +149,7 @@ public class MediaCodecVideoRendererTest {
|
||||
/* name= */ "h264-codec-hw",
|
||||
/* mimeType= */ MimeTypes.VIDEO_H264,
|
||||
/* codecMimeType= */ MimeTypes.VIDEO_H264,
|
||||
/* capabilities= */ createCodecCapabilities(
|
||||
CodecProfileLevel.AVCProfileHigh, CodecProfileLevel.AVCLevel4),
|
||||
/* capabilities= */ createCodecCapabilities(AVCProfileHigh, CodecProfileLevel.AVCLevel4),
|
||||
/* hardwareAccelerated= */ true,
|
||||
/* softwareOnly= */ false,
|
||||
/* vendor= */ false,
|
||||
@ -152,8 +161,7 @@ public class MediaCodecVideoRendererTest {
|
||||
/* name= */ "h264-codec-sw",
|
||||
/* mimeType= */ MimeTypes.VIDEO_H264,
|
||||
/* codecMimeType= */ MimeTypes.VIDEO_H264,
|
||||
/* capabilities= */ createCodecCapabilities(
|
||||
CodecProfileLevel.AVCProfileHigh, CodecProfileLevel.AVCLevel5),
|
||||
/* capabilities= */ createCodecCapabilities(AVCProfileHigh, CodecProfileLevel.AVCLevel5),
|
||||
/* hardwareAccelerated= */ false,
|
||||
/* softwareOnly= */ true,
|
||||
/* vendor= */ false,
|
||||
@ -1817,11 +1825,10 @@ public class MediaCodecVideoRendererTest {
|
||||
case MimeTypes.VIDEO_H264:
|
||||
CodecCapabilities capabilitiesH264 = new CodecCapabilities();
|
||||
capabilitiesH264.profileLevels =
|
||||
new CodecProfileLevel[] {new CodecProfileLevel(), new CodecProfileLevel()};
|
||||
capabilitiesH264.profileLevels[0].profile = CodecProfileLevel.AVCProfileBaseline;
|
||||
capabilitiesH264.profileLevels[0].level = CodecProfileLevel.AVCLevel42;
|
||||
capabilitiesH264.profileLevels[1].profile = CodecProfileLevel.AVCProfileHigh;
|
||||
capabilitiesH264.profileLevels[1].level = CodecProfileLevel.AVCLevel42;
|
||||
new CodecProfileLevel[] {
|
||||
createCodecProfileLevel(AVCProfileBaseline, AVCLevel42),
|
||||
createCodecProfileLevel(AVCProfileHigh, AVCLevel42)
|
||||
};
|
||||
return ImmutableList.of(
|
||||
MediaCodecInfo.newInstance(
|
||||
/* name= */ "h264-codec",
|
||||
@ -1836,11 +1843,10 @@ public class MediaCodecVideoRendererTest {
|
||||
case MimeTypes.VIDEO_H265:
|
||||
CodecCapabilities capabilitiesH265 = new CodecCapabilities();
|
||||
capabilitiesH265.profileLevels =
|
||||
new CodecProfileLevel[] {new CodecProfileLevel(), new CodecProfileLevel()};
|
||||
capabilitiesH265.profileLevels[0].profile = CodecProfileLevel.HEVCProfileMain;
|
||||
capabilitiesH265.profileLevels[0].level = CodecProfileLevel.HEVCMainTierLevel41;
|
||||
capabilitiesH265.profileLevels[1].profile = CodecProfileLevel.HEVCProfileMain10;
|
||||
capabilitiesH265.profileLevels[1].level = CodecProfileLevel.HEVCHighTierLevel51;
|
||||
new CodecProfileLevel[] {
|
||||
createCodecProfileLevel(HEVCProfileMain, HEVCMainTierLevel41),
|
||||
createCodecProfileLevel(HEVCProfileMain10, HEVCHighTierLevel51)
|
||||
};
|
||||
return ImmutableList.of(
|
||||
MediaCodecInfo.newInstance(
|
||||
/* name= */ "h265-codec",
|
||||
@ -1899,11 +1905,8 @@ public class MediaCodecVideoRendererTest {
|
||||
switch (mimeType) {
|
||||
case MimeTypes.VIDEO_DOLBY_VISION:
|
||||
{
|
||||
CodecCapabilities capabilitiesDolby = new CodecCapabilities();
|
||||
capabilitiesDolby.profileLevels = new CodecProfileLevel[] {new CodecProfileLevel()};
|
||||
capabilitiesDolby.profileLevels[0].profile =
|
||||
CodecProfileLevel.DolbyVisionProfileDvheDtr;
|
||||
capabilitiesDolby.profileLevels[0].level = CodecProfileLevel.DolbyVisionLevelFhd30;
|
||||
CodecCapabilities capabilitiesDolby =
|
||||
createCodecCapabilities(DolbyVisionProfileDvheDtr, DolbyVisionLevelFhd30);
|
||||
return ImmutableList.of(
|
||||
MediaCodecInfo.newInstance(
|
||||
/* name= */ "dvhe-codec",
|
||||
@ -1920,11 +1923,10 @@ public class MediaCodecVideoRendererTest {
|
||||
{
|
||||
CodecCapabilities capabilitiesH265 = new CodecCapabilities();
|
||||
capabilitiesH265.profileLevels =
|
||||
new CodecProfileLevel[] {new CodecProfileLevel(), new CodecProfileLevel()};
|
||||
capabilitiesH265.profileLevels[0].profile = CodecProfileLevel.HEVCProfileMain;
|
||||
capabilitiesH265.profileLevels[0].level = CodecProfileLevel.HEVCMainTierLevel41;
|
||||
capabilitiesH265.profileLevels[1].profile = CodecProfileLevel.HEVCProfileMain10;
|
||||
capabilitiesH265.profileLevels[1].level = CodecProfileLevel.HEVCHighTierLevel51;
|
||||
new CodecProfileLevel[] {
|
||||
createCodecProfileLevel(HEVCProfileMain, HEVCMainTierLevel41),
|
||||
createCodecProfileLevel(HEVCProfileMain10, HEVCHighTierLevel51)
|
||||
};
|
||||
return ImmutableList.of(
|
||||
MediaCodecInfo.newInstance(
|
||||
/* name= */ "h265-codec",
|
||||
@ -2150,9 +2152,7 @@ public class MediaCodecVideoRendererTest {
|
||||
|
||||
private static CodecCapabilities createCodecCapabilities(int profile, int level) {
|
||||
CodecCapabilities capabilities = new CodecCapabilities();
|
||||
capabilities.profileLevels = new CodecProfileLevel[] {new CodecProfileLevel()};
|
||||
capabilities.profileLevels[0].profile = profile;
|
||||
capabilities.profileLevels[0].level = level;
|
||||
capabilities.profileLevels = new CodecProfileLevel[] {createCodecProfileLevel(profile, level)};
|
||||
return capabilities;
|
||||
}
|
||||
|
||||
|
@ -18,6 +18,7 @@ package androidx.media3.test.utils.robolectric;
|
||||
import static androidx.media3.common.util.Assertions.checkArgument;
|
||||
import static androidx.media3.common.util.Assertions.checkState;
|
||||
import static androidx.media3.common.util.Assertions.checkStateNotNull;
|
||||
import static androidx.media3.exoplayer.mediacodec.MediaCodecUtil.createCodecProfileLevel;
|
||||
|
||||
import android.media.MediaCodecInfo;
|
||||
import android.media.MediaCodecInfo.CodecProfileLevel;
|
||||
@ -145,7 +146,7 @@ public final class ShadowMediaCodecConfig extends ExternalResource {
|
||||
/* codecName= */ "exotest.video.avc",
|
||||
/* mimeType= */ MimeTypes.VIDEO_H264,
|
||||
/* profileLevels= */ ImmutableList.of(
|
||||
createProfileLevel(
|
||||
createCodecProfileLevel(
|
||||
MediaCodecInfo.CodecProfileLevel.AVCProfileHigh,
|
||||
MediaCodecInfo.CodecProfileLevel.AVCLevel62)),
|
||||
/* colorFormats= */ ImmutableList.of(
|
||||
@ -156,7 +157,7 @@ public final class ShadowMediaCodecConfig extends ExternalResource {
|
||||
/* codecName= */ "exotest.video.hevc",
|
||||
/* mimeType= */ MimeTypes.VIDEO_H265,
|
||||
/* profileLevels= */ ImmutableList.of(
|
||||
createProfileLevel(
|
||||
createCodecProfileLevel(
|
||||
CodecProfileLevel.HEVCProfileMain, CodecProfileLevel.HEVCMainTierLevel61)),
|
||||
/* colorFormats= */ ImmutableList.of(
|
||||
MediaCodecInfo.CodecCapabilities.COLOR_FormatYUV420Flexible)));
|
||||
@ -166,7 +167,7 @@ public final class ShadowMediaCodecConfig extends ExternalResource {
|
||||
/* codecName= */ "exotest.video.mpeg2",
|
||||
/* mimeType= */ MimeTypes.VIDEO_MPEG2,
|
||||
/* profileLevels= */ ImmutableList.of(
|
||||
createProfileLevel(
|
||||
createCodecProfileLevel(
|
||||
MediaCodecInfo.CodecProfileLevel.MPEG2ProfileMain,
|
||||
MediaCodecInfo.CodecProfileLevel.MPEG2LevelML)),
|
||||
/* colorFormats= */ ImmutableList.of(
|
||||
@ -232,13 +233,6 @@ public final class ShadowMediaCodecConfig extends ExternalResource {
|
||||
return codecs.buildOrThrow();
|
||||
}
|
||||
|
||||
private static MediaCodecInfo.CodecProfileLevel createProfileLevel(int profile, int level) {
|
||||
MediaCodecInfo.CodecProfileLevel profileLevel = new MediaCodecInfo.CodecProfileLevel();
|
||||
profileLevel.profile = profile;
|
||||
profileLevel.level = level;
|
||||
return profileLevel;
|
||||
}
|
||||
|
||||
/**
|
||||
* A {@link ShadowMediaCodec.CodecConfig.Codec} that passes data through without modifying it.
|
||||
*
|
||||
|
@ -16,6 +16,9 @@
|
||||
|
||||
package androidx.media3.transformer;
|
||||
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.AVCLevel4;
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.AVCProfileHigh;
|
||||
import static androidx.media3.exoplayer.mediacodec.MediaCodecUtil.createCodecProfileLevel;
|
||||
import static androidx.media3.transformer.ExportException.ERROR_CODE_ENCODING_FORMAT_UNSUPPORTED;
|
||||
import static androidx.test.core.app.ApplicationProvider.getApplicationContext;
|
||||
import static com.google.common.truth.Truth.assertThat;
|
||||
@ -23,6 +26,7 @@ import static org.junit.Assert.assertThrows;
|
||||
|
||||
import android.content.Context;
|
||||
import android.media.MediaCodecInfo;
|
||||
import android.media.MediaCodecInfo.CodecProfileLevel;
|
||||
import android.media.MediaFormat;
|
||||
import androidx.media3.common.Format;
|
||||
import androidx.media3.common.MimeTypes;
|
||||
@ -58,11 +62,9 @@ public class DefaultEncoderFactoryTest {
|
||||
private static void createShadowH264Encoder() {
|
||||
MediaFormat avcFormat = new MediaFormat();
|
||||
avcFormat.setString(MediaFormat.KEY_MIME, MediaFormat.MIMETYPE_VIDEO_AVC);
|
||||
MediaCodecInfo.CodecProfileLevel profileLevel = new MediaCodecInfo.CodecProfileLevel();
|
||||
profileLevel.profile = MediaCodecInfo.CodecProfileLevel.AVCProfileHigh;
|
||||
// Using Level4 gives us 8192 16x16 blocks. If using width 1920 uses 120 blocks, 8192 / 120 = 68
|
||||
// blocks will be left for encoding height 1088.
|
||||
profileLevel.level = MediaCodecInfo.CodecProfileLevel.AVCLevel4;
|
||||
CodecProfileLevel profileLevel = createCodecProfileLevel(AVCProfileHigh, AVCLevel4);
|
||||
|
||||
createShadowVideoEncoder(avcFormat, profileLevel, "test.transformer.avc.encoder");
|
||||
}
|
||||
@ -79,16 +81,14 @@ public class DefaultEncoderFactoryTest {
|
||||
}
|
||||
|
||||
private static void createShadowVideoEncoder(
|
||||
MediaFormat supportedFormat,
|
||||
MediaCodecInfo.CodecProfileLevel supportedProfileLevel,
|
||||
String name) {
|
||||
MediaFormat supportedFormat, CodecProfileLevel supportedProfileLevel, String name) {
|
||||
MediaCodecInfo.CodecCapabilities capabilities =
|
||||
MediaCodecInfoBuilder.CodecCapabilitiesBuilder.newBuilder()
|
||||
.setMediaFormat(supportedFormat)
|
||||
.setIsEncoder(true)
|
||||
.setColorFormats(
|
||||
new int[] {MediaCodecInfo.CodecCapabilities.COLOR_FormatYUV420Flexible})
|
||||
.setProfileLevels(new MediaCodecInfo.CodecProfileLevel[] {supportedProfileLevel})
|
||||
.setProfileLevels(new CodecProfileLevel[] {supportedProfileLevel})
|
||||
.build();
|
||||
createShadowEncoder(name, capabilities);
|
||||
}
|
||||
|
@ -16,10 +16,14 @@
|
||||
|
||||
package androidx.media3.transformer;
|
||||
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.AVCLevel4;
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.AVCProfileHigh;
|
||||
import static androidx.media3.common.MimeTypes.VIDEO_H264;
|
||||
import static androidx.media3.exoplayer.mediacodec.MediaCodecUtil.createCodecProfileLevel;
|
||||
import static com.google.common.truth.Truth.assertThat;
|
||||
|
||||
import android.media.MediaCodecInfo;
|
||||
import android.media.MediaCodecInfo.CodecProfileLevel;
|
||||
import android.media.MediaFormat;
|
||||
import android.util.Size;
|
||||
import androidx.annotation.Nullable;
|
||||
@ -48,11 +52,9 @@ public class EncoderUtilTest {
|
||||
public void setUp() {
|
||||
MediaFormat avcFormat = new MediaFormat();
|
||||
avcFormat.setString(MediaFormat.KEY_MIME, VIDEO_H264);
|
||||
MediaCodecInfo.CodecProfileLevel profileLevel = new MediaCodecInfo.CodecProfileLevel();
|
||||
profileLevel.profile = MediaCodecInfo.CodecProfileLevel.AVCProfileHigh;
|
||||
// Using Level4 gives us 8192 16x16 blocks. If using width 1920 uses 120 blocks, 8192 / 120 = 68
|
||||
// blocks will be left for encoding height 1088.
|
||||
profileLevel.level = MediaCodecInfo.CodecProfileLevel.AVCLevel4;
|
||||
CodecProfileLevel profileLevel = createCodecProfileLevel(AVCProfileHigh, AVCLevel4);
|
||||
|
||||
ShadowMediaCodecList.addCodec(
|
||||
MediaCodecInfoBuilder.newBuilder()
|
||||
@ -64,7 +66,7 @@ public class EncoderUtilTest {
|
||||
.setIsEncoder(true)
|
||||
.setColorFormats(
|
||||
new int[] {MediaCodecInfo.CodecCapabilities.COLOR_FormatYUV420Flexible})
|
||||
.setProfileLevels(new MediaCodecInfo.CodecProfileLevel[] {profileLevel})
|
||||
.setProfileLevels(new CodecProfileLevel[] {profileLevel})
|
||||
.build())
|
||||
.build());
|
||||
}
|
||||
|
@ -15,11 +15,15 @@
|
||||
*/
|
||||
package androidx.media3.transformer;
|
||||
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.AVCLevel4;
|
||||
import static android.media.MediaCodecInfo.CodecProfileLevel.AVCProfileHigh;
|
||||
import static androidx.media3.exoplayer.mediacodec.MediaCodecUtil.createCodecProfileLevel;
|
||||
import static com.google.common.truth.Truth.assertThat;
|
||||
import static org.mockito.Mockito.mock;
|
||||
import static org.mockito.Mockito.when;
|
||||
|
||||
import android.media.MediaCodecInfo;
|
||||
import android.media.MediaCodecInfo.CodecProfileLevel;
|
||||
import android.media.MediaFormat;
|
||||
import android.net.Uri;
|
||||
import android.os.Looper;
|
||||
@ -139,19 +143,15 @@ public final class VideoEncoderWrapperTest {
|
||||
private static void createShadowH264Encoder() {
|
||||
MediaFormat avcFormat = new MediaFormat();
|
||||
avcFormat.setString(MediaFormat.KEY_MIME, MediaFormat.MIMETYPE_VIDEO_AVC);
|
||||
MediaCodecInfo.CodecProfileLevel profileLevel = new MediaCodecInfo.CodecProfileLevel();
|
||||
profileLevel.profile = MediaCodecInfo.CodecProfileLevel.AVCProfileHigh;
|
||||
// Using Level4 gives us 8192 16x16 blocks. If using width 1920 uses 120 blocks, 8192 / 120 = 68
|
||||
// blocks will be left for encoding height 1088.
|
||||
profileLevel.level = MediaCodecInfo.CodecProfileLevel.AVCLevel4;
|
||||
CodecProfileLevel profileLevel = createCodecProfileLevel(AVCProfileHigh, AVCLevel4);
|
||||
|
||||
createShadowVideoEncoder(avcFormat, profileLevel, "test.transformer.avc.encoder");
|
||||
}
|
||||
|
||||
private static void createShadowVideoEncoder(
|
||||
MediaFormat supportedFormat,
|
||||
MediaCodecInfo.CodecProfileLevel supportedProfileLevel,
|
||||
String name) {
|
||||
MediaFormat supportedFormat, CodecProfileLevel supportedProfileLevel, String name) {
|
||||
// ShadowMediaCodecList is static. The added encoders will be visible for every test.
|
||||
ShadowMediaCodecList.addCodec(
|
||||
MediaCodecInfoBuilder.newBuilder()
|
||||
@ -163,8 +163,7 @@ public final class VideoEncoderWrapperTest {
|
||||
.setIsEncoder(true)
|
||||
.setColorFormats(
|
||||
new int[] {MediaCodecInfo.CodecCapabilities.COLOR_FormatYUV420Flexible})
|
||||
.setProfileLevels(
|
||||
new MediaCodecInfo.CodecProfileLevel[] {supportedProfileLevel})
|
||||
.setProfileLevels(new CodecProfileLevel[] {supportedProfileLevel})
|
||||
.build())
|
||||
.build());
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user