can't compile new SDL Activity on Android, can't find "import java.util.Objects;"
will investigate later
This commit is contained in:
		@@ -1,37 +0,0 @@
 | 
				
			|||||||
package org.libsdl.app;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
import android.content.Context;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
/**
 | 
					 | 
				
			||||||
    SDL library initialization
 | 
					 | 
				
			||||||
*/
 | 
					 | 
				
			||||||
public class SDL {
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    // This function should be called first and sets up the native code
 | 
					 | 
				
			||||||
    // so it can call into the Java classes
 | 
					 | 
				
			||||||
    public static void setupJNI() {
 | 
					 | 
				
			||||||
        SDLActivity.nativeSetupJNI();
 | 
					 | 
				
			||||||
        SDLAudioManager.nativeSetupJNI();
 | 
					 | 
				
			||||||
        SDLControllerManager.nativeSetupJNI();
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    // This function should be called each time the activity is started
 | 
					 | 
				
			||||||
    public static void initialize() {
 | 
					 | 
				
			||||||
        setContext(null);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        SDLActivity.initialize();
 | 
					 | 
				
			||||||
        SDLAudioManager.initialize();
 | 
					 | 
				
			||||||
        SDLControllerManager.initialize();
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    // This function stores the current activity (SDL or not)
 | 
					 | 
				
			||||||
    public static void setContext(Context context) {
 | 
					 | 
				
			||||||
        mContext = context;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    public static Context getContext() {
 | 
					 | 
				
			||||||
        return mContext;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    protected static Context mContext;
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							@@ -1,178 +0,0 @@
 | 
				
			|||||||
package org.libsdl.app;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
import android.media.*;
 | 
					 | 
				
			||||||
import android.util.Log;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
public class SDLAudioManager
 | 
					 | 
				
			||||||
{
 | 
					 | 
				
			||||||
    protected static final String TAG = "SDLAudio";
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    protected static AudioTrack mAudioTrack;
 | 
					 | 
				
			||||||
    protected static AudioRecord mAudioRecord;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    public static void initialize() {
 | 
					 | 
				
			||||||
        mAudioTrack = null;
 | 
					 | 
				
			||||||
        mAudioRecord = null;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    // Audio
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    /**
 | 
					 | 
				
			||||||
     * This method is called by SDL using JNI.
 | 
					 | 
				
			||||||
     */
 | 
					 | 
				
			||||||
    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);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        Log.v(TAG, "SDL audio: 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, (AudioTrack.getMinBufferSize(sampleRate, channelConfig, audioFormat) + frameSize - 1) / frameSize);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        if (mAudioTrack == null) {
 | 
					 | 
				
			||||||
            mAudioTrack = new AudioTrack(AudioManager.STREAM_MUSIC, sampleRate,
 | 
					 | 
				
			||||||
                    channelConfig, audioFormat, desiredFrames * frameSize, AudioTrack.MODE_STREAM);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
            // Instantiating AudioTrack can "succeed" without an exception and the track may still be invalid
 | 
					 | 
				
			||||||
            // Ref: https://android.googlesource.com/platform/frameworks/base/+/refs/heads/master/media/java/android/media/AudioTrack.java
 | 
					 | 
				
			||||||
            // Ref: http://developer.android.com/reference/android/media/AudioTrack.html#getState()
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
            if (mAudioTrack.getState() != AudioTrack.STATE_INITIALIZED) {
 | 
					 | 
				
			||||||
                Log.e(TAG, "Failed during initialization of Audio Track");
 | 
					 | 
				
			||||||
                mAudioTrack = null;
 | 
					 | 
				
			||||||
                return -1;
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
            mAudioTrack.play();
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        Log.v(TAG, "SDL audio: got " + ((mAudioTrack.getChannelCount() >= 2) ? "stereo" : "mono") + " " + ((mAudioTrack.getAudioFormat() == AudioFormat.ENCODING_PCM_16BIT) ? "16-bit" : "8-bit") + " " + (mAudioTrack.getSampleRate() / 1000f) + "kHz, " + desiredFrames + " frames buffer");
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        return 0;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    /**
 | 
					 | 
				
			||||||
     * This method is called by SDL using JNI.
 | 
					 | 
				
			||||||
     */
 | 
					 | 
				
			||||||
    public static void audioWriteShortBuffer(short[] buffer) {
 | 
					 | 
				
			||||||
        if (mAudioTrack == null) {
 | 
					 | 
				
			||||||
            Log.e(TAG, "Attempted to make audio call with uninitialized audio!");
 | 
					 | 
				
			||||||
            return;
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        for (int i = 0; i < buffer.length; ) {
 | 
					 | 
				
			||||||
            int result = mAudioTrack.write(buffer, i, buffer.length - i);
 | 
					 | 
				
			||||||
            if (result > 0) {
 | 
					 | 
				
			||||||
                i += result;
 | 
					 | 
				
			||||||
            } else if (result == 0) {
 | 
					 | 
				
			||||||
                try {
 | 
					 | 
				
			||||||
                    Thread.sleep(1);
 | 
					 | 
				
			||||||
                } catch(InterruptedException e) {
 | 
					 | 
				
			||||||
                    // Nom nom
 | 
					 | 
				
			||||||
                }
 | 
					 | 
				
			||||||
            } else {
 | 
					 | 
				
			||||||
                Log.w(TAG, "SDL audio: error return from write(short)");
 | 
					 | 
				
			||||||
                return;
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    /**
 | 
					 | 
				
			||||||
     * This method is called by SDL using JNI.
 | 
					 | 
				
			||||||
     */
 | 
					 | 
				
			||||||
    public static void audioWriteByteBuffer(byte[] buffer) {
 | 
					 | 
				
			||||||
        if (mAudioTrack == null) {
 | 
					 | 
				
			||||||
            Log.e(TAG, "Attempted to make audio call with uninitialized audio!");
 | 
					 | 
				
			||||||
            return;
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
        
 | 
					 | 
				
			||||||
        for (int i = 0; i < buffer.length; ) {
 | 
					 | 
				
			||||||
            int result = mAudioTrack.write(buffer, i, buffer.length - i);
 | 
					 | 
				
			||||||
            if (result > 0) {
 | 
					 | 
				
			||||||
                i += result;
 | 
					 | 
				
			||||||
            } else if (result == 0) {
 | 
					 | 
				
			||||||
                try {
 | 
					 | 
				
			||||||
                    Thread.sleep(1);
 | 
					 | 
				
			||||||
                } catch(InterruptedException e) {
 | 
					 | 
				
			||||||
                    // Nom nom
 | 
					 | 
				
			||||||
                }
 | 
					 | 
				
			||||||
            } else {
 | 
					 | 
				
			||||||
                Log.w(TAG, "SDL audio: error return from write(byte)");
 | 
					 | 
				
			||||||
                return;
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    /**
 | 
					 | 
				
			||||||
     * This method is called by SDL using JNI.
 | 
					 | 
				
			||||||
     */
 | 
					 | 
				
			||||||
    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;
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    public static native int nativeSetupJNI();
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
@@ -1,433 +0,0 @@
 | 
				
			|||||||
package org.libsdl.app;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
import java.util.ArrayList;
 | 
					 | 
				
			||||||
import java.util.Collections;
 | 
					 | 
				
			||||||
import java.util.Comparator;
 | 
					 | 
				
			||||||
import java.util.List;
 | 
					 | 
				
			||||||
import java.util.Objects;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
import android.content.Context;
 | 
					 | 
				
			||||||
import android.os.*;
 | 
					 | 
				
			||||||
import android.view.*;
 | 
					 | 
				
			||||||
import android.util.Log;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
public class SDLControllerManager 
 | 
					 | 
				
			||||||
{
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    public static native int nativeSetupJNI();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    public static native int nativeAddJoystick(int device_id, String name, String desc,
 | 
					 | 
				
			||||||
                                               int is_accelerometer, int nbuttons,
 | 
					 | 
				
			||||||
                                               int naxes, int nhats, int nballs);
 | 
					 | 
				
			||||||
    public static native int nativeRemoveJoystick(int device_id);
 | 
					 | 
				
			||||||
    public static native int nativeAddHaptic(int device_id, String name);
 | 
					 | 
				
			||||||
    public static native int nativeRemoveHaptic(int device_id);
 | 
					 | 
				
			||||||
    public static native int onNativePadDown(int device_id, int keycode);
 | 
					 | 
				
			||||||
    public static native int onNativePadUp(int device_id, int keycode);
 | 
					 | 
				
			||||||
    public static native void onNativeJoy(int device_id, int axis,
 | 
					 | 
				
			||||||
                                          float value);
 | 
					 | 
				
			||||||
    public static native void onNativeHat(int device_id, int hat_id,
 | 
					 | 
				
			||||||
                                          int x, int y);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    protected static SDLJoystickHandler mJoystickHandler;
 | 
					 | 
				
			||||||
    protected static SDLHapticHandler mHapticHandler;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    private static final String TAG = "SDLControllerManager";
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    public static void initialize() {
 | 
					 | 
				
			||||||
        mJoystickHandler = null;
 | 
					 | 
				
			||||||
        mHapticHandler = null;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        SDLControllerManager.setup();
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    public static void setup() {
 | 
					 | 
				
			||||||
        if (Build.VERSION.SDK_INT >= 16) {
 | 
					 | 
				
			||||||
            mJoystickHandler = new SDLJoystickHandler_API16();
 | 
					 | 
				
			||||||
        } else if (Build.VERSION.SDK_INT >= 12) {
 | 
					 | 
				
			||||||
            mJoystickHandler = new SDLJoystickHandler_API12();
 | 
					 | 
				
			||||||
        } else {
 | 
					 | 
				
			||||||
            mJoystickHandler = new SDLJoystickHandler();
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
        mHapticHandler = new SDLHapticHandler();
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    // Joystick glue code, just a series of stubs that redirect to the SDLJoystickHandler instance
 | 
					 | 
				
			||||||
    public static boolean handleJoystickMotionEvent(MotionEvent event) {
 | 
					 | 
				
			||||||
        return mJoystickHandler.handleMotionEvent(event);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    /**
 | 
					 | 
				
			||||||
     * This method is called by SDL using JNI.
 | 
					 | 
				
			||||||
     */
 | 
					 | 
				
			||||||
    public static void pollInputDevices() {
 | 
					 | 
				
			||||||
        mJoystickHandler.pollInputDevices();
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    /**
 | 
					 | 
				
			||||||
     * This method is called by SDL using JNI.
 | 
					 | 
				
			||||||
     */
 | 
					 | 
				
			||||||
    public static void pollHapticDevices() {
 | 
					 | 
				
			||||||
        mHapticHandler.pollHapticDevices();
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    /**
 | 
					 | 
				
			||||||
     * This method is called by SDL using JNI.
 | 
					 | 
				
			||||||
     */
 | 
					 | 
				
			||||||
    public static void hapticRun(int device_id, int length) {
 | 
					 | 
				
			||||||
        mHapticHandler.run(device_id, length);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    // 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();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        if ((sources & InputDevice.SOURCE_CLASS_JOYSTICK) == InputDevice.SOURCE_CLASS_JOYSTICK) {
 | 
					 | 
				
			||||||
            Log.v(TAG, "Input device " + device.getName() + " is a joystick.");
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
        if ((sources & InputDevice.SOURCE_DPAD) == InputDevice.SOURCE_DPAD) {
 | 
					 | 
				
			||||||
            Log.v(TAG, "Input device " + device.getName() + " is a dpad.");
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
        if ((sources & InputDevice.SOURCE_GAMEPAD) == InputDevice.SOURCE_GAMEPAD) {
 | 
					 | 
				
			||||||
            Log.v(TAG, "Input device " + device.getName() + " is a gamepad.");
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        return (((sources & InputDevice.SOURCE_CLASS_JOYSTICK) == InputDevice.SOURCE_CLASS_JOYSTICK) ||
 | 
					 | 
				
			||||||
                ((sources & InputDevice.SOURCE_DPAD) == InputDevice.SOURCE_DPAD) ||
 | 
					 | 
				
			||||||
                ((sources & InputDevice.SOURCE_GAMEPAD) == InputDevice.SOURCE_GAMEPAD)
 | 
					 | 
				
			||||||
        );
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
/* A null joystick handler for API level < 12 devices (the accelerometer is handled separately) */
 | 
					 | 
				
			||||||
class SDLJoystickHandler {
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    /**
 | 
					 | 
				
			||||||
     * Handles given MotionEvent.
 | 
					 | 
				
			||||||
     * @param event the event to be handled.
 | 
					 | 
				
			||||||
     * @return if given event was processed.
 | 
					 | 
				
			||||||
     */
 | 
					 | 
				
			||||||
    public boolean handleMotionEvent(MotionEvent event) {
 | 
					 | 
				
			||||||
        return false;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    /**
 | 
					 | 
				
			||||||
     * Handles adding and removing of input devices.
 | 
					 | 
				
			||||||
     */
 | 
					 | 
				
			||||||
    public void pollInputDevices() {
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
/* Actual joystick functionality available for API >= 12 devices */
 | 
					 | 
				
			||||||
class SDLJoystickHandler_API12 extends SDLJoystickHandler {
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    static class SDLJoystick {
 | 
					 | 
				
			||||||
        public int device_id;
 | 
					 | 
				
			||||||
        public String name;
 | 
					 | 
				
			||||||
        public String desc;
 | 
					 | 
				
			||||||
        public ArrayList<InputDevice.MotionRange> axes;
 | 
					 | 
				
			||||||
        public ArrayList<InputDevice.MotionRange> hats;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    static class RangeComparator implements Comparator<InputDevice.MotionRange> {
 | 
					 | 
				
			||||||
        @Override
 | 
					 | 
				
			||||||
        public int compare(InputDevice.MotionRange arg0, InputDevice.MotionRange arg1) {
 | 
					 | 
				
			||||||
            return arg0.getAxis() - arg1.getAxis();
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    private ArrayList<SDLJoystick> mJoysticks;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    public SDLJoystickHandler_API12() {
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        mJoysticks = new ArrayList<SDLJoystick>();
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    @Override
 | 
					 | 
				
			||||||
    public void pollInputDevices() {
 | 
					 | 
				
			||||||
        int[] deviceIds = InputDevice.getDeviceIds();
 | 
					 | 
				
			||||||
        // It helps processing the device ids in reverse order
 | 
					 | 
				
			||||||
        // For example, in the case of the XBox 360 wireless dongle,
 | 
					 | 
				
			||||||
        // so the first controller seen by SDL matches what the receiver
 | 
					 | 
				
			||||||
        // considers to be the first controller
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        for(int i=deviceIds.length-1; i>-1; i--) {
 | 
					 | 
				
			||||||
            SDLJoystick joystick = getJoystick(deviceIds[i]);
 | 
					 | 
				
			||||||
            if (joystick == null) {
 | 
					 | 
				
			||||||
                joystick = new SDLJoystick();
 | 
					 | 
				
			||||||
                InputDevice joystickDevice = InputDevice.getDevice(deviceIds[i]);
 | 
					 | 
				
			||||||
                if (SDLControllerManager.isDeviceSDLJoystick(deviceIds[i])) {
 | 
					 | 
				
			||||||
                    joystick.device_id = deviceIds[i];
 | 
					 | 
				
			||||||
                    joystick.name = joystickDevice.getName();
 | 
					 | 
				
			||||||
                    joystick.desc = getJoystickDescriptor(joystickDevice);
 | 
					 | 
				
			||||||
                    joystick.axes = new ArrayList<InputDevice.MotionRange>();
 | 
					 | 
				
			||||||
                    joystick.hats = new ArrayList<InputDevice.MotionRange>();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
                    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.getAxis() == MotionEvent.AXIS_HAT_X ||
 | 
					 | 
				
			||||||
                                range.getAxis() == MotionEvent.AXIS_HAT_Y) {
 | 
					 | 
				
			||||||
                                joystick.hats.add(range);
 | 
					 | 
				
			||||||
                            }
 | 
					 | 
				
			||||||
                            else {
 | 
					 | 
				
			||||||
                                joystick.axes.add(range);
 | 
					 | 
				
			||||||
                            }
 | 
					 | 
				
			||||||
                        }
 | 
					 | 
				
			||||||
                    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
                    mJoysticks.add(joystick);
 | 
					 | 
				
			||||||
                    SDLControllerManager.nativeAddJoystick(joystick.device_id, joystick.name, joystick.desc, 0, -1,
 | 
					 | 
				
			||||||
                                                           joystick.axes.size(), joystick.hats.size()/2, 0);
 | 
					 | 
				
			||||||
                }
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        /* Check removed devices */
 | 
					 | 
				
			||||||
        ArrayList<Integer> removedDevices = new ArrayList<Integer>();
 | 
					 | 
				
			||||||
        for(int i=0; i < mJoysticks.size(); i++) {
 | 
					 | 
				
			||||||
            int device_id = mJoysticks.get(i).device_id;
 | 
					 | 
				
			||||||
            int j;
 | 
					 | 
				
			||||||
            for (j=0; j < deviceIds.length; j++) {
 | 
					 | 
				
			||||||
                if (device_id == deviceIds[j]) break;
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
            if (j == deviceIds.length) {
 | 
					 | 
				
			||||||
                removedDevices.add(Integer.valueOf(device_id));
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        for(int i=0; i < removedDevices.size(); i++) {
 | 
					 | 
				
			||||||
            int device_id = removedDevices.get(i).intValue();
 | 
					 | 
				
			||||||
            SDLControllerManager.nativeRemoveJoystick(device_id);
 | 
					 | 
				
			||||||
            for (int j=0; j < mJoysticks.size(); j++) {
 | 
					 | 
				
			||||||
                if (mJoysticks.get(j).device_id == device_id) {
 | 
					 | 
				
			||||||
                    mJoysticks.remove(j);
 | 
					 | 
				
			||||||
                    break;
 | 
					 | 
				
			||||||
                }
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    protected SDLJoystick getJoystick(int device_id) {
 | 
					 | 
				
			||||||
        for(int i=0; i < mJoysticks.size(); i++) {
 | 
					 | 
				
			||||||
            if (mJoysticks.get(i).device_id == device_id) {
 | 
					 | 
				
			||||||
                return mJoysticks.get(i);
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
        return null;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    @Override
 | 
					 | 
				
			||||||
    public boolean handleMotionEvent(MotionEvent event) {
 | 
					 | 
				
			||||||
        if ((event.getSource() & InputDevice.SOURCE_JOYSTICK) != 0) {
 | 
					 | 
				
			||||||
            int actionPointerIndex = event.getActionIndex();
 | 
					 | 
				
			||||||
            int action = event.getActionMasked();
 | 
					 | 
				
			||||||
            switch(action) {
 | 
					 | 
				
			||||||
                case MotionEvent.ACTION_MOVE:
 | 
					 | 
				
			||||||
                    SDLJoystick joystick = getJoystick(event.getDeviceId());
 | 
					 | 
				
			||||||
                    if ( joystick != null ) {
 | 
					 | 
				
			||||||
                        for (int i = 0; i < joystick.axes.size(); i++) {
 | 
					 | 
				
			||||||
                            InputDevice.MotionRange range = joystick.axes.get(i);
 | 
					 | 
				
			||||||
                            /* Normalize the value to -1...1 */
 | 
					 | 
				
			||||||
                            float value = ( event.getAxisValue( range.getAxis(), actionPointerIndex) - range.getMin() ) / range.getRange() * 2.0f - 1.0f;
 | 
					 | 
				
			||||||
                            SDLControllerManager.onNativeJoy(joystick.device_id, i, value );
 | 
					 | 
				
			||||||
                        }
 | 
					 | 
				
			||||||
                        for (int i = 0; i < joystick.hats.size(); i+=2) {
 | 
					 | 
				
			||||||
                            int hatX = Math.round(event.getAxisValue( joystick.hats.get(i).getAxis(), actionPointerIndex ) );
 | 
					 | 
				
			||||||
                            int hatY = Math.round(event.getAxisValue( joystick.hats.get(i+1).getAxis(), actionPointerIndex ) );
 | 
					 | 
				
			||||||
                            SDLControllerManager.onNativeHat(joystick.device_id, i/2, hatX, hatY );
 | 
					 | 
				
			||||||
                        }
 | 
					 | 
				
			||||||
                    }
 | 
					 | 
				
			||||||
                    break;
 | 
					 | 
				
			||||||
                default:
 | 
					 | 
				
			||||||
                    break;
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
        return true;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    public String getJoystickDescriptor(InputDevice joystickDevice) {
 | 
					 | 
				
			||||||
        return joystickDevice.getName();
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class SDLJoystickHandler_API16 extends SDLJoystickHandler_API12 {
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    @Override
 | 
					 | 
				
			||||||
    public String getJoystickDescriptor(InputDevice joystickDevice) {
 | 
					 | 
				
			||||||
        String desc = joystickDevice.getDescriptor();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        if (desc != null && !Objects.equals(desc, "")) {
 | 
					 | 
				
			||||||
            return desc;
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        return super.getJoystickDescriptor(joystickDevice);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class SDLHapticHandler {
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    class SDLHaptic {
 | 
					 | 
				
			||||||
        public int device_id;
 | 
					 | 
				
			||||||
        public String name;
 | 
					 | 
				
			||||||
        public Vibrator vib;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    private ArrayList<SDLHaptic> mHaptics;
 | 
					 | 
				
			||||||
    
 | 
					 | 
				
			||||||
    public SDLHapticHandler() {
 | 
					 | 
				
			||||||
        mHaptics = new ArrayList<SDLHaptic>();
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    public void run(int device_id, int length) {
 | 
					 | 
				
			||||||
        SDLHaptic haptic = getHaptic(device_id);
 | 
					 | 
				
			||||||
        if (haptic != null) {
 | 
					 | 
				
			||||||
            haptic.vib.vibrate (length);
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    public void pollHapticDevices() {
 | 
					 | 
				
			||||||
        
 | 
					 | 
				
			||||||
        final int deviceId_VIBRATOR_SERVICE = 999999;
 | 
					 | 
				
			||||||
        boolean hasVibratorService = false;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        int[] deviceIds = InputDevice.getDeviceIds();
 | 
					 | 
				
			||||||
        // It helps processing the device ids in reverse order
 | 
					 | 
				
			||||||
        // For example, in the case of the XBox 360 wireless dongle,
 | 
					 | 
				
			||||||
        // so the first controller seen by SDL matches what the receiver
 | 
					 | 
				
			||||||
        // considers to be the first controller
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        if (Build.VERSION.SDK_INT >= 16)
 | 
					 | 
				
			||||||
        {
 | 
					 | 
				
			||||||
            for (int i = deviceIds.length - 1; i > -1; i--) {
 | 
					 | 
				
			||||||
                SDLHaptic haptic = getHaptic(deviceIds[i]);
 | 
					 | 
				
			||||||
                if (haptic == null) {
 | 
					 | 
				
			||||||
                    InputDevice device = InputDevice.getDevice(deviceIds[i]);
 | 
					 | 
				
			||||||
                    Vibrator vib = device.getVibrator();
 | 
					 | 
				
			||||||
                    if (vib.hasVibrator()) {
 | 
					 | 
				
			||||||
                        haptic = new SDLHaptic();
 | 
					 | 
				
			||||||
                        haptic.device_id = deviceIds[i];
 | 
					 | 
				
			||||||
                        haptic.name = device.getName();
 | 
					 | 
				
			||||||
                        haptic.vib = vib;
 | 
					 | 
				
			||||||
                        mHaptics.add(haptic);
 | 
					 | 
				
			||||||
                        SDLControllerManager.nativeAddHaptic(haptic.device_id, haptic.name);
 | 
					 | 
				
			||||||
                    }
 | 
					 | 
				
			||||||
                }
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        /* Check VIBRATOR_SERVICE */
 | 
					 | 
				
			||||||
        Vibrator vib = (Vibrator) SDL.getContext().getSystemService(Context.VIBRATOR_SERVICE);
 | 
					 | 
				
			||||||
        if (vib != null) {
 | 
					 | 
				
			||||||
            if (Build.VERSION.SDK_INT >= 11) {
 | 
					 | 
				
			||||||
                hasVibratorService = vib.hasVibrator();
 | 
					 | 
				
			||||||
            } else {
 | 
					 | 
				
			||||||
                hasVibratorService = true;
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
            if (hasVibratorService) {
 | 
					 | 
				
			||||||
                SDLHaptic haptic = getHaptic(deviceId_VIBRATOR_SERVICE);
 | 
					 | 
				
			||||||
                if (haptic == null) {
 | 
					 | 
				
			||||||
                    haptic = new SDLHaptic();
 | 
					 | 
				
			||||||
                    haptic.device_id = deviceId_VIBRATOR_SERVICE;
 | 
					 | 
				
			||||||
                    haptic.name = "VIBRATOR_SERVICE";
 | 
					 | 
				
			||||||
                    haptic.vib = vib; 
 | 
					 | 
				
			||||||
                    mHaptics.add(haptic);
 | 
					 | 
				
			||||||
                    SDLControllerManager.nativeAddHaptic(haptic.device_id, haptic.name);
 | 
					 | 
				
			||||||
                }
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        /* Check removed devices */
 | 
					 | 
				
			||||||
        ArrayList<Integer> removedDevices = new ArrayList<Integer>();
 | 
					 | 
				
			||||||
        for(int i=0; i < mHaptics.size(); i++) {
 | 
					 | 
				
			||||||
            int device_id = mHaptics.get(i).device_id;
 | 
					 | 
				
			||||||
            int j;
 | 
					 | 
				
			||||||
            for (j=0; j < deviceIds.length; j++) {
 | 
					 | 
				
			||||||
                if (device_id == deviceIds[j]) break;
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
            if (device_id == deviceId_VIBRATOR_SERVICE && hasVibratorService) {
 | 
					 | 
				
			||||||
                // don't remove the vibrator if it is still present
 | 
					 | 
				
			||||||
            } else if (j == deviceIds.length) {
 | 
					 | 
				
			||||||
                removedDevices.add(device_id);
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        for(int i=0; i < removedDevices.size(); i++) {
 | 
					 | 
				
			||||||
            int device_id = removedDevices.get(i);
 | 
					 | 
				
			||||||
            SDLControllerManager.nativeRemoveHaptic(device_id);
 | 
					 | 
				
			||||||
            for (int j=0; j < mHaptics.size(); j++) {
 | 
					 | 
				
			||||||
                if (mHaptics.get(j).device_id == device_id) {
 | 
					 | 
				
			||||||
                    mHaptics.remove(j);
 | 
					 | 
				
			||||||
                    break;
 | 
					 | 
				
			||||||
                }
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    protected SDLHaptic getHaptic(int device_id) {
 | 
					 | 
				
			||||||
        for(int i=0; i < mHaptics.size(); i++) {
 | 
					 | 
				
			||||||
            if (mHaptics.get(i).device_id == device_id) {
 | 
					 | 
				
			||||||
                return mHaptics.get(i);
 | 
					 | 
				
			||||||
            }
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
        return null;
 | 
					 | 
				
			||||||
    }   
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class SDLGenericMotionListener_API12 implements View.OnGenericMotionListener {
 | 
					 | 
				
			||||||
    // Generic Motion (mouse hover, joystick...) events go here
 | 
					 | 
				
			||||||
    @Override
 | 
					 | 
				
			||||||
    public boolean onGenericMotion(View v, MotionEvent event) {
 | 
					 | 
				
			||||||
        float x, y;
 | 
					 | 
				
			||||||
        int action;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        switch ( event.getSource() ) {
 | 
					 | 
				
			||||||
            case InputDevice.SOURCE_JOYSTICK:
 | 
					 | 
				
			||||||
            case InputDevice.SOURCE_GAMEPAD:
 | 
					 | 
				
			||||||
            case InputDevice.SOURCE_DPAD:
 | 
					 | 
				
			||||||
                return SDLControllerManager.handleJoystickMotionEvent(event);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
            case InputDevice.SOURCE_MOUSE:
 | 
					 | 
				
			||||||
                if (!SDLActivity.mSeparateMouseAndTouch) {
 | 
					 | 
				
			||||||
                    break;
 | 
					 | 
				
			||||||
                }
 | 
					 | 
				
			||||||
                action = event.getActionMasked();
 | 
					 | 
				
			||||||
                switch (action) {
 | 
					 | 
				
			||||||
                    case MotionEvent.ACTION_SCROLL:
 | 
					 | 
				
			||||||
                        x = event.getAxisValue(MotionEvent.AXIS_HSCROLL, 0);
 | 
					 | 
				
			||||||
                        y = event.getAxisValue(MotionEvent.AXIS_VSCROLL, 0);
 | 
					 | 
				
			||||||
                        SDLActivity.onNativeMouse(0, action, x, y);
 | 
					 | 
				
			||||||
                        return true;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
                    case MotionEvent.ACTION_HOVER_MOVE:
 | 
					 | 
				
			||||||
                        x = event.getX(0);
 | 
					 | 
				
			||||||
                        y = event.getY(0);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
                        SDLActivity.onNativeMouse(0, action, x, y);
 | 
					 | 
				
			||||||
                        return true;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
                    default:
 | 
					 | 
				
			||||||
                        break;
 | 
					 | 
				
			||||||
                }
 | 
					 | 
				
			||||||
                break;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
            default:
 | 
					 | 
				
			||||||
                break;
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        // Event was not managed
 | 
					 | 
				
			||||||
        return false;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
		Reference in New Issue
	
	Block a user