summaryrefslogtreecommitdiff
path: root/Source/3rdParty/SDL2/src/core/android
diff options
context:
space:
mode:
authorchai <chaifix@163.com>2019-01-31 18:38:35 +0800
committerchai <chaifix@163.com>2019-01-31 18:38:35 +0800
commit2ec55fd974a63b705a4777c256d2222c874fa043 (patch)
tree48f1fea59ee9fc713a28a9aac3f05b98dc5ae66f /Source/3rdParty/SDL2/src/core/android
parentc581dfbf1e849f393861d15e82aa6446c0c1c310 (diff)
*SDL project
Diffstat (limited to 'Source/3rdParty/SDL2/src/core/android')
-rw-r--r--Source/3rdParty/SDL2/src/core/android/SDL_android.c426
-rw-r--r--Source/3rdParty/SDL2/src/core/android/SDL_android.h29
2 files changed, 354 insertions, 101 deletions
diff --git a/Source/3rdParty/SDL2/src/core/android/SDL_android.c b/Source/3rdParty/SDL2/src/core/android/SDL_android.c
index c40c676..a56575e 100644
--- a/Source/3rdParty/SDL2/src/core/android/SDL_android.c
+++ b/Source/3rdParty/SDL2/src/core/android/SDL_android.c
@@ -61,6 +61,10 @@
#define SDL_JAVA_CONTROLLER_INTERFACE(function) CONCAT1(SDL_JAVA_PREFIX, SDLControllerManager, function)
#define SDL_JAVA_INTERFACE_INPUT_CONNECTION(function) CONCAT1(SDL_JAVA_PREFIX, SDLInputConnection, function)
+/* Audio encoding definitions */
+#define ENCODING_PCM_8BIT 3
+#define ENCODING_PCM_16BIT 2
+#define ENCODING_PCM_FLOAT 4
/* Java class SDLActivity */
JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(nativeSetupJNI)(
@@ -76,7 +80,8 @@ JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeDropFile)(
JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeResize)(
JNIEnv* env, jclass jcls,
- jint width, jint height, jint format, jfloat rate);
+ jint surfaceWidth, jint surfaceHeight,
+ jint deviceWidth, jint deviceHeight, jint format, jfloat rate);
JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeSurfaceChanged)(
JNIEnv* env, jclass jcls);
@@ -102,7 +107,7 @@ JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeTouch)(
JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeMouse)(
JNIEnv* env, jclass jcls,
- jint button, jint action, jfloat x, jfloat y);
+ jint button, jint action, jfloat x, jfloat y, jboolean relative);
JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeAccel)(
JNIEnv* env, jclass jcls,
@@ -134,11 +139,19 @@ JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(nativeSetenv)(
JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(nativeEnvironmentVariablesSet)(
JNIEnv* env, jclass cls);
+JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeOrientationChanged)(
+ JNIEnv* env, jclass cls,
+ jint orientation);
+
/* Java class SDLInputConnection */
JNIEXPORT void JNICALL SDL_JAVA_INTERFACE_INPUT_CONNECTION(nativeCommitText)(
JNIEnv* env, jclass cls,
jstring text, jint newCursorPosition);
+JNIEXPORT void JNICALL SDL_JAVA_INTERFACE_INPUT_CONNECTION(nativeGenerateScancodeForUnichar)(
+ JNIEnv* env, jclass cls,
+ jchar chUnicode);
+
JNIEXPORT void JNICALL SDL_JAVA_INTERFACE_INPUT_CONNECTION(nativeSetComposingText)(
JNIEnv* env, jclass cls,
jstring text, jint newCursorPosition);
@@ -169,8 +182,8 @@ JNIEXPORT void JNICALL SDL_JAVA_CONTROLLER_INTERFACE(onNativeHat)(
JNIEXPORT jint JNICALL SDL_JAVA_CONTROLLER_INTERFACE(nativeAddJoystick)(
JNIEnv* env, jclass jcls,
- jint device_id, jstring device_name, jstring device_desc, jint is_accelerometer,
- jint nbuttons, jint naxes, jint nhats, jint nballs);
+ jint device_id, jstring device_name, jstring device_desc, jint vendor_id, jint product_id,
+ jboolean is_accelerometer, jint button_mask, jint naxes, jint nhats, jint nballs);
JNIEXPORT jint JNICALL SDL_JAVA_CONTROLLER_INTERFACE(nativeRemoveJoystick)(
JNIEnv* env, jclass jcls,
@@ -190,6 +203,7 @@ JNIEXPORT jint JNICALL SDL_JAVA_CONTROLLER_INTERFACE(nativeRemoveHaptic)(
/* #define DEBUG_JNI */
static void Android_JNI_ThreadDestroyed(void*);
+static void checkJNIReady(void);
/*******************************************************************************
This file links the Java side of Android with libsdl
@@ -212,7 +226,11 @@ static jmethodID midSetActivityTitle;
static jmethodID midSetWindowStyle;
static jmethodID midSetOrientation;
static jmethodID midGetContext;
+static jmethodID midIsTablet;
static jmethodID midIsAndroidTV;
+static jmethodID midIsChromebook;
+static jmethodID midIsDeXMode;
+static jmethodID midManualBackButton;
static jmethodID midInputGetInputDeviceIds;
static jmethodID midSendMessage;
static jmethodID midShowTextInput;
@@ -223,18 +241,25 @@ static jmethodID midClipboardHasText;
static jmethodID midOpenAPKExpansionInputStream;
static jmethodID midGetManifestEnvironmentVariables;
static jmethodID midGetDisplayDPI;
+static jmethodID midCreateCustomCursor;
+static jmethodID midSetCustomCursor;
+static jmethodID midSetSystemCursor;
+static jmethodID midSupportsRelativeMouse;
+static jmethodID midSetRelativeMouseEnabled;
/* audio manager */
static jclass mAudioManagerClass;
/* method signatures */
static jmethodID midAudioOpen;
-static jmethodID midAudioWriteShortBuffer;
static jmethodID midAudioWriteByteBuffer;
+static jmethodID midAudioWriteShortBuffer;
+static jmethodID midAudioWriteFloatBuffer;
static jmethodID midAudioClose;
static jmethodID midCaptureOpen;
-static jmethodID midCaptureReadShortBuffer;
static jmethodID midCaptureReadByteBuffer;
+static jmethodID midCaptureReadShortBuffer;
+static jmethodID midCaptureReadFloatBuffer;
static jmethodID midCaptureClose;
/* controller manager */
@@ -244,6 +269,7 @@ static jclass mControllerManagerClass;
static jmethodID midPollInputDevices;
static jmethodID midPollHapticDevices;
static jmethodID midHapticRun;
+static jmethodID midHapticStop;
/* static fields */
static jfieldID fidSeparateMouseAndTouch;
@@ -309,8 +335,16 @@ JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(nativeSetupJNI)(JNIEnv* mEnv, jclass c
"setOrientation","(IIZLjava/lang/String;)V");
midGetContext = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass,
"getContext","()Landroid/content/Context;");
+ midIsTablet = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass,
+ "isTablet", "()Z");
midIsAndroidTV = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass,
"isAndroidTV","()Z");
+ midIsChromebook = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass,
+ "isChromebook", "()Z");
+ midIsDeXMode = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass,
+ "isDeXMode", "()Z");
+ midManualBackButton = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass,
+ "manualBackButton", "()V");
midInputGetInputDeviceIds = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass,
"inputGetInputDeviceIds", "(I)[I");
midSendMessage = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass,
@@ -332,13 +366,21 @@ JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(nativeSetupJNI)(JNIEnv* mEnv, jclass c
"getManifestEnvironmentVariables", "()Z");
midGetDisplayDPI = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass, "getDisplayDPI", "()Landroid/util/DisplayMetrics;");
- midGetDisplayDPI = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass, "getDisplayDPI", "()Landroid/util/DisplayMetrics;");
+ midCreateCustomCursor = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass, "createCustomCursor", "([IIIII)I");
+ midSetCustomCursor = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass, "setCustomCursor", "(I)Z");
+ midSetSystemCursor = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass, "setSystemCursor", "(I)Z");
+
+ midSupportsRelativeMouse = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass, "supportsRelativeMouse", "()Z");
+ midSetRelativeMouseEnabled = (*mEnv)->GetStaticMethodID(mEnv, mActivityClass, "setRelativeMouseEnabled", "(Z)Z");
+
if (!midGetNativeSurface ||
- !midSetActivityTitle || !midSetWindowStyle || !midSetOrientation || !midGetContext || !midIsAndroidTV || !midInputGetInputDeviceIds ||
+ !midSetActivityTitle || !midSetWindowStyle || !midSetOrientation || !midGetContext || !midIsTablet || !midIsAndroidTV || !midInputGetInputDeviceIds ||
!midSendMessage || !midShowTextInput || !midIsScreenKeyboardShown ||
!midClipboardSetText || !midClipboardGetText || !midClipboardHasText ||
- !midOpenAPKExpansionInputStream || !midGetManifestEnvironmentVariables|| !midGetDisplayDPI) {
+ !midOpenAPKExpansionInputStream || !midGetManifestEnvironmentVariables || !midGetDisplayDPI ||
+ !midCreateCustomCursor || !midSetCustomCursor || !midSetSystemCursor || !midSupportsRelativeMouse || !midSetRelativeMouseEnabled ||
+ !midIsChromebook || !midIsDeXMode || !midManualBackButton) {
__android_log_print(ANDROID_LOG_WARN, "SDL", "Missing some Java callbacks, do you have the latest version of SDLActivity.java?");
}
@@ -361,24 +403,28 @@ JNIEXPORT void JNICALL SDL_JAVA_AUDIO_INTERFACE(nativeSetupJNI)(JNIEnv* mEnv, jc
mAudioManagerClass = (jclass)((*mEnv)->NewGlobalRef(mEnv, cls));
midAudioOpen = (*mEnv)->GetStaticMethodID(mEnv, mAudioManagerClass,
- "audioOpen", "(IZZI)I");
- midAudioWriteShortBuffer = (*mEnv)->GetStaticMethodID(mEnv, mAudioManagerClass,
- "audioWriteShortBuffer", "([S)V");
+ "audioOpen", "(IIII)[I");
midAudioWriteByteBuffer = (*mEnv)->GetStaticMethodID(mEnv, mAudioManagerClass,
"audioWriteByteBuffer", "([B)V");
+ midAudioWriteShortBuffer = (*mEnv)->GetStaticMethodID(mEnv, mAudioManagerClass,
+ "audioWriteShortBuffer", "([S)V");
+ midAudioWriteFloatBuffer = (*mEnv)->GetStaticMethodID(mEnv, mAudioManagerClass,
+ "audioWriteFloatBuffer", "([F)V");
midAudioClose = (*mEnv)->GetStaticMethodID(mEnv, mAudioManagerClass,
"audioClose", "()V");
midCaptureOpen = (*mEnv)->GetStaticMethodID(mEnv, mAudioManagerClass,
- "captureOpen", "(IZZI)I");
- midCaptureReadShortBuffer = (*mEnv)->GetStaticMethodID(mEnv, mAudioManagerClass,
- "captureReadShortBuffer", "([SZ)I");
+ "captureOpen", "(IIII)[I");
midCaptureReadByteBuffer = (*mEnv)->GetStaticMethodID(mEnv, mAudioManagerClass,
"captureReadByteBuffer", "([BZ)I");
+ midCaptureReadShortBuffer = (*mEnv)->GetStaticMethodID(mEnv, mAudioManagerClass,
+ "captureReadShortBuffer", "([SZ)I");
+ midCaptureReadFloatBuffer = (*mEnv)->GetStaticMethodID(mEnv, mAudioManagerClass,
+ "captureReadFloatBuffer", "([FZ)I");
midCaptureClose = (*mEnv)->GetStaticMethodID(mEnv, mAudioManagerClass,
"captureClose", "()V");
- if (!midAudioOpen || !midAudioWriteShortBuffer || !midAudioWriteByteBuffer || !midAudioClose ||
- !midCaptureOpen || !midCaptureReadShortBuffer || !midCaptureReadByteBuffer || !midCaptureClose) {
+ if (!midAudioOpen || !midAudioWriteByteBuffer || !midAudioWriteShortBuffer || !midAudioWriteFloatBuffer || !midAudioClose ||
+ !midCaptureOpen || !midCaptureReadByteBuffer || !midCaptureReadShortBuffer || !midCaptureReadFloatBuffer || !midCaptureClose) {
__android_log_print(ANDROID_LOG_WARN, "SDL", "Missing some Java callbacks, do you have the latest version of SDLAudioManager.java?");
}
@@ -399,9 +445,11 @@ JNIEXPORT void JNICALL SDL_JAVA_CONTROLLER_INTERFACE(nativeSetupJNI)(JNIEnv* mEn
midPollHapticDevices = (*mEnv)->GetStaticMethodID(mEnv, mControllerManagerClass,
"pollHapticDevices", "()V");
midHapticRun = (*mEnv)->GetStaticMethodID(mEnv, mControllerManagerClass,
- "hapticRun", "(II)V");
+ "hapticRun", "(IFI)V");
+ midHapticStop = (*mEnv)->GetStaticMethodID(mEnv, mControllerManagerClass,
+ "hapticStop", "(I)V");
- if (!midPollInputDevices || !midPollHapticDevices || !midHapticRun) {
+ if (!midPollInputDevices || !midPollHapticDevices || !midHapticRun || !midHapticStop) {
__android_log_print(ANDROID_LOG_WARN, "SDL", "Missing some Java callbacks, do you have the latest version of SDLControllerManager.java?");
}
@@ -503,9 +551,18 @@ JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeDropFile)(
/* Resize */
JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeResize)(
JNIEnv* env, jclass jcls,
- jint width, jint height, jint format, jfloat rate)
+ jint surfaceWidth, jint surfaceHeight,
+ jint deviceWidth, jint deviceHeight, jint format, jfloat rate)
{
- Android_SetScreenResolution(width, height, format, rate);
+ Android_SetScreenResolution(surfaceWidth, surfaceHeight, deviceWidth, deviceHeight, format, rate);
+}
+
+JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeOrientationChanged)(
+ JNIEnv *env, jclass jcls,
+ jint orientation)
+{
+ SDL_VideoDisplay *display = SDL_GetDisplay(0);
+ SDL_SendDisplayEvent(display, SDL_DISPLAYEVENT_ORIENTATION, orientation);
}
/* Paddown */
@@ -543,14 +600,15 @@ JNIEXPORT void JNICALL SDL_JAVA_CONTROLLER_INTERFACE(onNativeHat)(
JNIEXPORT jint JNICALL SDL_JAVA_CONTROLLER_INTERFACE(nativeAddJoystick)(
JNIEnv* env, jclass jcls,
- jint device_id, jstring device_name, jstring device_desc, jint is_accelerometer,
- jint nbuttons, jint naxes, jint nhats, jint nballs)
+ jint device_id, jstring device_name, jstring device_desc,
+ jint vendor_id, jint product_id, jboolean is_accelerometer,
+ jint button_mask, jint naxes, jint nhats, jint nballs)
{
int retval;
const char *name = (*env)->GetStringUTFChars(env, device_name, NULL);
const char *desc = (*env)->GetStringUTFChars(env, device_desc, NULL);
- retval = Android_AddJoystick(device_id, name, desc, (SDL_bool) is_accelerometer, nbuttons, naxes, nhats, nballs);
+ retval = Android_AddJoystick(device_id, name, desc, vendor_id, product_id, is_accelerometer ? SDL_TRUE : SDL_FALSE, button_mask, naxes, nhats, nballs);
(*env)->ReleaseStringUTFChars(env, device_name, name);
(*env)->ReleaseStringUTFChars(env, device_desc, desc);
@@ -675,9 +733,9 @@ JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeTouch)(
/* Mouse */
JNIEXPORT void JNICALL SDL_JAVA_INTERFACE(onNativeMouse)(
JNIEnv* env, jclass jcls,
- jint button, jint action, jfloat x, jfloat y)
+ jint button, jint action, jfloat x, jfloat y, jboolean relative)
{
- Android_OnMouse(button, action, x, y);
+ Android_OnMouse(button, action, x, y, relative);
}
/* Accelerometer */
@@ -995,17 +1053,19 @@ int Android_JNI_SetupThread(void)
/*
* Audio support
*/
-static jboolean audioBuffer16Bit = JNI_FALSE;
+static int audioBufferFormat = 0;
static jobject audioBuffer = NULL;
static void* audioBufferPinned = NULL;
-static jboolean captureBuffer16Bit = JNI_FALSE;
+static int captureBufferFormat = 0;
static jobject captureBuffer = NULL;
-int Android_JNI_OpenAudioDevice(int iscapture, int sampleRate, int is16Bit, int channelCount, int desiredBufferFrames)
+int Android_JNI_OpenAudioDevice(int iscapture, SDL_AudioSpec *spec)
{
- jboolean audioBufferStereo;
- int audioBufferFrames;
+ int audioformat;
+ int numBufferFrames;
jobject jbufobj = NULL;
+ jobject result;
+ int *resultElements;
jboolean isCopy;
JNIEnv *env = Android_JNI_GetEnv();
@@ -1015,74 +1075,123 @@ int Android_JNI_OpenAudioDevice(int iscapture, int sampleRate, int is16Bit, int
}
Android_JNI_SetupThread();
- audioBufferStereo = channelCount > 1;
+ switch (spec->format) {
+ case AUDIO_U8:
+ audioformat = ENCODING_PCM_8BIT;
+ break;
+ case AUDIO_S16:
+ audioformat = ENCODING_PCM_16BIT;
+ break;
+ case AUDIO_F32:
+ audioformat = ENCODING_PCM_FLOAT;
+ break;
+ default:
+ return SDL_SetError("Unsupported audio format: 0x%x", spec->format);
+ }
if (iscapture) {
__android_log_print(ANDROID_LOG_VERBOSE, "SDL", "SDL audio: opening device for capture");
- captureBuffer16Bit = is16Bit;
- if ((*env)->CallStaticIntMethod(env, mAudioManagerClass, midCaptureOpen, sampleRate, audioBuffer16Bit, audioBufferStereo, desiredBufferFrames) != 0) {
- /* Error during audio initialization */
- __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL audio: error on AudioRecord initialization!");
- return 0;
- }
+ result = (*env)->CallStaticObjectMethod(env, mAudioManagerClass, midCaptureOpen, spec->freq, audioformat, spec->channels, spec->samples);
} else {
__android_log_print(ANDROID_LOG_VERBOSE, "SDL", "SDL audio: opening device for output");
- audioBuffer16Bit = is16Bit;
- if ((*env)->CallStaticIntMethod(env, mAudioManagerClass, midAudioOpen, sampleRate, audioBuffer16Bit, audioBufferStereo, desiredBufferFrames) != 0) {
- /* Error during audio initialization */
- __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL audio: error on AudioTrack initialization!");
- return 0;
- }
+ result = (*env)->CallStaticObjectMethod(env, mAudioManagerClass, midAudioOpen, spec->freq, audioformat, spec->channels, spec->samples);
+ }
+ if (result == NULL) {
+ /* Error during audio initialization, error printed from Java */
+ return SDL_SetError("Java-side initialization failed");
}
+ if ((*env)->GetArrayLength(env, (jintArray)result) != 4) {
+ return SDL_SetError("Unexpected results from Java, expected 4, got %d", (*env)->GetArrayLength(env, (jintArray)result));
+ }
+ isCopy = JNI_FALSE;
+ resultElements = (*env)->GetIntArrayElements(env, (jintArray)result, &isCopy);
+ spec->freq = resultElements[0];
+ audioformat = resultElements[1];
+ switch (audioformat) {
+ case ENCODING_PCM_8BIT:
+ spec->format = AUDIO_U8;
+ break;
+ case ENCODING_PCM_16BIT:
+ spec->format = AUDIO_S16;
+ break;
+ case ENCODING_PCM_FLOAT:
+ spec->format = AUDIO_F32;
+ break;
+ default:
+ return SDL_SetError("Unexpected audio format from Java: %d\n", audioformat);
+ }
+ spec->channels = resultElements[2];
+ spec->samples = resultElements[3];
+ (*env)->ReleaseIntArrayElements(env, (jintArray)result, resultElements, JNI_ABORT);
+ (*env)->DeleteLocalRef(env, result);
+
/* Allocating the audio buffer from the Java side and passing it as the return value for audioInit no longer works on
* Android >= 4.2 due to a "stale global reference" error. So now we allocate this buffer directly from this side. */
-
- if (is16Bit) {
- jshortArray audioBufferLocal = (*env)->NewShortArray(env, desiredBufferFrames * (audioBufferStereo ? 2 : 1));
- if (audioBufferLocal) {
- jbufobj = (*env)->NewGlobalRef(env, audioBufferLocal);
- (*env)->DeleteLocalRef(env, audioBufferLocal);
+ switch (audioformat) {
+ case ENCODING_PCM_8BIT:
+ {
+ jbyteArray audioBufferLocal = (*env)->NewByteArray(env, spec->samples * spec->channels);
+ if (audioBufferLocal) {
+ jbufobj = (*env)->NewGlobalRef(env, audioBufferLocal);
+ (*env)->DeleteLocalRef(env, audioBufferLocal);
+ }
}
- }
- else {
- jbyteArray audioBufferLocal = (*env)->NewByteArray(env, desiredBufferFrames * (audioBufferStereo ? 2 : 1));
- if (audioBufferLocal) {
- jbufobj = (*env)->NewGlobalRef(env, audioBufferLocal);
- (*env)->DeleteLocalRef(env, audioBufferLocal);
+ break;
+ case ENCODING_PCM_16BIT:
+ {
+ jshortArray audioBufferLocal = (*env)->NewShortArray(env, spec->samples * spec->channels);
+ if (audioBufferLocal) {
+ jbufobj = (*env)->NewGlobalRef(env, audioBufferLocal);
+ (*env)->DeleteLocalRef(env, audioBufferLocal);
+ }
}
+ break;
+ case ENCODING_PCM_FLOAT:
+ {
+ jfloatArray audioBufferLocal = (*env)->NewFloatArray(env, spec->samples * spec->channels);
+ if (audioBufferLocal) {
+ jbufobj = (*env)->NewGlobalRef(env, audioBufferLocal);
+ (*env)->DeleteLocalRef(env, audioBufferLocal);
+ }
+ }
+ break;
+ default:
+ return SDL_SetError("Unexpected audio format from Java: %d\n", audioformat);
}
if (jbufobj == NULL) {
- __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL audio: could not allocate an audio buffer!");
- return 0;
+ __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL audio: could not allocate an audio buffer");
+ return SDL_OutOfMemory();
}
if (iscapture) {
+ captureBufferFormat = audioformat;
captureBuffer = jbufobj;
} else {
+ audioBufferFormat = audioformat;
audioBuffer = jbufobj;
}
+ numBufferFrames = (*env)->GetArrayLength(env, (jarray)jbufobj);
- isCopy = JNI_FALSE;
+ if (!iscapture) {
+ isCopy = JNI_FALSE;
- if (is16Bit) {
- if (!iscapture) {
- audioBufferPinned = (*env)->GetShortArrayElements(env, (jshortArray)audioBuffer, &isCopy);
- }
- audioBufferFrames = (*env)->GetArrayLength(env, (jshortArray)audioBuffer);
- } else {
- if (!iscapture) {
+ switch (audioformat) {
+ case ENCODING_PCM_8BIT:
audioBufferPinned = (*env)->GetByteArrayElements(env, (jbyteArray)audioBuffer, &isCopy);
+ break;
+ case ENCODING_PCM_16BIT:
+ audioBufferPinned = (*env)->GetShortArrayElements(env, (jshortArray)audioBuffer, &isCopy);
+ break;
+ case ENCODING_PCM_FLOAT:
+ audioBufferPinned = (*env)->GetFloatArrayElements(env, (jfloatArray)audioBuffer, &isCopy);
+ break;
+ default:
+ return SDL_SetError("Unexpected audio format from Java: %d\n", audioformat);
}
- audioBufferFrames = (*env)->GetArrayLength(env, (jbyteArray)audioBuffer);
- }
-
- if (audioBufferStereo) {
- audioBufferFrames /= 2;
}
-
- return audioBufferFrames;
+ return 0;
}
int Android_JNI_GetDisplayDPI(float *ddpi, float *xdpi, float *ydpi)
@@ -1126,12 +1235,22 @@ void Android_JNI_WriteAudioBuffer(void)
{
JNIEnv *mAudioEnv = Android_JNI_GetEnv();
- if (audioBuffer16Bit) {
- (*mAudioEnv)->ReleaseShortArrayElements(mAudioEnv, (jshortArray)audioBuffer, (jshort *)audioBufferPinned, JNI_COMMIT);
- (*mAudioEnv)->CallStaticVoidMethod(mAudioEnv, mAudioManagerClass, midAudioWriteShortBuffer, (jshortArray)audioBuffer);
- } else {
+ switch (audioBufferFormat) {
+ case ENCODING_PCM_8BIT:
(*mAudioEnv)->ReleaseByteArrayElements(mAudioEnv, (jbyteArray)audioBuffer, (jbyte *)audioBufferPinned, JNI_COMMIT);
(*mAudioEnv)->CallStaticVoidMethod(mAudioEnv, mAudioManagerClass, midAudioWriteByteBuffer, (jbyteArray)audioBuffer);
+ break;
+ case ENCODING_PCM_16BIT:
+ (*mAudioEnv)->ReleaseShortArrayElements(mAudioEnv, (jshortArray)audioBuffer, (jshort *)audioBufferPinned, JNI_COMMIT);
+ (*mAudioEnv)->CallStaticVoidMethod(mAudioEnv, mAudioManagerClass, midAudioWriteShortBuffer, (jshortArray)audioBuffer);
+ break;
+ case ENCODING_PCM_FLOAT:
+ (*mAudioEnv)->ReleaseFloatArrayElements(mAudioEnv, (jfloatArray)audioBuffer, (jfloat *)audioBufferPinned, JNI_COMMIT);
+ (*mAudioEnv)->CallStaticVoidMethod(mAudioEnv, mAudioManagerClass, midAudioWriteFloatBuffer, (jfloatArray)audioBuffer);
+ break;
+ default:
+ __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL audio: unhandled audio buffer format");
+ break;
}
/* JNI_COMMIT means the changes are committed to the VM but the buffer remains pinned */
@@ -1143,44 +1262,84 @@ int Android_JNI_CaptureAudioBuffer(void *buffer, int buflen)
jboolean isCopy = JNI_FALSE;
jint br;
- if (captureBuffer16Bit) {
- SDL_assert((*env)->GetArrayLength(env, (jshortArray)captureBuffer) == (buflen / 2));
+ switch (captureBufferFormat) {
+ case ENCODING_PCM_8BIT:
+ SDL_assert((*env)->GetArrayLength(env, (jshortArray)captureBuffer) == buflen);
+ br = (*env)->CallStaticIntMethod(env, mAudioManagerClass, midCaptureReadByteBuffer, (jbyteArray)captureBuffer, JNI_TRUE);
+ if (br > 0) {
+ jbyte *ptr = (*env)->GetByteArrayElements(env, (jbyteArray)captureBuffer, &isCopy);
+ SDL_memcpy(buffer, ptr, br);
+ (*env)->ReleaseByteArrayElements(env, (jbyteArray)captureBuffer, (jbyte *)ptr, JNI_ABORT);
+ }
+ break;
+ case ENCODING_PCM_16BIT:
+ SDL_assert((*env)->GetArrayLength(env, (jshortArray)captureBuffer) == (buflen / sizeof(Sint16)));
br = (*env)->CallStaticIntMethod(env, mAudioManagerClass, midCaptureReadShortBuffer, (jshortArray)captureBuffer, JNI_TRUE);
if (br > 0) {
jshort *ptr = (*env)->GetShortArrayElements(env, (jshortArray)captureBuffer, &isCopy);
- br *= 2;
+ br *= sizeof(Sint16);
SDL_memcpy(buffer, ptr, br);
(*env)->ReleaseShortArrayElements(env, (jshortArray)captureBuffer, (jshort *)ptr, JNI_ABORT);
}
- } else {
- SDL_assert((*env)->GetArrayLength(env, (jshortArray)captureBuffer) == buflen);
- br = (*env)->CallStaticIntMethod(env, mAudioManagerClass, midCaptureReadByteBuffer, (jbyteArray)captureBuffer, JNI_TRUE);
+ break;
+ case ENCODING_PCM_FLOAT:
+ SDL_assert((*env)->GetArrayLength(env, (jfloatArray)captureBuffer) == (buflen / sizeof(float)));
+ br = (*env)->CallStaticIntMethod(env, mAudioManagerClass, midCaptureReadFloatBuffer, (jfloatArray)captureBuffer, JNI_TRUE);
if (br > 0) {
- jbyte *ptr = (*env)->GetByteArrayElements(env, (jbyteArray)captureBuffer, &isCopy);
+ jfloat *ptr = (*env)->GetFloatArrayElements(env, (jfloatArray)captureBuffer, &isCopy);
+ br *= sizeof(float);
SDL_memcpy(buffer, ptr, br);
- (*env)->ReleaseByteArrayElements(env, (jbyteArray)captureBuffer, (jbyte *)ptr, JNI_ABORT);
+ (*env)->ReleaseFloatArrayElements(env, (jfloatArray)captureBuffer, (jfloat *)ptr, JNI_ABORT);
}
+ break;
+ default:
+ __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL audio: unhandled capture buffer format");
+ break;
}
-
- return (int) br;
+ return br;
}
void Android_JNI_FlushCapturedAudio(void)
{
JNIEnv *env = Android_JNI_GetEnv();
#if 0 /* !!! FIXME: this needs API 23, or it'll do blocking reads and never end. */
- if (captureBuffer16Bit) {
- const jint len = (*env)->GetArrayLength(env, (jshortArray)captureBuffer);
- while ((*env)->CallStaticIntMethod(env, mActivityClass, midCaptureReadShortBuffer, (jshortArray)captureBuffer, JNI_FALSE) == len) { /* spin */ }
- } else {
- const jint len = (*env)->GetArrayLength(env, (jbyteArray)captureBuffer);
- while ((*env)->CallStaticIntMethod(env, mActivityClass, midCaptureReadByteBuffer, (jbyteArray)captureBuffer, JNI_FALSE) == len) { /* spin */ }
+ switch (captureBufferFormat) {
+ case ENCODING_PCM_8BIT:
+ {
+ const jint len = (*env)->GetArrayLength(env, (jbyteArray)captureBuffer);
+ while ((*env)->CallStaticIntMethod(env, mActivityClass, midCaptureReadByteBuffer, (jbyteArray)captureBuffer, JNI_FALSE) == len) { /* spin */ }
+ }
+ break;
+ case ENCODING_PCM_16BIT:
+ {
+ const jint len = (*env)->GetArrayLength(env, (jshortArray)captureBuffer);
+ while ((*env)->CallStaticIntMethod(env, mActivityClass, midCaptureReadShortBuffer, (jshortArray)captureBuffer, JNI_FALSE) == len) { /* spin */ }
+ }
+ break;
+ case ENCODING_PCM_FLOAT:
+ {
+ const jint len = (*env)->GetArrayLength(env, (jfloatArray)captureBuffer);
+ while ((*env)->CallStaticIntMethod(env, mActivityClass, midCaptureReadFloatBuffer, (jfloatArray)captureBuffer, JNI_FALSE) == len) { /* spin */ }
+ }
+ break;
+ default:
+ __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL audio: flushing unhandled capture buffer format");
+ break;
}
#else
- if (captureBuffer16Bit) {
- (*env)->CallStaticIntMethod(env, mAudioManagerClass, midCaptureReadShortBuffer, (jshortArray)captureBuffer, JNI_FALSE);
- } else {
+ switch (captureBufferFormat) {
+ case ENCODING_PCM_8BIT:
(*env)->CallStaticIntMethod(env, mAudioManagerClass, midCaptureReadByteBuffer, (jbyteArray)captureBuffer, JNI_FALSE);
+ break;
+ case ENCODING_PCM_16BIT:
+ (*env)->CallStaticIntMethod(env, mAudioManagerClass, midCaptureReadShortBuffer, (jshortArray)captureBuffer, JNI_FALSE);
+ break;
+ case ENCODING_PCM_FLOAT:
+ (*env)->CallStaticIntMethod(env, mAudioManagerClass, midCaptureReadFloatBuffer, (jfloatArray)captureBuffer, JNI_FALSE);
+ break;
+ default:
+ __android_log_print(ANDROID_LOG_WARN, "SDL", "SDL audio: flushing unhandled capture buffer format");
+ break;
}
#endif
}
@@ -1846,12 +2005,17 @@ void Android_JNI_PollHapticDevices(void)
(*env)->CallStaticVoidMethod(env, mControllerManagerClass, midPollHapticDevices);
}
-void Android_JNI_HapticRun(int device_id, int length)
+void Android_JNI_HapticRun(int device_id, float intensity, int length)
{
JNIEnv *env = Android_JNI_GetEnv();
- (*env)->CallStaticVoidMethod(env, mControllerManagerClass, midHapticRun, device_id, length);
+ (*env)->CallStaticVoidMethod(env, mControllerManagerClass, midHapticRun, device_id, intensity, length);
}
+void Android_JNI_HapticStop(int device_id)
+{
+ JNIEnv *env = Android_JNI_GetEnv();
+ (*env)->CallStaticVoidMethod(env, mControllerManagerClass, midHapticStop, device_id);
+}
/* See SDLActivity.java for constants. */
#define COMMAND_SET_KEEP_SCREEN_ON 5
@@ -2006,12 +2170,36 @@ void *SDL_AndroidGetActivity(void)
return (*env)->CallStaticObjectMethod(env, mActivityClass, midGetContext);
}
+SDL_bool SDL_IsAndroidTablet(void)
+{
+ JNIEnv *env = Android_JNI_GetEnv();
+ return (*env)->CallStaticBooleanMethod(env, mActivityClass, midIsTablet);
+}
+
SDL_bool SDL_IsAndroidTV(void)
{
JNIEnv *env = Android_JNI_GetEnv();
return (*env)->CallStaticBooleanMethod(env, mActivityClass, midIsAndroidTV);
}
+SDL_bool SDL_IsChromebook(void)
+{
+ JNIEnv *env = Android_JNI_GetEnv();
+ return (*env)->CallStaticBooleanMethod(env, mActivityClass, midIsChromebook);
+}
+
+SDL_bool SDL_IsDeXMode(void)
+{
+ JNIEnv *env = Android_JNI_GetEnv();
+ return (*env)->CallStaticBooleanMethod(env, mActivityClass, midIsDeXMode);
+}
+
+void SDL_AndroidBackButton(void)
+{
+ JNIEnv *env = Android_JNI_GetEnv();
+ return (*env)->CallStaticVoidMethod(env, mActivityClass, midManualBackButton);
+}
+
const char * SDL_AndroidGetInternalStoragePath(void)
{
static char *s_AndroidInternalFilesPath = NULL;
@@ -2166,6 +2354,48 @@ void Android_JNI_GetManifestEnvironmentVariables(void)
}
}
+int Android_JNI_CreateCustomCursor(SDL_Surface *surface, int hot_x, int hot_y)
+{
+ JNIEnv *mEnv = Android_JNI_GetEnv();
+ int custom_cursor = 0;
+ jintArray pixels;
+ pixels = (*mEnv)->NewIntArray(mEnv, surface->w * surface->h);
+ if (pixels) {
+ (*mEnv)->SetIntArrayRegion(mEnv, pixels, 0, surface->w * surface->h, (int *)surface->pixels);
+ custom_cursor = (*mEnv)->CallStaticIntMethod(mEnv, mActivityClass, midCreateCustomCursor, pixels, surface->w, surface->h, hot_x, hot_y);
+ (*mEnv)->DeleteLocalRef(mEnv, pixels);
+ } else {
+ SDL_OutOfMemory();
+ }
+ return custom_cursor;
+}
+
+
+SDL_bool Android_JNI_SetCustomCursor(int cursorID)
+{
+ JNIEnv *mEnv = Android_JNI_GetEnv();
+ return (*mEnv)->CallStaticBooleanMethod(mEnv, mActivityClass, midSetCustomCursor, cursorID);
+}
+
+SDL_bool Android_JNI_SetSystemCursor(int cursorID)
+{
+ JNIEnv *mEnv = Android_JNI_GetEnv();
+ return (*mEnv)->CallStaticBooleanMethod(mEnv, mActivityClass, midSetSystemCursor, cursorID);
+}
+
+SDL_bool Android_JNI_SupportsRelativeMouse()
+{
+ JNIEnv *mEnv = Android_JNI_GetEnv();
+ return (*mEnv)->CallStaticBooleanMethod(mEnv, mActivityClass, midSupportsRelativeMouse);
+}
+
+SDL_bool Android_JNI_SetRelativeMouseEnabled(SDL_bool enabled)
+{
+ JNIEnv *mEnv = Android_JNI_GetEnv();
+ return (*mEnv)->CallStaticBooleanMethod(mEnv, mActivityClass, midSetRelativeMouseEnabled, (enabled == 1));
+}
+
+
#endif /* __ANDROID__ */
/* vi: set ts=4 sw=4 expandtab: */
diff --git a/Source/3rdParty/SDL2/src/core/android/SDL_android.h b/Source/3rdParty/SDL2/src/core/android/SDL_android.h
index c800dc6..b2ff32e 100644
--- a/Source/3rdParty/SDL2/src/core/android/SDL_android.h
+++ b/Source/3rdParty/SDL2/src/core/android/SDL_android.h
@@ -19,6 +19,7 @@
3. This notice may not be removed or altered from any source distribution.
*/
#include "../../SDL_internal.h"
+#include "SDL_system.h"
/* Set up for C function definitions, even when using C++ */
#ifdef __cplusplus
@@ -30,6 +31,7 @@ extern "C" {
#include <EGL/eglplatform.h>
#include <android/native_window_jni.h>
+#include "SDL_audio.h"
#include "SDL_rect.h"
/* Interface from the SDL library into the Android Java activity */
@@ -46,13 +48,17 @@ extern ANativeWindow* Android_JNI_GetNativeWindow(void);
extern int Android_JNI_GetDisplayDPI(float *ddpi, float *xdpi, float *ydpi);
/* Audio support */
-extern int Android_JNI_OpenAudioDevice(int iscapture, int sampleRate, int is16Bit, int channelCount, int desiredBufferFrames);
+extern int Android_JNI_OpenAudioDevice(int iscapture, SDL_AudioSpec *spec);
extern void* Android_JNI_GetAudioBuffer(void);
extern void Android_JNI_WriteAudioBuffer(void);
extern int Android_JNI_CaptureAudioBuffer(void *buffer, int buflen);
extern void Android_JNI_FlushCapturedAudio(void);
extern void Android_JNI_CloseAudioDevice(const int iscapture);
+/* Detecting device type */
+extern SDL_bool Android_IsDeXMode();
+extern SDL_bool Android_IsChromebook();
+
#include "SDL_rwops.h"
int Android_JNI_FileOpen(SDL_RWops* ctx, const char* fileName, const char* mode);
@@ -78,14 +84,16 @@ void Android_JNI_PollInputDevices(void);
/* Haptic support */
void Android_JNI_PollHapticDevices(void);
-void Android_JNI_HapticRun(int device_id, int length);
+void Android_JNI_HapticRun(int device_id, float intensity, int length);
+void Android_JNI_HapticStop(int device_id);
/* Video */
void Android_JNI_SuspendScreenSaver(SDL_bool suspend);
/* Touch support */
-int Android_JNI_GetTouchDeviceIds(int **ids);
+int Android_JNI_InitTouch(void);
void Android_JNI_SetSeparateMouseAndTouch(SDL_bool new_value);
+int Android_JNI_GetTouchDeviceIds(int **ids);
/* Threads */
#include <jni.h>
@@ -102,6 +110,21 @@ JNIEXPORT void JNICALL SDL_Android_Init(JNIEnv* mEnv, jclass cls);
#include "SDL_messagebox.h"
int Android_JNI_ShowMessageBox(const SDL_MessageBoxData *messageboxdata, int *buttonid);
+/* Cursor support */
+int Android_JNI_CreateCustomCursor(SDL_Surface *surface, int hot_x, int hot_y);
+SDL_bool Android_JNI_SetCustomCursor(int cursorID);
+SDL_bool Android_JNI_SetSystemCursor(int cursorID);
+
+/* Relative mouse support */
+SDL_bool Android_JNI_SupportsRelativeMouse(void);
+SDL_bool Android_JNI_SetRelativeMouseEnabled(SDL_bool enabled);
+
+
+SDL_bool SDL_IsAndroidTablet(void);
+SDL_bool SDL_IsAndroidTV(void);
+SDL_bool SDL_IsChromebook(void);
+SDL_bool SDL_IsDeXMode(void);
+
/* Ends C function definitions when using C++ */
#ifdef __cplusplus
/* *INDENT-OFF* */