Loading api/current.txt +11 −0 Original line number Diff line number Diff line Loading @@ -22662,6 +22662,7 @@ package android.media { method public boolean isBluetoothScoOn(); method public boolean isMicrophoneMute(); method public boolean isMusicActive(); method public static boolean isOffloadedPlaybackSupported(android.media.AudioFormat); method public boolean isSpeakerphoneOn(); method public boolean isStreamMute(int); method public boolean isVolumeFixed(); Loading Loading @@ -22983,6 +22984,7 @@ package android.media { method public int getUnderrunCount(); method public void pause() throws java.lang.IllegalStateException; method public void play() throws java.lang.IllegalStateException; method public void registerStreamEventCallback(java.util.concurrent.Executor, android.media.AudioTrack.StreamEventCallback); method public void release(); method public int reloadStaticData(); method public void removeOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener); Loading @@ -23003,6 +23005,7 @@ package android.media { method public deprecated int setStereoVolume(float, float); method public int setVolume(float); method public void stop() throws java.lang.IllegalStateException; method public void unregisterStreamEventCallback(android.media.AudioTrack.StreamEventCallback); method public int write(byte[], int, int); method public int write(byte[], int, int, int); method public int write(short[], int, int); Loading Loading @@ -23036,6 +23039,7 @@ package android.media { method public android.media.AudioTrack.Builder setAudioAttributes(android.media.AudioAttributes) throws java.lang.IllegalArgumentException; method public android.media.AudioTrack.Builder setAudioFormat(android.media.AudioFormat) throws java.lang.IllegalArgumentException; method public android.media.AudioTrack.Builder setBufferSizeInBytes(int) throws java.lang.IllegalArgumentException; method public android.media.AudioTrack.Builder setOffloadedPlayback(boolean); method public android.media.AudioTrack.Builder setPerformanceMode(int); method public android.media.AudioTrack.Builder setSessionId(int) throws java.lang.IllegalArgumentException; method public android.media.AudioTrack.Builder setTransferMode(int) throws java.lang.IllegalArgumentException; Loading @@ -23059,6 +23063,13 @@ package android.media { method public default void onRoutingChanged(android.media.AudioRouting); } public static abstract class AudioTrack.StreamEventCallback { ctor public AudioTrack.StreamEventCallback(); method public void onDataRequest(android.media.AudioTrack, int); method public void onPresentationEnded(android.media.AudioTrack); method public void onTearDown(android.media.AudioTrack); } public class CamcorderProfile { method public static android.media.CamcorderProfile get(int); method public static android.media.CamcorderProfile get(int, int); core/jni/android_media_AudioFormat.h +3 −4 Original line number Diff line number Diff line Loading @@ -128,9 +128,8 @@ static inline int audioFormatFromNative(audio_format_t nativeFormat) return ENCODING_DOLBY_TRUEHD; case AUDIO_FORMAT_AAC_ELD: return ENCODING_AAC_ELD; // FIXME needs addition of AUDIO_FORMAT_AAC_XHE //case AUDIO_FORMAT_AAC_XHE: // return ENCODING_AAC_XHE; case AUDIO_FORMAT_AAC_XHE: return ENCODING_AAC_XHE; case AUDIO_FORMAT_AC4: return ENCODING_AC4; case AUDIO_FORMAT_E_AC3_JOC: Loading core/jni/android_media_AudioTrack.cpp +40 −27 Original line number Diff line number Diff line Loading @@ -29,6 +29,7 @@ #include <media/AudioSystem.h> #include <media/AudioTrack.h> #include <android-base/macros.h> #include <binder/MemoryHeapBase.h> #include <binder/MemoryBase.h> Loading Loading @@ -134,41 +135,53 @@ static void audioCallback(int event, void* user, void *info) { callbackInfo->busy = true; } // used as default argument when event callback doesn't have any, or number of // frames for EVENT_CAN_WRITE_MORE_DATA int arg = 0; bool postEvent = false; switch (event) { // Offload only events case AudioTrack::EVENT_STREAM_END: case AudioTrack::EVENT_MORE_DATA: // a.k.a. tear down case AudioTrack::EVENT_NEW_IAUDIOTRACK: case AudioTrack::EVENT_CAN_WRITE_MORE_DATA: // this event will read the info return parameter of the callback: // for JNI offload, use the returned size to indicate: // 1/ no data is returned through callback, as it's all done through write() // 2/ do not wait as AudioTrack does when it receives 0 bytes if (callbackInfo->isOffload) { JNIEnv *env = AndroidRuntime::getJNIEnv(); if (user != NULL && env != NULL) { env->CallStaticVoidMethod( callbackInfo->audioTrack_class, javaAudioTrackFields.postNativeEventInJava, callbackInfo->audioTrack_ref, event, 0,0, NULL); if (env->ExceptionCheck()) { env->ExceptionDescribe(); env->ExceptionClear(); AudioTrack::Buffer* pBuffer = (AudioTrack::Buffer*) info; const size_t availableForWrite = pBuffer->size; arg = availableForWrite > INT32_MAX ? INT32_MAX : (int) availableForWrite; pBuffer->size = 0; } FALLTHROUGH_INTENDED; case AudioTrack::EVENT_STREAM_END: case AudioTrack::EVENT_NEW_IAUDIOTRACK: // a.k.a. tear down if (callbackInfo->isOffload) { postEvent = true; } } break; break; // PCM and offload events case AudioTrack::EVENT_MARKER: case AudioTrack::EVENT_NEW_POS: { case AudioTrack::EVENT_NEW_POS: postEvent = true; break; default: // event will not be posted break; } if (postEvent) { JNIEnv *env = AndroidRuntime::getJNIEnv(); if (user != NULL && env != NULL) { if (env != NULL) { env->CallStaticVoidMethod( callbackInfo->audioTrack_class, javaAudioTrackFields.postNativeEventInJava, callbackInfo->audioTrack_ref, event, 0,0, NULL); callbackInfo->audioTrack_ref, event, arg, 0, NULL); if (env->ExceptionCheck()) { env->ExceptionDescribe(); env->ExceptionClear(); } } } break; } { Loading Loading @@ -215,10 +228,10 @@ android_media_AudioTrack_setup(JNIEnv *env, jobject thiz, jobject weak_this, job jint audioFormat, jint buffSizeInBytes, jint memoryMode, jintArray jSession, jlong nativeAudioTrack, jboolean offload) { ALOGV("sampleRates=%p, channel mask=%x, index mask=%x, audioFormat(Java)=%d, buffSize=%d" "nativeAudioTrack=0x%" PRIX64, ALOGV("sampleRates=%p, channel mask=%x, index mask=%x, audioFormat(Java)=%d, buffSize=%d," " nativeAudioTrack=0x%" PRIX64 ", offload=%d", jSampleRate, channelPositionMask, channelIndexMask, audioFormat, buffSizeInBytes, nativeAudioTrack); nativeAudioTrack, offload); sp<AudioTrack> lpTrack = 0; Loading Loading @@ -318,7 +331,7 @@ android_media_AudioTrack_setup(JNIEnv *env, jobject thiz, jobject weak_this, job lpJniStorage->mCallbackData.busy = false; audio_offload_info_t offloadInfo; if (offload) { if (offload == JNI_TRUE) { offloadInfo = AUDIO_INFO_INITIALIZER; offloadInfo.format = format; offloadInfo.sample_rate = sampleRateInHertz; Loading @@ -331,23 +344,23 @@ android_media_AudioTrack_setup(JNIEnv *env, jobject thiz, jobject weak_this, job status_t status = NO_ERROR; switch (memoryMode) { case MODE_STREAM: status = lpTrack->set( AUDIO_STREAM_DEFAULT,// stream type, but more info conveyed in paa (last argument) sampleRateInHertz, format,// word length, PCM nativeChannelMask, frameCount, AUDIO_OUTPUT_FLAG_NONE, offload ? 0 : frameCount, offload ? AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD : AUDIO_OUTPUT_FLAG_NONE, audioCallback, &(lpJniStorage->mCallbackData),//callback, callback data (user) 0,// notificationFrames == 0 since not using EVENT_MORE_DATA to feed the AudioTrack 0,// shared mem true,// thread can call Java sessionId,// audio session ID AudioTrack::TRANSFER_SYNC, offload ? AudioTrack::TRANSFER_SYNC_NOTIF_CALLBACK : AudioTrack::TRANSFER_SYNC, offload ? &offloadInfo : NULL, -1, -1, // default uid, pid values paa); break; case MODE_STATIC: Loading media/java/android/media/AudioFormat.java +1 −0 Original line number Diff line number Diff line Loading @@ -1068,6 +1068,7 @@ public final class AudioFormat implements Parcelable { ENCODING_E_AC3_JOC, ENCODING_DTS, ENCODING_DTS_HD, ENCODING_MP3, ENCODING_IEC61937, ENCODING_AAC_HE_V1, ENCODING_AAC_HE_V2, Loading media/java/android/media/AudioManager.java +10 −4 Original line number Diff line number Diff line Loading @@ -1379,14 +1379,20 @@ public class AudioManager { //==================================================================== // Offload query /** * @hide * Returns whether offloaded playback of an audio format is supported on the device. * Offloaded playback is where the decoding of an audio stream is not competing with other * software resources. In general, it is supported by dedicated hardware, such as audio DSPs. * <p>Offloaded playback is the feature where the decoding and playback of an audio stream * is not competing with other software resources. In general, it is supported by dedicated * hardware, such as audio DSPs. * <p>Note that this query only provides information about the support of an audio format, * it does not indicate whether the resources necessary for the offloaded playback are * available at that instant. * @param format the audio format (codec, sample rate, channels) being checked. * @return true if the given audio format can be offloaded. */ public boolean isOffloadedPlaybackSupported(@NonNull AudioFormat format) { public static boolean isOffloadedPlaybackSupported(@NonNull AudioFormat format) { if (format == null) { throw new IllegalArgumentException("Illegal null AudioFormat"); } return AudioSystem.isOffloadSupported(format); } Loading Loading
api/current.txt +11 −0 Original line number Diff line number Diff line Loading @@ -22662,6 +22662,7 @@ package android.media { method public boolean isBluetoothScoOn(); method public boolean isMicrophoneMute(); method public boolean isMusicActive(); method public static boolean isOffloadedPlaybackSupported(android.media.AudioFormat); method public boolean isSpeakerphoneOn(); method public boolean isStreamMute(int); method public boolean isVolumeFixed(); Loading Loading @@ -22983,6 +22984,7 @@ package android.media { method public int getUnderrunCount(); method public void pause() throws java.lang.IllegalStateException; method public void play() throws java.lang.IllegalStateException; method public void registerStreamEventCallback(java.util.concurrent.Executor, android.media.AudioTrack.StreamEventCallback); method public void release(); method public int reloadStaticData(); method public void removeOnRoutingChangedListener(android.media.AudioRouting.OnRoutingChangedListener); Loading @@ -23003,6 +23005,7 @@ package android.media { method public deprecated int setStereoVolume(float, float); method public int setVolume(float); method public void stop() throws java.lang.IllegalStateException; method public void unregisterStreamEventCallback(android.media.AudioTrack.StreamEventCallback); method public int write(byte[], int, int); method public int write(byte[], int, int, int); method public int write(short[], int, int); Loading Loading @@ -23036,6 +23039,7 @@ package android.media { method public android.media.AudioTrack.Builder setAudioAttributes(android.media.AudioAttributes) throws java.lang.IllegalArgumentException; method public android.media.AudioTrack.Builder setAudioFormat(android.media.AudioFormat) throws java.lang.IllegalArgumentException; method public android.media.AudioTrack.Builder setBufferSizeInBytes(int) throws java.lang.IllegalArgumentException; method public android.media.AudioTrack.Builder setOffloadedPlayback(boolean); method public android.media.AudioTrack.Builder setPerformanceMode(int); method public android.media.AudioTrack.Builder setSessionId(int) throws java.lang.IllegalArgumentException; method public android.media.AudioTrack.Builder setTransferMode(int) throws java.lang.IllegalArgumentException; Loading @@ -23059,6 +23063,13 @@ package android.media { method public default void onRoutingChanged(android.media.AudioRouting); } public static abstract class AudioTrack.StreamEventCallback { ctor public AudioTrack.StreamEventCallback(); method public void onDataRequest(android.media.AudioTrack, int); method public void onPresentationEnded(android.media.AudioTrack); method public void onTearDown(android.media.AudioTrack); } public class CamcorderProfile { method public static android.media.CamcorderProfile get(int); method public static android.media.CamcorderProfile get(int, int);
core/jni/android_media_AudioFormat.h +3 −4 Original line number Diff line number Diff line Loading @@ -128,9 +128,8 @@ static inline int audioFormatFromNative(audio_format_t nativeFormat) return ENCODING_DOLBY_TRUEHD; case AUDIO_FORMAT_AAC_ELD: return ENCODING_AAC_ELD; // FIXME needs addition of AUDIO_FORMAT_AAC_XHE //case AUDIO_FORMAT_AAC_XHE: // return ENCODING_AAC_XHE; case AUDIO_FORMAT_AAC_XHE: return ENCODING_AAC_XHE; case AUDIO_FORMAT_AC4: return ENCODING_AC4; case AUDIO_FORMAT_E_AC3_JOC: Loading
core/jni/android_media_AudioTrack.cpp +40 −27 Original line number Diff line number Diff line Loading @@ -29,6 +29,7 @@ #include <media/AudioSystem.h> #include <media/AudioTrack.h> #include <android-base/macros.h> #include <binder/MemoryHeapBase.h> #include <binder/MemoryBase.h> Loading Loading @@ -134,41 +135,53 @@ static void audioCallback(int event, void* user, void *info) { callbackInfo->busy = true; } // used as default argument when event callback doesn't have any, or number of // frames for EVENT_CAN_WRITE_MORE_DATA int arg = 0; bool postEvent = false; switch (event) { // Offload only events case AudioTrack::EVENT_STREAM_END: case AudioTrack::EVENT_MORE_DATA: // a.k.a. tear down case AudioTrack::EVENT_NEW_IAUDIOTRACK: case AudioTrack::EVENT_CAN_WRITE_MORE_DATA: // this event will read the info return parameter of the callback: // for JNI offload, use the returned size to indicate: // 1/ no data is returned through callback, as it's all done through write() // 2/ do not wait as AudioTrack does when it receives 0 bytes if (callbackInfo->isOffload) { JNIEnv *env = AndroidRuntime::getJNIEnv(); if (user != NULL && env != NULL) { env->CallStaticVoidMethod( callbackInfo->audioTrack_class, javaAudioTrackFields.postNativeEventInJava, callbackInfo->audioTrack_ref, event, 0,0, NULL); if (env->ExceptionCheck()) { env->ExceptionDescribe(); env->ExceptionClear(); AudioTrack::Buffer* pBuffer = (AudioTrack::Buffer*) info; const size_t availableForWrite = pBuffer->size; arg = availableForWrite > INT32_MAX ? INT32_MAX : (int) availableForWrite; pBuffer->size = 0; } FALLTHROUGH_INTENDED; case AudioTrack::EVENT_STREAM_END: case AudioTrack::EVENT_NEW_IAUDIOTRACK: // a.k.a. tear down if (callbackInfo->isOffload) { postEvent = true; } } break; break; // PCM and offload events case AudioTrack::EVENT_MARKER: case AudioTrack::EVENT_NEW_POS: { case AudioTrack::EVENT_NEW_POS: postEvent = true; break; default: // event will not be posted break; } if (postEvent) { JNIEnv *env = AndroidRuntime::getJNIEnv(); if (user != NULL && env != NULL) { if (env != NULL) { env->CallStaticVoidMethod( callbackInfo->audioTrack_class, javaAudioTrackFields.postNativeEventInJava, callbackInfo->audioTrack_ref, event, 0,0, NULL); callbackInfo->audioTrack_ref, event, arg, 0, NULL); if (env->ExceptionCheck()) { env->ExceptionDescribe(); env->ExceptionClear(); } } } break; } { Loading Loading @@ -215,10 +228,10 @@ android_media_AudioTrack_setup(JNIEnv *env, jobject thiz, jobject weak_this, job jint audioFormat, jint buffSizeInBytes, jint memoryMode, jintArray jSession, jlong nativeAudioTrack, jboolean offload) { ALOGV("sampleRates=%p, channel mask=%x, index mask=%x, audioFormat(Java)=%d, buffSize=%d" "nativeAudioTrack=0x%" PRIX64, ALOGV("sampleRates=%p, channel mask=%x, index mask=%x, audioFormat(Java)=%d, buffSize=%d," " nativeAudioTrack=0x%" PRIX64 ", offload=%d", jSampleRate, channelPositionMask, channelIndexMask, audioFormat, buffSizeInBytes, nativeAudioTrack); nativeAudioTrack, offload); sp<AudioTrack> lpTrack = 0; Loading Loading @@ -318,7 +331,7 @@ android_media_AudioTrack_setup(JNIEnv *env, jobject thiz, jobject weak_this, job lpJniStorage->mCallbackData.busy = false; audio_offload_info_t offloadInfo; if (offload) { if (offload == JNI_TRUE) { offloadInfo = AUDIO_INFO_INITIALIZER; offloadInfo.format = format; offloadInfo.sample_rate = sampleRateInHertz; Loading @@ -331,23 +344,23 @@ android_media_AudioTrack_setup(JNIEnv *env, jobject thiz, jobject weak_this, job status_t status = NO_ERROR; switch (memoryMode) { case MODE_STREAM: status = lpTrack->set( AUDIO_STREAM_DEFAULT,// stream type, but more info conveyed in paa (last argument) sampleRateInHertz, format,// word length, PCM nativeChannelMask, frameCount, AUDIO_OUTPUT_FLAG_NONE, offload ? 0 : frameCount, offload ? AUDIO_OUTPUT_FLAG_COMPRESS_OFFLOAD : AUDIO_OUTPUT_FLAG_NONE, audioCallback, &(lpJniStorage->mCallbackData),//callback, callback data (user) 0,// notificationFrames == 0 since not using EVENT_MORE_DATA to feed the AudioTrack 0,// shared mem true,// thread can call Java sessionId,// audio session ID AudioTrack::TRANSFER_SYNC, offload ? AudioTrack::TRANSFER_SYNC_NOTIF_CALLBACK : AudioTrack::TRANSFER_SYNC, offload ? &offloadInfo : NULL, -1, -1, // default uid, pid values paa); break; case MODE_STATIC: Loading
media/java/android/media/AudioFormat.java +1 −0 Original line number Diff line number Diff line Loading @@ -1068,6 +1068,7 @@ public final class AudioFormat implements Parcelable { ENCODING_E_AC3_JOC, ENCODING_DTS, ENCODING_DTS_HD, ENCODING_MP3, ENCODING_IEC61937, ENCODING_AAC_HE_V1, ENCODING_AAC_HE_V2, Loading
media/java/android/media/AudioManager.java +10 −4 Original line number Diff line number Diff line Loading @@ -1379,14 +1379,20 @@ public class AudioManager { //==================================================================== // Offload query /** * @hide * Returns whether offloaded playback of an audio format is supported on the device. * Offloaded playback is where the decoding of an audio stream is not competing with other * software resources. In general, it is supported by dedicated hardware, such as audio DSPs. * <p>Offloaded playback is the feature where the decoding and playback of an audio stream * is not competing with other software resources. In general, it is supported by dedicated * hardware, such as audio DSPs. * <p>Note that this query only provides information about the support of an audio format, * it does not indicate whether the resources necessary for the offloaded playback are * available at that instant. * @param format the audio format (codec, sample rate, channels) being checked. * @return true if the given audio format can be offloaded. */ public boolean isOffloadedPlaybackSupported(@NonNull AudioFormat format) { public static boolean isOffloadedPlaybackSupported(@NonNull AudioFormat format) { if (format == null) { throw new IllegalArgumentException("Illegal null AudioFormat"); } return AudioSystem.isOffloadSupported(format); } Loading