Mercurial > sdl-ios-xcode
diff src/SDL_android.cpp @ 4996:8d7315668e35
Fixed audio buffer lifecycle and implemented audio shutdown
author | Sam Lantinga <slouken@libsdl.org> |
---|---|
date | Thu, 13 Jan 2011 12:32:55 -0800 |
parents | 9f9bea41e88f |
children | a21501393bef |
line wrap: on
line diff
--- a/src/SDL_android.cpp Thu Jan 13 11:14:20 2011 -0800 +++ b/src/SDL_android.cpp Thu Jan 13 12:32:55 2011 -0800 @@ -55,6 +55,7 @@ static jmethodID midAudioInit; static jmethodID midAudioWriteShortBuffer; static jmethodID midAudioWriteByteBuffer; +static jmethodID midAudioQuit; // Accelerometer data storage float fLastAccelerometer[3]; @@ -83,13 +84,14 @@ mActivityInstance = cls; midCreateGLContext = mEnv->GetStaticMethodID(cls,"createGLContext","()V"); midFlipBuffers = mEnv->GetStaticMethodID(cls,"flipBuffers","()V"); - midAudioInit = mEnv->GetStaticMethodID(cls, "audioInit", "(IZZI)Ljava/lang/Object;"); - midAudioWriteShortBuffer = mEnv->GetStaticMethodID(cls, "audioWriteShortBuffer", "([S)V"); - midAudioWriteByteBuffer = mEnv->GetStaticMethodID(cls, "audioWriteByteBuffer", "([B)V"); + midAudioInit = mEnv->GetStaticMethodID(cls, "audioInit", "(IZZI)Ljava/lang/Object;"); + midAudioWriteShortBuffer = mEnv->GetStaticMethodID(cls, "audioWriteShortBuffer", "([S)V"); + midAudioWriteByteBuffer = mEnv->GetStaticMethodID(cls, "audioWriteByteBuffer", "([B)V"); + midAudioQuit = mEnv->GetStaticMethodID(cls, "audioQuit", "()V"); if(!midCreateGLContext || !midFlipBuffers || !midAudioInit || - !midAudioWriteShortBuffer || !midAudioWriteByteBuffer) { - __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL: Couldn't locate Java callbacks, check that they're named and typed correctly"); + !midAudioWriteShortBuffer || !midAudioWriteByteBuffer || !midAudioQuit) { + __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL: Couldn't locate Java callbacks, check that they're named and typed correctly"); } } @@ -150,8 +152,8 @@ extern "C" void Java_org_libsdl_app_SDLActivity_nativeRunAudioThread( JNIEnv* env) { - mVM->AttachCurrentThread(&mAudioEnv, NULL); - Android_RunAudioThread(); + mVM->AttachCurrentThread(&mAudioEnv, NULL); + Android_RunAudioThread(); } @@ -171,78 +173,69 @@ // // Audio support // -static jint audioBufferFrames = 0; -static bool audioBuffer16Bit = false; -static bool audioBufferStereo = false; - -static jobject audioBuffer; -static void * audioPinnedBuffer; +static jboolean audioBuffer16Bit = JNI_FALSE; +static jboolean audioBufferStereo = JNI_FALSE; +static jobject audioBuffer = NULL; +static void* audioBufferPinned = NULL; extern "C" int Android_JNI_OpenAudioDevice(int sampleRate, int is16Bit, int channelCount, int desiredBufferFrames) { - __android_log_print(ANDROID_LOG_VERBOSE, "SDL", "SDL audio: opening device"); - audioBuffer16Bit = is16Bit; - audioBufferStereo = channelCount > 1; + int audioBufferFrames; + + __android_log_print(ANDROID_LOG_VERBOSE, "SDL", "SDL audio: opening device"); + audioBuffer16Bit = is16Bit; + audioBufferStereo = channelCount > 1; - audioBuffer = mEnv->CallStaticObjectMethod(mActivityInstance, midAudioInit, sampleRate, audioBuffer16Bit, audioBufferStereo, desiredBufferFrames); - audioBuffer = mEnv->NewGlobalRef(audioBuffer); + audioBuffer = mEnv->CallStaticObjectMethod(mActivityInstance, midAudioInit, sampleRate, audioBuffer16Bit, audioBufferStereo, desiredBufferFrames); + + if (audioBuffer == NULL) { + __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL audio: didn't get back a good audio buffer!"); + return 0; + } + audioBuffer = mEnv->NewGlobalRef(audioBuffer); - if (audioBuffer == NULL) { - __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL audio: didn't get back a good audio buffer!"); - return 0; - } + jboolean isCopy = JNI_FALSE; + if (audioBuffer16Bit) { + audioBufferPinned = mEnv->GetShortArrayElements((jshortArray)audioBuffer, &isCopy); + audioBufferFrames = mEnv->GetArrayLength((jshortArray)audioBuffer); + } else { + audioBufferPinned = mEnv->GetByteArrayElements((jbyteArray)audioBuffer, &isCopy); + audioBufferFrames = mEnv->GetArrayLength((jbyteArray)audioBuffer); + } + if (audioBufferStereo) { + audioBufferFrames /= 2; + } - if (audioBufferStereo) { - audioBufferFrames = mEnv->GetArrayLength((jshortArray)audioBuffer) / 2; - } else { - audioBufferFrames = mEnv->GetArrayLength((jbyteArray)audioBuffer); - } - - return audioBufferFrames; + return audioBufferFrames; } -extern "C" void * Android_JNI_PinAudioBuffer() +extern "C" void * Android_JNI_GetAudioBuffer() { - jboolean isCopy = JNI_FALSE; - - if (audioPinnedBuffer != NULL) { - return audioPinnedBuffer; - } - - if (audioBuffer16Bit) { - audioPinnedBuffer = mAudioEnv->GetShortArrayElements((jshortArray)audioBuffer, &isCopy); - } else { - audioPinnedBuffer = mAudioEnv->GetByteArrayElements((jbyteArray)audioBuffer, &isCopy); - } - - return audioPinnedBuffer; + //jboolean isCopy = JNI_FALSE; + //audioBufferPinned = mAudioEnv->GetPrimitiveArrayCritical((jarray)audioBuffer, &isCopy); + return audioBufferPinned; } -extern "C" void Android_JNI_WriteAudioBufferAndUnpin() +extern "C" void Android_JNI_WriteAudioBuffer() { - if (audioPinnedBuffer == NULL) { - return; - } + //mAudioEnv->ReleasePrimitiveArrayCritical((jarray)audioBuffer, audioBufferPinned, 0); + if (audioBuffer16Bit) { + mAudioEnv->ReleaseShortArrayElements((jshortArray)audioBuffer, (jshort *)audioBufferPinned, JNI_COMMIT); + mAudioEnv->CallStaticVoidMethod(mActivityInstance, midAudioWriteShortBuffer, (jshortArray)audioBuffer); + } else { + mAudioEnv->ReleaseByteArrayElements((jbyteArray)audioBuffer, (jbyte *)audioBufferPinned, JNI_COMMIT); + mAudioEnv->CallStaticVoidMethod(mActivityInstance, midAudioWriteByteBuffer, (jbyteArray)audioBuffer); + } - if (audioBuffer16Bit) { - mAudioEnv->ReleaseShortArrayElements((jshortArray)audioBuffer, (jshort *)audioPinnedBuffer, JNI_COMMIT); - mAudioEnv->CallStaticVoidMethod(mActivityInstance, midAudioWriteShortBuffer, (jshortArray)audioBuffer); - } else { - mAudioEnv->ReleaseByteArrayElements((jbyteArray)audioBuffer, (jbyte *)audioPinnedBuffer, JNI_COMMIT); - mAudioEnv->CallStaticVoidMethod(mActivityInstance, midAudioWriteByteBuffer, (jbyteArray)audioBuffer); - } - - audioPinnedBuffer = NULL; + /* JNI_COMMIT means the changes are committed to the VM but the buffer remains pinned */ } extern "C" void Android_JNI_CloseAudioDevice() { - if (audioBuffer) { - mEnv->DeleteGlobalRef(audioBuffer); - audioBuffer = NULL; - } + mEnv->CallStaticVoidMethod(mActivityInstance, midAudioQuit); - // TODO: Implement + mEnv->DeleteGlobalRef(audioBuffer); + audioBuffer = NULL; } /* vi: set ts=4 sw=4 expandtab: */