mirror of
https://github.com/samsonjs/media.git
synced 2026-04-04 11:05:47 +00:00
Add support for AudioTrack pitch/speed alteration on API 23.
Issue #26 ------------- Created by MOE: https://github.com/google/moe MOE_MIGRATED_REVID=108958826
This commit is contained in:
parent
33506adab5
commit
6570ef0e48
2 changed files with 87 additions and 7 deletions
|
|
@ -24,6 +24,7 @@ import com.google.android.exoplayer.util.MimeTypes;
|
|||
import android.annotation.TargetApi;
|
||||
import android.media.AudioManager;
|
||||
import android.media.MediaCodec;
|
||||
import android.media.PlaybackParams;
|
||||
import android.media.audiofx.Virtualizer;
|
||||
import android.os.Handler;
|
||||
import android.os.SystemClock;
|
||||
|
|
@ -76,6 +77,14 @@ public class MediaCodecAudioTrackRenderer extends MediaCodecTrackRenderer implem
|
|||
*/
|
||||
public static final int MSG_SET_VOLUME = 1;
|
||||
|
||||
/**
|
||||
* The type of a message that can be passed to an instance of this class via
|
||||
* {@link ExoPlayer#sendMessage} or {@link ExoPlayer#blockingSendMessage}. The message object
|
||||
* should be a {@link android.media.PlaybackParams}. This will be used to configure the
|
||||
* underlying {@link android.media.AudioTrack}.
|
||||
*/
|
||||
public static final int MSG_SET_PLAYBACK_PARAMS = 2;
|
||||
|
||||
/**
|
||||
* The name for the raw (passthrough) decoder OMX component.
|
||||
*/
|
||||
|
|
@ -401,10 +410,16 @@ public class MediaCodecAudioTrackRenderer extends MediaCodecTrackRenderer implem
|
|||
|
||||
@Override
|
||||
public void handleMessage(int messageType, Object message) throws ExoPlaybackException {
|
||||
if (messageType == MSG_SET_VOLUME) {
|
||||
audioTrack.setVolume((Float) message);
|
||||
} else {
|
||||
super.handleMessage(messageType, message);
|
||||
switch (messageType) {
|
||||
case MSG_SET_VOLUME:
|
||||
audioTrack.setVolume((Float) message);
|
||||
break;
|
||||
case MSG_SET_PLAYBACK_PARAMS:
|
||||
audioTrack.setPlaybackParams((PlaybackParams) message);
|
||||
break;
|
||||
default:
|
||||
super.handleMessage(messageType, message);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -26,6 +26,7 @@ import android.media.AudioFormat;
|
|||
import android.media.AudioManager;
|
||||
import android.media.AudioTimestamp;
|
||||
import android.media.MediaFormat;
|
||||
import android.media.PlaybackParams;
|
||||
import android.os.ConditionVariable;
|
||||
import android.os.SystemClock;
|
||||
import android.util.Log;
|
||||
|
|
@ -248,7 +249,9 @@ public final class AudioTrack {
|
|||
// There's no guarantee this method exists. Do nothing.
|
||||
}
|
||||
}
|
||||
if (Util.SDK_INT >= 19) {
|
||||
if (Util.SDK_INT >= 23) {
|
||||
audioTrackUtil = new AudioTrackUtilV23();
|
||||
} else if (Util.SDK_INT >= 19) {
|
||||
audioTrackUtil = new AudioTrackUtilV19();
|
||||
} else {
|
||||
audioTrackUtil = new AudioTrackUtil();
|
||||
|
|
@ -300,7 +303,10 @@ public final class AudioTrack {
|
|||
if (audioTimestampSet) {
|
||||
// How long ago in the past the audio timestamp is (negative if it's in the future).
|
||||
long presentationDiff = systemClockUs - (audioTrackUtil.getTimestampNanoTime() / 1000);
|
||||
long framesDiff = durationUsToFrames(presentationDiff);
|
||||
// Fixes such difference if the playback speed is not real time speed.
|
||||
long actualSpeedPresentationDiff = (long) (presentationDiff
|
||||
* audioTrackUtil.getPlaybackSpeed());
|
||||
long framesDiff = durationUsToFrames(actualSpeedPresentationDiff);
|
||||
// The position of the frame that's currently being presented.
|
||||
long currentFramePosition = audioTrackUtil.getTimestampFramePosition() + framesDiff;
|
||||
currentPositionUs = framesToDurationUs(currentFramePosition) + startMediaTimeUs;
|
||||
|
|
@ -652,9 +658,20 @@ public final class AudioTrack {
|
|||
public boolean hasPendingData() {
|
||||
return isInitialized()
|
||||
&& (getSubmittedFrames() > audioTrackUtil.getPlaybackHeadPosition()
|
||||
|| overrideHasPendingData());
|
||||
|| overrideHasPendingData());
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the playback parameters. Only available for SDK_INT >= 23
|
||||
*
|
||||
* @throws UnsupportedOperationException if the Playback Parameters are not supported. That is,
|
||||
* SDK_INT < 23.
|
||||
*/
|
||||
public void setPlaybackParams(PlaybackParams playbackParams) {
|
||||
audioTrackUtil.setPlaybackParameters(playbackParams);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Sets the playback volume.
|
||||
*/
|
||||
|
|
@ -1100,6 +1117,27 @@ public final class AudioTrack {
|
|||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the Playback Parameters to be used by the underlying {@link android.media.AudioTrack}.
|
||||
*
|
||||
* @param playbackParams to be used by the {@link android.media.AudioTrack}.
|
||||
* @throws UnsupportedOperationException If Playback Parameters are not supported
|
||||
* (i.e. SDK_INT < 23).
|
||||
*/
|
||||
public void setPlaybackParameters(PlaybackParams playbackParams) {
|
||||
throw new UnsupportedOperationException();
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the configured playback speed according to the used Playback Parameters. If these are
|
||||
* not supported, 1.0f(normal speed) is returned.
|
||||
*
|
||||
* @return The speed factor used by the underlying {@link android.media.AudioTrack}.
|
||||
*/
|
||||
public float getPlaybackSpeed() {
|
||||
return 1.0f;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@TargetApi(19)
|
||||
|
|
@ -1151,4 +1189,31 @@ public final class AudioTrack {
|
|||
|
||||
}
|
||||
|
||||
@TargetApi(23)
|
||||
private static class AudioTrackUtilV23 extends AudioTrackUtilV19 {
|
||||
|
||||
private PlaybackParams playbackParams;
|
||||
|
||||
@Override
|
||||
public void reconfigure(android.media.AudioTrack audioTrack,
|
||||
boolean needsPassthroughWorkaround) {
|
||||
super.reconfigure(audioTrack, needsPassthroughWorkaround);
|
||||
setPlaybackParameters(playbackParams);
|
||||
}
|
||||
|
||||
public void setPlaybackParameters(PlaybackParams playbackParams) {
|
||||
this.playbackParams = playbackParams;
|
||||
if (audioTrack != null && playbackParams != null) {
|
||||
audioTrack.setPlaybackParams(playbackParams);
|
||||
}
|
||||
}
|
||||
|
||||
public float getPlaybackSpeed() {
|
||||
if (playbackParams != null) {
|
||||
return playbackParams.getSpeed();
|
||||
} else {
|
||||
return 1.0f;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue