mirror of
https://github.com/dolphin-emu/dolphin.git
synced 2025-07-22 22:00:39 -06:00
Android: Make input state changes observable
This commit is contained in:
@ -6,6 +6,7 @@ import android.content.Context
|
||||
import android.hardware.input.InputManager
|
||||
import android.os.Build
|
||||
import android.os.Handler
|
||||
import android.os.Looper
|
||||
import android.os.VibrationEffect
|
||||
import android.os.Vibrator
|
||||
import android.os.VibratorManager
|
||||
@ -13,8 +14,11 @@ import android.view.InputDevice
|
||||
import android.view.KeyEvent
|
||||
import android.view.MotionEvent
|
||||
import androidx.annotation.Keep
|
||||
import androidx.lifecycle.LiveData
|
||||
import androidx.lifecycle.MutableLiveData
|
||||
import org.dolphinemu.dolphinemu.DolphinApplication
|
||||
import org.dolphinemu.dolphinemu.utils.LooperThread
|
||||
import java.util.concurrent.atomic.AtomicBoolean
|
||||
|
||||
/**
|
||||
* This class interfaces with the native ControllerInterface,
|
||||
@ -24,6 +28,12 @@ object ControllerInterface {
|
||||
private var inputDeviceListener: InputDeviceListener? = null
|
||||
private lateinit var looperThread: LooperThread
|
||||
|
||||
private var inputStateUpdatePending = AtomicBoolean(false)
|
||||
private val inputStateVersion = MutableLiveData(0)
|
||||
|
||||
val inputStateChanged: LiveData<Int>
|
||||
get() = inputStateVersion
|
||||
|
||||
/**
|
||||
* Activities which want to pass on inputs to native code
|
||||
* should call this in their own dispatchKeyEvent method.
|
||||
@ -31,7 +41,13 @@ object ControllerInterface {
|
||||
* @return true if the emulator core seems to be interested in this event.
|
||||
* false if the event should be passed on to the default dispatchKeyEvent.
|
||||
*/
|
||||
external fun dispatchKeyEvent(event: KeyEvent): Boolean
|
||||
fun dispatchKeyEvent(event: KeyEvent): Boolean {
|
||||
val result = dispatchKeyEventNative(event)
|
||||
onInputStateChanged()
|
||||
return result
|
||||
}
|
||||
|
||||
private external fun dispatchKeyEventNative(event: KeyEvent): Boolean
|
||||
|
||||
/**
|
||||
* Activities which want to pass on inputs to native code
|
||||
@ -40,7 +56,13 @@ object ControllerInterface {
|
||||
* @return true if the emulator core seems to be interested in this event.
|
||||
* false if the event should be passed on to the default dispatchGenericMotionEvent.
|
||||
*/
|
||||
external fun dispatchGenericMotionEvent(event: MotionEvent): Boolean
|
||||
fun dispatchGenericMotionEvent(event: MotionEvent): Boolean {
|
||||
val result = dispatchGenericMotionEventNative(event)
|
||||
onInputStateChanged()
|
||||
return result
|
||||
}
|
||||
|
||||
private external fun dispatchGenericMotionEventNative(event: MotionEvent): Boolean
|
||||
|
||||
/**
|
||||
* [DolphinSensorEventListener] calls this for each axis of a received SensorEvent.
|
||||
@ -48,7 +70,13 @@ object ControllerInterface {
|
||||
* @return true if the emulator core seems to be interested in this event.
|
||||
* false if the sensor can be suspended to save battery.
|
||||
*/
|
||||
external fun dispatchSensorEvent(
|
||||
fun dispatchSensorEvent(deviceQualifier: String, axisName: String, value: Float): Boolean {
|
||||
val result = dispatchSensorEventNative(deviceQualifier, axisName, value)
|
||||
onInputStateChanged()
|
||||
return result
|
||||
}
|
||||
|
||||
private external fun dispatchSensorEventNative(
|
||||
deviceQualifier: String,
|
||||
axisName: String,
|
||||
value: Float
|
||||
@ -76,6 +104,19 @@ object ControllerInterface {
|
||||
|
||||
external fun getDevice(deviceString: String): CoreDevice?
|
||||
|
||||
private fun onInputStateChanged() {
|
||||
// When a single SensorEvent is dispatched, this method is likely to get called many times.
|
||||
// For the sake of performance, let's batch input state updates so that observers only have
|
||||
// to process one update.
|
||||
if (!inputStateUpdatePending.getAndSet(true)) {
|
||||
Handler(Looper.getMainLooper()).post {
|
||||
if (inputStateUpdatePending.getAndSet(false)) {
|
||||
inputStateVersion.value = inputStateVersion.value?.plus(1)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Keep
|
||||
@JvmStatic
|
||||
private fun registerInputDeviceListener() {
|
||||
|
Reference in New Issue
Block a user