limit transmuxing to regular rotations only

PiperOrigin-RevId: 601710663
This commit is contained in:
tofunmi 2024-01-26 02:41:30 -08:00 committed by Copybara-Service
parent 605689a020
commit 2e6982be2c
3 changed files with 46 additions and 3 deletions

View File

@ -17,6 +17,7 @@
package androidx.media3.transformer; package androidx.media3.transformer;
import static androidx.media3.transformer.Composition.HDR_MODE_KEEP_HDR; import static androidx.media3.transformer.Composition.HDR_MODE_KEEP_HDR;
import static java.lang.Math.round;
import android.media.MediaCodec; import android.media.MediaCodec;
import androidx.annotation.Nullable; import androidx.annotation.Nullable;
@ -178,6 +179,9 @@ import com.google.common.collect.ImmutableList;
return false; return false;
} }
float rotationDegrees = scaleAndRotateTransformation.rotationDegrees; float rotationDegrees = scaleAndRotateTransformation.rotationDegrees;
if (rotationDegrees % 90f != 0) {
return false;
}
totalRotationDegrees += rotationDegrees; totalRotationDegrees += rotationDegrees;
if (totalRotationDegrees % 90 == 0 && !widthHeightFlipped) { if (totalRotationDegrees % 90 == 0 && !widthHeightFlipped) {
int temp = decodedWidth; int temp = decodedWidth;
@ -205,7 +209,7 @@ import com.google.common.collect.ImmutableList;
|| totalRotationDegrees == 270f) { || totalRotationDegrees == 270f) {
// The MuxerWrapper rotation is clockwise while the ScaleAndRotateTransformation rotation // The MuxerWrapper rotation is clockwise while the ScaleAndRotateTransformation rotation
// is counterclockwise. // is counterclockwise.
muxerWrapper.setAdditionalRotationDegrees(360 - Math.round(totalRotationDegrees)); muxerWrapper.setAdditionalRotationDegrees(360 - round(totalRotationDegrees));
return true; return true;
} }
return false; return false;

View File

@ -1073,10 +1073,9 @@ public final class MediaItemExportTest {
// Total rotation is 270. // Total rotation is 270.
ImmutableList<Effect> videoEffects = ImmutableList<Effect> videoEffects =
ImmutableList.of( ImmutableList.of(
new ScaleAndRotateTransformation.Builder().setRotationDegrees(315).build(), new ScaleAndRotateTransformation.Builder().setRotationDegrees(90).build(),
new Contrast(0f), new Contrast(0f),
new ScaleAndRotateTransformation.Builder().setRotationDegrees(180).build(), new ScaleAndRotateTransformation.Builder().setRotationDegrees(180).build(),
new ScaleAndRotateTransformation.Builder().setRotationDegrees(135).build(),
Presentation.createForHeight(1080)); Presentation.createForHeight(1080));
EditedMediaItem editedMediaItem = EditedMediaItem editedMediaItem =
new EditedMediaItem.Builder(MediaItem.fromUri(ASSET_URI_PREFIX + FILE_AUDIO_VIDEO)) new EditedMediaItem.Builder(MediaItem.fromUri(ASSET_URI_PREFIX + FILE_AUDIO_VIDEO))

View File

@ -81,6 +81,46 @@ public class TransformerUtilTest {
.isTrue(); .isTrue();
} }
@Test
public void shouldTranscodeVideo_irregularRotationAndPresentation_returnsTrue() throws Exception {
MediaItem mediaItem = MediaItem.fromUri(ASSET_URI_PREFIX + FILE_AUDIO_VIDEO);
Format format =
new Format.Builder()
.setSampleMimeType(VIDEO_H264)
.setWidth(1080)
.setHeight(720)
.setFrameRate(29.97f)
.setCodecs("avc1.64001F")
.build();
ImmutableList<Effect> videoEffects =
ImmutableList.of(
new ScaleAndRotateTransformation.Builder().setRotationDegrees(45).build(),
Presentation.createForHeight(format.height),
new ScaleAndRotateTransformation.Builder().setRotationDegrees(45).build());
Effects effects = new Effects(/* audioProcessors= */ ImmutableList.of(), videoEffects);
EditedMediaItem editedMediaItem =
new EditedMediaItem.Builder(mediaItem).setEffects(effects).build();
Composition composition =
new Composition.Builder(new EditedMediaItemSequence(editedMediaItem)).build();
MuxerWrapper muxerWrapper =
new MuxerWrapper(
temporaryFolder.newFile().getPath(),
new DefaultMuxer.Factory(),
new NoOpMuxerListenerImpl(),
MUXER_MODE_DEFAULT,
/* dropSamplesBeforeFirstVideoSample= */ false);
assertThat(
shouldTranscodeVideo(
format,
composition,
/* sequenceIndex= */ 0,
new TransformationRequest.Builder().build(),
new DefaultEncoderFactory.Builder(getApplicationContext()).build(),
muxerWrapper))
.isTrue();
}
private static final class NoOpMuxerListenerImpl implements MuxerWrapper.Listener { private static final class NoOpMuxerListenerImpl implements MuxerWrapper.Listener {
@Override @Override