Commit 01e0db62 by samrobinson Committed by microkatz

Utilize AudioProcessingPipeline in Transformer.

Provides an API for applications to set AudioProcessors for use
in Transformer.

PiperOrigin-RevId: 488621242
parent 20151b99
...@@ -24,7 +24,6 @@ import androidx.annotation.IntDef; ...@@ -24,7 +24,6 @@ import androidx.annotation.IntDef;
import androidx.annotation.Nullable; import androidx.annotation.Nullable;
import com.google.android.exoplayer2.Format; import com.google.android.exoplayer2.Format;
import com.google.android.exoplayer2.PlaybackException; import com.google.android.exoplayer2.PlaybackException;
import com.google.android.exoplayer2.audio.AudioProcessor;
import com.google.android.exoplayer2.audio.AudioProcessor.AudioFormat; import com.google.android.exoplayer2.audio.AudioProcessor.AudioFormat;
import com.google.android.exoplayer2.util.Clock; import com.google.android.exoplayer2.util.Clock;
import com.google.android.exoplayer2.util.FrameProcessingException; import com.google.android.exoplayer2.util.FrameProcessingException;
...@@ -71,6 +70,7 @@ public final class TransformationException extends Exception { ...@@ -71,6 +70,7 @@ public final class TransformationException extends Exception {
ERROR_CODE_OUTPUT_FORMAT_UNSUPPORTED, ERROR_CODE_OUTPUT_FORMAT_UNSUPPORTED,
ERROR_CODE_HDR_ENCODING_UNSUPPORTED, ERROR_CODE_HDR_ENCODING_UNSUPPORTED,
ERROR_CODE_FRAME_PROCESSING_FAILED, ERROR_CODE_FRAME_PROCESSING_FAILED,
ERROR_CODE_AUDIO_PROCESSING_FAILED,
ERROR_CODE_MUXING_FAILED, ERROR_CODE_MUXING_FAILED,
}) })
public @interface ErrorCode {} public @interface ErrorCode {}
...@@ -161,9 +161,15 @@ public final class TransformationException extends Exception { ...@@ -161,9 +161,15 @@ public final class TransformationException extends Exception {
/** Caused by a frame processing failure. */ /** Caused by a frame processing failure. */
public static final int ERROR_CODE_FRAME_PROCESSING_FAILED = 5001; public static final int ERROR_CODE_FRAME_PROCESSING_FAILED = 5001;
// Muxing errors (6xxx). // Audio processing errors (6xxx).
/** Caused by an audio processing failure. */
public static final int ERROR_CODE_AUDIO_PROCESSING_FAILED = 6001;
// Muxing errors (7xxx).
/** Caused by a failure while muxing media samples. */ /** Caused by a failure while muxing media samples. */
public static final int ERROR_CODE_MUXING_FAILED = 6001; public static final int ERROR_CODE_MUXING_FAILED = 7001;
private static final ImmutableBiMap<String, @ErrorCode Integer> NAME_TO_ERROR_CODE = private static final ImmutableBiMap<String, @ErrorCode Integer> NAME_TO_ERROR_CODE =
new ImmutableBiMap.Builder<String, @ErrorCode Integer>() new ImmutableBiMap.Builder<String, @ErrorCode Integer>()
...@@ -186,6 +192,7 @@ public final class TransformationException extends Exception { ...@@ -186,6 +192,7 @@ public final class TransformationException extends Exception {
.put("ERROR_CODE_OUTPUT_FORMAT_UNSUPPORTED", ERROR_CODE_OUTPUT_FORMAT_UNSUPPORTED) .put("ERROR_CODE_OUTPUT_FORMAT_UNSUPPORTED", ERROR_CODE_OUTPUT_FORMAT_UNSUPPORTED)
.put("ERROR_CODE_HDR_ENCODING_UNSUPPORTED", ERROR_CODE_HDR_ENCODING_UNSUPPORTED) .put("ERROR_CODE_HDR_ENCODING_UNSUPPORTED", ERROR_CODE_HDR_ENCODING_UNSUPPORTED)
.put("ERROR_CODE_FRAME_PROCESSING_FAILED", ERROR_CODE_FRAME_PROCESSING_FAILED) .put("ERROR_CODE_FRAME_PROCESSING_FAILED", ERROR_CODE_FRAME_PROCESSING_FAILED)
.put("ERROR_CODE_AUDIO_PROCESSING_FAILED", ERROR_CODE_AUDIO_PROCESSING_FAILED)
.put("ERROR_CODE_MUXING_FAILED", ERROR_CODE_MUXING_FAILED) .put("ERROR_CODE_MUXING_FAILED", ERROR_CODE_MUXING_FAILED)
.buildOrThrow(); .buildOrThrow();
...@@ -262,18 +269,18 @@ public final class TransformationException extends Exception { ...@@ -262,18 +269,18 @@ public final class TransformationException extends Exception {
} }
/** /**
* Creates an instance for an {@link AudioProcessor} related exception. * Creates an instance for an audio processing related exception.
* *
* @param cause The cause of the failure. * @param cause The cause of the failure.
* @param componentName The name of the {@link AudioProcessor} used.
* @param audioFormat The {@link AudioFormat} used. * @param audioFormat The {@link AudioFormat} used.
* @param errorCode See {@link #errorCode}.
* @return The created instance. * @return The created instance.
*/ */
public static TransformationException createForAudioProcessor( public static TransformationException createForAudioProcessing(
Throwable cause, String componentName, AudioFormat audioFormat, int errorCode) { Throwable cause, AudioFormat audioFormat) {
return new TransformationException( return new TransformationException(
componentName + " error, audio_format = " + audioFormat, cause, errorCode); "Audio processing error, audio_format = " + audioFormat,
cause,
ERROR_CODE_AUDIO_PROCESSING_FAILED);
} }
/** /**
......
...@@ -31,6 +31,7 @@ import androidx.annotation.VisibleForTesting; ...@@ -31,6 +31,7 @@ import androidx.annotation.VisibleForTesting;
import com.google.android.exoplayer2.C; import com.google.android.exoplayer2.C;
import com.google.android.exoplayer2.ExoPlayerLibraryInfo; import com.google.android.exoplayer2.ExoPlayerLibraryInfo;
import com.google.android.exoplayer2.MediaItem; import com.google.android.exoplayer2.MediaItem;
import com.google.android.exoplayer2.audio.AudioProcessor;
import com.google.android.exoplayer2.effect.GlEffect; import com.google.android.exoplayer2.effect.GlEffect;
import com.google.android.exoplayer2.effect.GlEffectsFrameProcessor; import com.google.android.exoplayer2.effect.GlEffectsFrameProcessor;
import com.google.android.exoplayer2.effect.GlMatrixTransformation; import com.google.android.exoplayer2.effect.GlMatrixTransformation;
...@@ -83,6 +84,7 @@ public final class Transformer { ...@@ -83,6 +84,7 @@ public final class Transformer {
// Optional fields. // Optional fields.
private TransformationRequest transformationRequest; private TransformationRequest transformationRequest;
private ImmutableList<AudioProcessor> audioProcessors;
private ImmutableList<Effect> videoEffects; private ImmutableList<Effect> videoEffects;
private boolean removeAudio; private boolean removeAudio;
private boolean removeVideo; private boolean removeVideo;
...@@ -104,6 +106,7 @@ public final class Transformer { ...@@ -104,6 +106,7 @@ public final class Transformer {
public Builder(Context context) { public Builder(Context context) {
this.context = context.getApplicationContext(); this.context = context.getApplicationContext();
transformationRequest = new TransformationRequest.Builder().build(); transformationRequest = new TransformationRequest.Builder().build();
audioProcessors = ImmutableList.of();
videoEffects = ImmutableList.of(); videoEffects = ImmutableList.of();
decoderFactory = new DefaultDecoderFactory(this.context); decoderFactory = new DefaultDecoderFactory(this.context);
encoderFactory = new DefaultEncoderFactory.Builder(this.context).build(); encoderFactory = new DefaultEncoderFactory.Builder(this.context).build();
...@@ -119,6 +122,7 @@ public final class Transformer { ...@@ -119,6 +122,7 @@ public final class Transformer {
private Builder(Transformer transformer) { private Builder(Transformer transformer) {
this.context = transformer.context; this.context = transformer.context;
this.transformationRequest = transformer.transformationRequest; this.transformationRequest = transformer.transformationRequest;
this.audioProcessors = transformer.audioProcessors;
this.videoEffects = transformer.videoEffects; this.videoEffects = transformer.videoEffects;
this.removeAudio = transformer.removeAudio; this.removeAudio = transformer.removeAudio;
this.removeVideo = transformer.removeVideo; this.removeVideo = transformer.removeVideo;
...@@ -150,6 +154,19 @@ public final class Transformer { ...@@ -150,6 +154,19 @@ public final class Transformer {
} }
/** /**
* Sets the {@link AudioProcessor} instances to apply to audio buffers.
*
* <p>The {@link AudioProcessor} instances are applied in the order of the list, and buffers
* will only be modified by that {@link AudioProcessor} if it {@link AudioProcessor#isActive()}
* based on the current configuration.
*/
@CanIgnoreReturnValue
public Builder setAudioProcessors(List<AudioProcessor> audioProcessors) {
this.audioProcessors = ImmutableList.copyOf(audioProcessors);
return this;
}
/**
* Sets the {@link Effect} instances to apply to each video frame. * Sets the {@link Effect} instances to apply to each video frame.
* *
* <p>The {@link Effect} instances are applied before any {@linkplain * <p>The {@link Effect} instances are applied before any {@linkplain
...@@ -424,6 +441,7 @@ public final class Transformer { ...@@ -424,6 +441,7 @@ public final class Transformer {
return new Transformer( return new Transformer(
context, context,
transformationRequest, transformationRequest,
audioProcessors,
videoEffects, videoEffects,
removeAudio, removeAudio,
removeVideo, removeVideo,
...@@ -535,6 +553,7 @@ public final class Transformer { ...@@ -535,6 +553,7 @@ public final class Transformer {
private final Context context; private final Context context;
private final TransformationRequest transformationRequest; private final TransformationRequest transformationRequest;
private final ImmutableList<AudioProcessor> audioProcessors;
private final ImmutableList<Effect> videoEffects; private final ImmutableList<Effect> videoEffects;
private final boolean removeAudio; private final boolean removeAudio;
private final boolean removeVideo; private final boolean removeVideo;
...@@ -556,6 +575,7 @@ public final class Transformer { ...@@ -556,6 +575,7 @@ public final class Transformer {
private Transformer( private Transformer(
Context context, Context context,
TransformationRequest transformationRequest, TransformationRequest transformationRequest,
ImmutableList<AudioProcessor> audioProcessors,
ImmutableList<Effect> videoEffects, ImmutableList<Effect> videoEffects,
boolean removeAudio, boolean removeAudio,
boolean removeVideo, boolean removeVideo,
...@@ -571,6 +591,7 @@ public final class Transformer { ...@@ -571,6 +591,7 @@ public final class Transformer {
checkState(!removeAudio || !removeVideo, "Audio and video cannot both be removed."); checkState(!removeAudio || !removeVideo, "Audio and video cannot both be removed.");
this.context = context; this.context = context;
this.transformationRequest = transformationRequest; this.transformationRequest = transformationRequest;
this.audioProcessors = audioProcessors;
this.videoEffects = videoEffects; this.videoEffects = videoEffects;
this.removeAudio = removeAudio; this.removeAudio = removeAudio;
this.removeVideo = removeVideo; this.removeVideo = removeVideo;
...@@ -587,6 +608,7 @@ public final class Transformer { ...@@ -587,6 +608,7 @@ public final class Transformer {
new TransformerInternal( new TransformerInternal(
context, context,
transformationRequest, transformationRequest,
audioProcessors,
videoEffects, videoEffects,
removeAudio, removeAudio,
removeVideo, removeVideo,
......
...@@ -29,6 +29,7 @@ import com.google.android.exoplayer2.C; ...@@ -29,6 +29,7 @@ import com.google.android.exoplayer2.C;
import com.google.android.exoplayer2.Format; import com.google.android.exoplayer2.Format;
import com.google.android.exoplayer2.MediaItem; import com.google.android.exoplayer2.MediaItem;
import com.google.android.exoplayer2.PlaybackException; import com.google.android.exoplayer2.PlaybackException;
import com.google.android.exoplayer2.audio.AudioProcessor;
import com.google.android.exoplayer2.metadata.Metadata; import com.google.android.exoplayer2.metadata.Metadata;
import com.google.android.exoplayer2.metadata.mp4.SlowMotionData; import com.google.android.exoplayer2.metadata.mp4.SlowMotionData;
import com.google.android.exoplayer2.source.MediaSource; import com.google.android.exoplayer2.source.MediaSource;
...@@ -52,6 +53,7 @@ import java.util.List; ...@@ -52,6 +53,7 @@ import java.util.List;
private final Context context; private final Context context;
private final TransformationRequest transformationRequest; private final TransformationRequest transformationRequest;
private final ImmutableList<AudioProcessor> audioProcessors;
private final ImmutableList<Effect> videoEffects; private final ImmutableList<Effect> videoEffects;
private final Codec.DecoderFactory decoderFactory; private final Codec.DecoderFactory decoderFactory;
private final Codec.EncoderFactory encoderFactory; private final Codec.EncoderFactory encoderFactory;
...@@ -66,6 +68,7 @@ import java.util.List; ...@@ -66,6 +68,7 @@ import java.util.List;
public TransformerInternal( public TransformerInternal(
Context context, Context context,
TransformationRequest transformationRequest, TransformationRequest transformationRequest,
ImmutableList<AudioProcessor> audioProcessors,
ImmutableList<Effect> videoEffects, ImmutableList<Effect> videoEffects,
boolean removeAudio, boolean removeAudio,
boolean removeVideo, boolean removeVideo,
...@@ -78,6 +81,7 @@ import java.util.List; ...@@ -78,6 +81,7 @@ import java.util.List;
Clock clock) { Clock clock) {
this.context = context; this.context = context;
this.transformationRequest = transformationRequest; this.transformationRequest = transformationRequest;
this.audioProcessors = audioProcessors;
this.videoEffects = videoEffects; this.videoEffects = videoEffects;
this.decoderFactory = decoderFactory; this.decoderFactory = decoderFactory;
this.encoderFactory = encoderFactory; this.encoderFactory = encoderFactory;
...@@ -210,6 +214,7 @@ import java.util.List; ...@@ -210,6 +214,7 @@ import java.util.List;
streamStartPositionUs, streamStartPositionUs,
streamOffsetUs, streamOffsetUs,
transformationRequest, transformationRequest,
audioProcessors,
decoderFactory, decoderFactory,
encoderFactory, encoderFactory,
muxerWrapper, muxerWrapper,
...@@ -256,6 +261,9 @@ import java.util.List; ...@@ -256,6 +261,9 @@ import java.util.List;
if (transformationRequest.flattenForSlowMotion && isSlowMotion(inputFormat)) { if (transformationRequest.flattenForSlowMotion && isSlowMotion(inputFormat)) {
return true; return true;
} }
if (!audioProcessors.isEmpty()) {
return true;
}
return false; return false;
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or sign in to comment