diff options
author | 2016-11-16 16:26:13 +0100 | |
---|---|---|
committer | 2016-11-16 16:28:01 +0100 | |
commit | 47a05778bff9388fc6c479461dd3804c79d7b539 (patch) | |
tree | bb3d4dc8df676b8aa478339b3fd0cd305dc4ac4d /3rdparty/SDL2/android-project/src | |
parent | e61b392edfbfe5b9d70908c087632da915a3abd8 (diff) |
Updated SDL2 to 2.0.5 (nw)
Diffstat (limited to '3rdparty/SDL2/android-project/src')
-rw-r--r-- | 3rdparty/SDL2/android-project/src/org/libsdl/app/SDLActivity.java | 157 |
1 files changed, 119 insertions, 38 deletions
diff --git a/3rdparty/SDL2/android-project/src/org/libsdl/app/SDLActivity.java b/3rdparty/SDL2/android-project/src/org/libsdl/app/SDLActivity.java index 0a2e5d87e31..c3d44843793 100644 --- a/3rdparty/SDL2/android-project/src/org/libsdl/app/SDLActivity.java +++ b/3rdparty/SDL2/android-project/src/org/libsdl/app/SDLActivity.java @@ -17,7 +17,7 @@ import android.view.inputmethod.BaseInputConnection; import android.view.inputmethod.EditorInfo; import android.view.inputmethod.InputConnection; import android.view.inputmethod.InputMethodManager; -import android.widget.AbsoluteLayout; +import android.widget.RelativeLayout; import android.widget.Button; import android.widget.LinearLayout; import android.widget.TextView; @@ -59,6 +59,7 @@ public class SDLActivity extends Activity { // Audio protected static AudioTrack mAudioTrack; + protected static AudioRecord mAudioRecord; /** * This method is called by SDL before loading the native shared libraries. @@ -106,6 +107,7 @@ public class SDLActivity extends Activity { mJoystickHandler = null; mSDLThread = null; mAudioTrack = null; + mAudioRecord = null; mExitCalledFromJava = false; mBrokenLibraries = false; mIsPaused = false; @@ -171,7 +173,7 @@ public class SDLActivity extends Activity { mJoystickHandler = new SDLJoystickHandler(); } - mLayout = new AbsoluteLayout(this); + mLayout = new RelativeLayout(this); mLayout.addView(mSurface); setContentView(mLayout); @@ -367,7 +369,10 @@ public class SDLActivity extends Activity { break; case COMMAND_TEXTEDIT_HIDE: if (mTextEdit != null) { - mTextEdit.setVisibility(View.GONE); + // Note: On some devices setting view to GONE creates a flicker in landscape. + // Setting the View's sizes to 0 is similar to GONE but without the flicker. + // The sizes will be set to useful values when the keyboard is shown again. + mTextEdit.setLayoutParams(new RelativeLayout.LayoutParams(0, 0)); InputMethodManager imm = (InputMethodManager) context.getSystemService(Context.INPUT_METHOD_SERVICE); imm.hideSoftInputFromWindow(mTextEdit.getWindowToken(), 0); @@ -504,8 +509,9 @@ public class SDLActivity extends Activity { @Override public void run() { - AbsoluteLayout.LayoutParams params = new AbsoluteLayout.LayoutParams( - w, h + HEIGHT_PADDING, x, y); + RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(w, h + HEIGHT_PADDING); + params.leftMargin = x; + params.topMargin = y; if (mTextEdit == null) { mTextEdit = new DummyEdit(getContext()); @@ -543,7 +549,7 @@ public class SDLActivity extends Activity { /** * This method is called by SDL using JNI. */ - public static int audioInit(int sampleRate, boolean is16Bit, boolean isStereo, int desiredFrames) { + public static int audioOpen(int sampleRate, boolean is16Bit, boolean isStereo, int desiredFrames) { int channelConfig = isStereo ? AudioFormat.CHANNEL_CONFIGURATION_STEREO : AudioFormat.CHANNEL_CONFIGURATION_MONO; int audioFormat = is16Bit ? AudioFormat.ENCODING_PCM_16BIT : AudioFormat.ENCODING_PCM_8BIT; int frameSize = (isStereo ? 2 : 1) * (is16Bit ? 2 : 1); @@ -622,13 +628,72 @@ public class SDLActivity extends Activity { /** * This method is called by SDL using JNI. */ - public static void audioQuit() { + public static int captureOpen(int sampleRate, boolean is16Bit, boolean isStereo, int desiredFrames) { + int channelConfig = isStereo ? AudioFormat.CHANNEL_CONFIGURATION_STEREO : AudioFormat.CHANNEL_CONFIGURATION_MONO; + int audioFormat = is16Bit ? AudioFormat.ENCODING_PCM_16BIT : AudioFormat.ENCODING_PCM_8BIT; + int frameSize = (isStereo ? 2 : 1) * (is16Bit ? 2 : 1); + + Log.v(TAG, "SDL capture: wanted " + (isStereo ? "stereo" : "mono") + " " + (is16Bit ? "16-bit" : "8-bit") + " " + (sampleRate / 1000f) + "kHz, " + desiredFrames + " frames buffer"); + + // Let the user pick a larger buffer if they really want -- but ye + // gods they probably shouldn't, the minimums are horrifyingly high + // latency already + desiredFrames = Math.max(desiredFrames, (AudioRecord.getMinBufferSize(sampleRate, channelConfig, audioFormat) + frameSize - 1) / frameSize); + + if (mAudioRecord == null) { + mAudioRecord = new AudioRecord(MediaRecorder.AudioSource.DEFAULT, sampleRate, + channelConfig, audioFormat, desiredFrames * frameSize); + + // see notes about AudioTrack state in audioOpen(), above. Probably also applies here. + if (mAudioRecord.getState() != AudioRecord.STATE_INITIALIZED) { + Log.e(TAG, "Failed during initialization of AudioRecord"); + mAudioRecord.release(); + mAudioRecord = null; + return -1; + } + + mAudioRecord.startRecording(); + } + + Log.v(TAG, "SDL capture: got " + ((mAudioRecord.getChannelCount() >= 2) ? "stereo" : "mono") + " " + ((mAudioRecord.getAudioFormat() == AudioFormat.ENCODING_PCM_16BIT) ? "16-bit" : "8-bit") + " " + (mAudioRecord.getSampleRate() / 1000f) + "kHz, " + desiredFrames + " frames buffer"); + + return 0; + } + + /** This method is called by SDL using JNI. */ + public static int captureReadShortBuffer(short[] buffer, boolean blocking) { + // !!! FIXME: this is available in API Level 23. Until then, we always block. :( + //return mAudioRecord.read(buffer, 0, buffer.length, blocking ? AudioRecord.READ_BLOCKING : AudioRecord.READ_NON_BLOCKING); + return mAudioRecord.read(buffer, 0, buffer.length); + } + + /** This method is called by SDL using JNI. */ + public static int captureReadByteBuffer(byte[] buffer, boolean blocking) { + // !!! FIXME: this is available in API Level 23. Until then, we always block. :( + //return mAudioRecord.read(buffer, 0, buffer.length, blocking ? AudioRecord.READ_BLOCKING : AudioRecord.READ_NON_BLOCKING); + return mAudioRecord.read(buffer, 0, buffer.length); + } + + + /** This method is called by SDL using JNI. */ + public static void audioClose() { if (mAudioTrack != null) { mAudioTrack.stop(); + mAudioTrack.release(); mAudioTrack = null; } } + /** This method is called by SDL using JNI. */ + public static void captureClose() { + if (mAudioRecord != null) { + mAudioRecord.stop(); + mAudioRecord.release(); + mAudioRecord = null; + } + } + + // Input /** @@ -662,6 +727,21 @@ public class SDLActivity extends Activity { } } + // Check if a given device is considered a possible SDL joystick + public static boolean isDeviceSDLJoystick(int deviceId) { + InputDevice device = InputDevice.getDevice(deviceId); + // We cannot use InputDevice.isVirtual before API 16, so let's accept + // only nonnegative device ids (VIRTUAL_KEYBOARD equals -1) + if ((device == null) || (deviceId < 0)) { + return false; + } + int sources = device.getSources(); + return (((sources & InputDevice.SOURCE_CLASS_JOYSTICK) == InputDevice.SOURCE_CLASS_JOYSTICK) || + ((sources & InputDevice.SOURCE_DPAD) == InputDevice.SOURCE_DPAD) || + ((sources & InputDevice.SOURCE_GAMEPAD) == InputDevice.SOURCE_GAMEPAD) + ); + } + // APK expansion files support /** com.android.vending.expansion.zipfile.ZipResourceFile object or null. */ @@ -671,15 +751,6 @@ public class SDLActivity extends Activity { private Method expansionFileMethod; /** - * This method was called by SDL using JNI. - * @deprecated because of an incorrect name - */ - @Deprecated - public InputStream openAPKExtensionInputStream(String fileName) throws IOException { - return openAPKExpansionInputStream(fileName); - } - - /** * This method is called by SDL using JNI. * @return an InputStream on success or null if no expansion file was used. * @throws IOException on errors. Message is set for the SDL error message. @@ -1167,11 +1238,14 @@ class SDLSurface extends SurfaceView implements SurfaceHolder.Callback, @Override public boolean onKey(View v, int keyCode, KeyEvent event) { // Dispatch the different events depending on where they come from - // Some SOURCE_DPAD or SOURCE_GAMEPAD are also SOURCE_KEYBOARD - // So, we try to process them as DPAD or GAMEPAD events first, if that fails we try them as KEYBOARD - - if ( (event.getSource() & InputDevice.SOURCE_GAMEPAD) != 0 || - (event.getSource() & InputDevice.SOURCE_DPAD) != 0 ) { + // Some SOURCE_JOYSTICK, SOURCE_DPAD or SOURCE_GAMEPAD are also SOURCE_KEYBOARD + // So, we try to process them as JOYSTICK/DPAD/GAMEPAD events first, if that fails we try them as KEYBOARD + // + // Furthermore, it's possible a game controller has SOURCE_KEYBOARD and + // SOURCE_JOYSTICK, while its key events arrive from the keyboard source + // So, retrieve the device itself and check all of its sources + if (SDLActivity.isDeviceSDLJoystick(event.getDeviceId())) { + // Note that we process events with specific key codes here if (event.getAction() == KeyEvent.ACTION_DOWN) { if (SDLActivity.onNativePadDown(event.getDeviceId(), keyCode) == 0) { return true; @@ -1183,7 +1257,7 @@ class SDLSurface extends SurfaceView implements SurfaceHolder.Callback, } } - if( (event.getSource() & InputDevice.SOURCE_KEYBOARD) != 0) { + if ((event.getSource() & InputDevice.SOURCE_KEYBOARD) != 0) { if (event.getAction() == KeyEvent.ACTION_DOWN) { //Log.v("SDL", "key down: " + keyCode); SDLActivity.onNativeKeyDown(keyCode); @@ -1196,6 +1270,20 @@ class SDLSurface extends SurfaceView implements SurfaceHolder.Callback, } } + if ((event.getSource() & InputDevice.SOURCE_MOUSE) != 0) { + // on some devices key events are sent for mouse BUTTON_BACK/FORWARD presses + // they are ignored here because sending them as mouse input to SDL is messy + if ((keyCode == KeyEvent.KEYCODE_BACK) || (keyCode == KeyEvent.KEYCODE_FORWARD)) { + switch (event.getAction()) { + case KeyEvent.ACTION_DOWN: + case KeyEvent.ACTION_UP: + // mark the event as handled or it will be handled by system + // handling KEYCODE_BACK by system will call onBackPressed() + return true; + } + } + } + return false; } @@ -1214,7 +1302,7 @@ class SDLSurface extends SurfaceView implements SurfaceHolder.Callback, // !!! FIXME: dump this SDK check after 2.0.4 ships and require API14. if (event.getSource() == InputDevice.SOURCE_MOUSE && SDLActivity.mSeparateMouseAndTouch) { if (Build.VERSION.SDK_INT < 14) { - mouseButton = 1; // For Android==12 all mouse buttons are the left button + mouseButton = 1; // all mouse buttons are the left button } else { try { mouseButton = (Integer) event.getClass().getMethod("getButtonState").invoke(event); @@ -1328,7 +1416,7 @@ class SDLSurface extends SurfaceView implements SurfaceHolder.Callback, } SDLActivity.onNativeAccel(-x / SensorManager.GRAVITY_EARTH, y / SensorManager.GRAVITY_EARTH, - event.values[2] / SensorManager.GRAVITY_EARTH - 1); + event.values[2] / SensorManager.GRAVITY_EARTH); } } } @@ -1355,7 +1443,7 @@ class DummyEdit extends View implements View.OnKeyListener { public boolean onKey(View v, int keyCode, KeyEvent event) { // This handles the hardware keyboard input - if (event.isPrintingKey()) { + if (event.isPrintingKey() || keyCode == KeyEvent.KEYCODE_SPACE) { if (event.getAction() == KeyEvent.ACTION_DOWN) { ic.commitText(String.valueOf((char) event.getUnicodeChar()), 1); } @@ -1379,7 +1467,7 @@ class DummyEdit extends View implements View.OnKeyListener { // As seen on StackOverflow: http://stackoverflow.com/questions/7634346/keyboard-hide-event // FIXME: Discussion at http://bugzilla.libsdl.org/show_bug.cgi?id=1639 // FIXME: This is not a 100% effective solution to the problem of detecting if the keyboard is showing or not - // FIXME: A more effective solution would be to change our Layout from AbsoluteLayout to Relative or Linear + // FIXME: A more effective solution would be to assume our Layout to be RelativeLayout or LinearLayout // FIXME: And determine the keyboard presence doing this: http://stackoverflow.com/questions/2150078/how-to-check-visibility-of-software-keyboard-in-android // FIXME: An even more effective way would be if Android provided this out of the box, but where would the fun be in that :) if (event.getAction()==KeyEvent.ACTION_UP && keyCode == KeyEvent.KEYCODE_BACK) { @@ -1418,7 +1506,7 @@ class SDLInputConnection extends BaseInputConnection { */ int keyCode = event.getKeyCode(); if (event.getAction() == KeyEvent.ACTION_DOWN) { - if (event.isPrintingKey()) { + if (event.isPrintingKey() || keyCode == KeyEvent.KEYCODE_SPACE) { commitText(String.valueOf((char) event.getUnicodeChar()), 1); } SDLActivity.onNativeKeyDown(keyCode); @@ -1519,13 +1607,7 @@ class SDLJoystickHandler_API12 extends SDLJoystickHandler { if (joystick == null) { joystick = new SDLJoystick(); InputDevice joystickDevice = InputDevice.getDevice(deviceIds[i]); - - if ( - (joystickDevice.getSources() & InputDevice.SOURCE_CLASS_JOYSTICK) != 0 - || - (joystickDevice.getSources() & InputDevice.SOURCE_CLASS_BUTTON) != 0 - ) - { + if (SDLActivity.isDeviceSDLJoystick(deviceIds[i])) { joystick.device_id = deviceIds[i]; joystick.name = joystickDevice.getName(); joystick.axes = new ArrayList<InputDevice.MotionRange>(); @@ -1534,7 +1616,7 @@ class SDLJoystickHandler_API12 extends SDLJoystickHandler { List<InputDevice.MotionRange> ranges = joystickDevice.getMotionRanges(); Collections.sort(ranges, new RangeComparator()); for (InputDevice.MotionRange range : ranges ) { - if ((range.getSource() & InputDevice.SOURCE_CLASS_JOYSTICK) != 0 ) { + if ((range.getSource() & InputDevice.SOURCE_CLASS_JOYSTICK) != 0) { if (range.getAxis() == MotionEvent.AXIS_HAT_X || range.getAxis() == MotionEvent.AXIS_HAT_Y) { joystick.hats.add(range); @@ -1588,7 +1670,7 @@ class SDLJoystickHandler_API12 extends SDLJoystickHandler { @Override public boolean handleMotionEvent(MotionEvent event) { - if ( (event.getSource() & InputDevice.SOURCE_JOYSTICK) != 0) { + if ((event.getSource() & InputDevice.SOURCE_JOYSTICK) != 0) { int actionPointerIndex = event.getActionIndex(); int action = event.getActionMasked(); switch(action) { @@ -1627,8 +1709,7 @@ class SDLGenericMotionListener_API12 implements View.OnGenericMotionListener { case InputDevice.SOURCE_JOYSTICK: case InputDevice.SOURCE_GAMEPAD: case InputDevice.SOURCE_DPAD: - SDLActivity.handleJoystickMotionEvent(event); - return true; + return SDLActivity.handleJoystickMotionEvent(event); case InputDevice.SOURCE_MOUSE: action = event.getActionMasked(); |