Input logic cleanup:
- Fix invalid detection of mouse input. Prioritize using the event tool type to detect the type of the event, and only use the event source as fallback. - Ensure that pressure and tilt information is passed for touch drag events - Consolidate logic and remove redundant methods - Improve the logic to detect when external hardware keyboards are connected to the device
This commit is contained in:
parent
daa81bbb7d
commit
625b92e3cd
|
@ -176,6 +176,8 @@ void AndroidInputHandler::process_touch_event(int p_event, int p_pointer, const
|
||||||
for (int i = 0; i < p_points.size(); i++) {
|
for (int i = 0; i < p_points.size(); i++) {
|
||||||
touch.write[i].id = p_points[i].id;
|
touch.write[i].id = p_points[i].id;
|
||||||
touch.write[i].pos = p_points[i].pos;
|
touch.write[i].pos = p_points[i].pos;
|
||||||
|
touch.write[i].pressure = p_points[i].pressure;
|
||||||
|
touch.write[i].tilt = p_points[i].tilt;
|
||||||
}
|
}
|
||||||
|
|
||||||
//send touch
|
//send touch
|
||||||
|
@ -208,6 +210,8 @@ void AndroidInputHandler::process_touch_event(int p_event, int p_pointer, const
|
||||||
ev->set_position(p_points[idx].pos);
|
ev->set_position(p_points[idx].pos);
|
||||||
ev->set_relative(p_points[idx].pos - touch[i].pos);
|
ev->set_relative(p_points[idx].pos - touch[i].pos);
|
||||||
ev->set_relative_screen_position(ev->get_relative());
|
ev->set_relative_screen_position(ev->get_relative());
|
||||||
|
ev->set_pressure(p_points[idx].pressure);
|
||||||
|
ev->set_tilt(p_points[idx].tilt);
|
||||||
Input::get_singleton()->parse_input_event(ev);
|
Input::get_singleton()->parse_input_event(ev);
|
||||||
touch.write[i].pos = p_points[idx].pos;
|
touch.write[i].pos = p_points[idx].pos;
|
||||||
}
|
}
|
||||||
|
|
|
@ -42,6 +42,8 @@ public:
|
||||||
struct TouchPos {
|
struct TouchPos {
|
||||||
int id = 0;
|
int id = 0;
|
||||||
Point2 pos;
|
Point2 pos;
|
||||||
|
float pressure = 0;
|
||||||
|
Vector2 tilt;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct MouseEventInfo {
|
struct MouseEventInfo {
|
||||||
|
|
|
@ -266,8 +266,13 @@ public class GodotEditText extends EditText {
|
||||||
|
|
||||||
boolean hasHardwareKeyboard() {
|
boolean hasHardwareKeyboard() {
|
||||||
Configuration config = getResources().getConfiguration();
|
Configuration config = getResources().getConfiguration();
|
||||||
return config.keyboard != Configuration.KEYBOARD_NOKEYS &&
|
boolean hasHardwareKeyboardConfig = config.keyboard != Configuration.KEYBOARD_NOKEYS &&
|
||||||
config.hardKeyboardHidden == Configuration.HARDKEYBOARDHIDDEN_NO;
|
config.hardKeyboardHidden == Configuration.HARDKEYBOARDHIDDEN_NO;
|
||||||
|
if (hasHardwareKeyboardConfig) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return mRenderView.getInputHandler().hasHardwareKeyboard();
|
||||||
}
|
}
|
||||||
|
|
||||||
// ===========================================================
|
// ===========================================================
|
||||||
|
|
|
@ -62,7 +62,7 @@ internal class GodotGestureHandler : SimpleOnGestureListener(), OnScaleGestureLi
|
||||||
private var pointerCaptureInProgress = false
|
private var pointerCaptureInProgress = false
|
||||||
|
|
||||||
override fun onDown(event: MotionEvent): Boolean {
|
override fun onDown(event: MotionEvent): Boolean {
|
||||||
GodotInputHandler.handleMotionEvent(event.source, MotionEvent.ACTION_DOWN, event.buttonState, event.x, event.y, nextDownIsDoubleTap)
|
GodotInputHandler.handleMotionEvent(event, MotionEvent.ACTION_DOWN, nextDownIsDoubleTap)
|
||||||
nextDownIsDoubleTap = false
|
nextDownIsDoubleTap = false
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
@ -82,20 +82,14 @@ internal class GodotGestureHandler : SimpleOnGestureListener(), OnScaleGestureLi
|
||||||
}
|
}
|
||||||
|
|
||||||
// Cancel the previous down event
|
// Cancel the previous down event
|
||||||
GodotInputHandler.handleMotionEvent(
|
GodotInputHandler.handleMotionEvent(event, MotionEvent.ACTION_CANCEL)
|
||||||
event.source,
|
|
||||||
MotionEvent.ACTION_CANCEL,
|
|
||||||
event.buttonState,
|
|
||||||
event.x,
|
|
||||||
event.y
|
|
||||||
)
|
|
||||||
|
|
||||||
// Turn a context click into a single tap right mouse button click.
|
// Turn a context click into a single tap right mouse button click.
|
||||||
GodotInputHandler.handleMouseEvent(
|
GodotInputHandler.handleMouseEvent(
|
||||||
|
event,
|
||||||
MotionEvent.ACTION_DOWN,
|
MotionEvent.ACTION_DOWN,
|
||||||
MotionEvent.BUTTON_SECONDARY,
|
MotionEvent.BUTTON_SECONDARY,
|
||||||
event.x,
|
false
|
||||||
event.y
|
|
||||||
)
|
)
|
||||||
contextClickInProgress = true
|
contextClickInProgress = true
|
||||||
}
|
}
|
||||||
|
@ -107,16 +101,7 @@ internal class GodotGestureHandler : SimpleOnGestureListener(), OnScaleGestureLi
|
||||||
|
|
||||||
if (!hasCapture) {
|
if (!hasCapture) {
|
||||||
// Dispatch a mouse relative ACTION_UP event to signal the end of the capture
|
// Dispatch a mouse relative ACTION_UP event to signal the end of the capture
|
||||||
GodotInputHandler.handleMouseEvent(
|
GodotInputHandler.handleMouseEvent(MotionEvent.ACTION_UP, true)
|
||||||
MotionEvent.ACTION_UP,
|
|
||||||
0,
|
|
||||||
0f,
|
|
||||||
0f,
|
|
||||||
0f,
|
|
||||||
0f,
|
|
||||||
false,
|
|
||||||
true
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
pointerCaptureInProgress = hasCapture
|
pointerCaptureInProgress = hasCapture
|
||||||
}
|
}
|
||||||
|
@ -139,26 +124,11 @@ internal class GodotGestureHandler : SimpleOnGestureListener(), OnScaleGestureLi
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
val sourceMouseRelative = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
|
||||||
event.isFromSource(InputDevice.SOURCE_MOUSE_RELATIVE)
|
|
||||||
} else {
|
|
||||||
false
|
|
||||||
}
|
|
||||||
|
|
||||||
if (pointerCaptureInProgress || dragInProgress || contextClickInProgress) {
|
if (pointerCaptureInProgress || dragInProgress || contextClickInProgress) {
|
||||||
if (contextClickInProgress || GodotInputHandler.isMouseEvent(event)) {
|
if (contextClickInProgress || GodotInputHandler.isMouseEvent(event)) {
|
||||||
// This may be an ACTION_BUTTON_RELEASE event which we don't handle,
|
// This may be an ACTION_BUTTON_RELEASE event which we don't handle,
|
||||||
// so we convert it to an ACTION_UP event.
|
// so we convert it to an ACTION_UP event.
|
||||||
GodotInputHandler.handleMouseEvent(
|
GodotInputHandler.handleMouseEvent(event, MotionEvent.ACTION_UP)
|
||||||
MotionEvent.ACTION_UP,
|
|
||||||
event.buttonState,
|
|
||||||
event.x,
|
|
||||||
event.y,
|
|
||||||
0f,
|
|
||||||
0f,
|
|
||||||
false,
|
|
||||||
sourceMouseRelative
|
|
||||||
)
|
|
||||||
} else {
|
} else {
|
||||||
GodotInputHandler.handleTouchEvent(event)
|
GodotInputHandler.handleTouchEvent(event)
|
||||||
}
|
}
|
||||||
|
@ -173,21 +143,7 @@ internal class GodotGestureHandler : SimpleOnGestureListener(), OnScaleGestureLi
|
||||||
|
|
||||||
private fun onActionMove(event: MotionEvent): Boolean {
|
private fun onActionMove(event: MotionEvent): Boolean {
|
||||||
if (contextClickInProgress) {
|
if (contextClickInProgress) {
|
||||||
val sourceMouseRelative = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
GodotInputHandler.handleMouseEvent(event, event.actionMasked, MotionEvent.BUTTON_SECONDARY, false)
|
||||||
event.isFromSource(InputDevice.SOURCE_MOUSE_RELATIVE)
|
|
||||||
} else {
|
|
||||||
false
|
|
||||||
}
|
|
||||||
GodotInputHandler.handleMouseEvent(
|
|
||||||
event.actionMasked,
|
|
||||||
MotionEvent.BUTTON_SECONDARY,
|
|
||||||
event.x,
|
|
||||||
event.y,
|
|
||||||
0f,
|
|
||||||
0f,
|
|
||||||
false,
|
|
||||||
sourceMouseRelative
|
|
||||||
)
|
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
return false
|
return false
|
||||||
|
@ -197,7 +153,7 @@ internal class GodotGestureHandler : SimpleOnGestureListener(), OnScaleGestureLi
|
||||||
if (event.actionMasked == MotionEvent.ACTION_UP) {
|
if (event.actionMasked == MotionEvent.ACTION_UP) {
|
||||||
nextDownIsDoubleTap = false
|
nextDownIsDoubleTap = false
|
||||||
GodotInputHandler.handleMotionEvent(event)
|
GodotInputHandler.handleMotionEvent(event)
|
||||||
} else if (event.actionMasked == MotionEvent.ACTION_MOVE && panningAndScalingEnabled == false) {
|
} else if (event.actionMasked == MotionEvent.ACTION_MOVE && !panningAndScalingEnabled) {
|
||||||
GodotInputHandler.handleMotionEvent(event)
|
GodotInputHandler.handleMotionEvent(event)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -219,13 +175,7 @@ internal class GodotGestureHandler : SimpleOnGestureListener(), OnScaleGestureLi
|
||||||
if (dragInProgress) {
|
if (dragInProgress) {
|
||||||
if (originEvent != null) {
|
if (originEvent != null) {
|
||||||
// Cancel the drag
|
// Cancel the drag
|
||||||
GodotInputHandler.handleMotionEvent(
|
GodotInputHandler.handleMotionEvent(originEvent, MotionEvent.ACTION_CANCEL)
|
||||||
originEvent.source,
|
|
||||||
MotionEvent.ACTION_CANCEL,
|
|
||||||
originEvent.buttonState,
|
|
||||||
originEvent.x,
|
|
||||||
originEvent.y
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
dragInProgress = false
|
dragInProgress = false
|
||||||
}
|
}
|
||||||
|
|
|
@ -62,6 +62,7 @@ public class GodotInputHandler implements InputManager.InputDeviceListener {
|
||||||
|
|
||||||
private final SparseIntArray mJoystickIds = new SparseIntArray(4);
|
private final SparseIntArray mJoystickIds = new SparseIntArray(4);
|
||||||
private final SparseArray<Joystick> mJoysticksDevices = new SparseArray<>(4);
|
private final SparseArray<Joystick> mJoysticksDevices = new SparseArray<>(4);
|
||||||
|
private final HashSet<Integer> mHardwareKeyboardIds = new HashSet<>();
|
||||||
|
|
||||||
private final GodotRenderView mRenderView;
|
private final GodotRenderView mRenderView;
|
||||||
private final InputManager mInputManager;
|
private final InputManager mInputManager;
|
||||||
|
@ -114,6 +115,10 @@ public class GodotInputHandler implements InputManager.InputDeviceListener {
|
||||||
rotaryInputAxis = axis;
|
rotaryInputAxis = axis;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
boolean hasHardwareKeyboard() {
|
||||||
|
return !mHardwareKeyboardIds.isEmpty();
|
||||||
|
}
|
||||||
|
|
||||||
private boolean isKeyEventGameDevice(int source) {
|
private boolean isKeyEventGameDevice(int source) {
|
||||||
// Note that keyboards are often (SOURCE_KEYBOARD | SOURCE_DPAD)
|
// Note that keyboards are often (SOURCE_KEYBOARD | SOURCE_DPAD)
|
||||||
if (source == (InputDevice.SOURCE_KEYBOARD | InputDevice.SOURCE_DPAD))
|
if (source == (InputDevice.SOURCE_KEYBOARD | InputDevice.SOURCE_DPAD))
|
||||||
|
@ -195,7 +200,7 @@ public class GodotInputHandler implements InputManager.InputDeviceListener {
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean onTouchEvent(final MotionEvent event) {
|
public boolean onTouchEvent(final MotionEvent event) {
|
||||||
lastSeenToolType = event.getToolType(0);
|
lastSeenToolType = getEventToolType(event);
|
||||||
|
|
||||||
this.scaleGestureDetector.onTouchEvent(event);
|
this.scaleGestureDetector.onTouchEvent(event);
|
||||||
if (this.gestureDetector.onTouchEvent(event)) {
|
if (this.gestureDetector.onTouchEvent(event)) {
|
||||||
|
@ -221,7 +226,7 @@ public class GodotInputHandler implements InputManager.InputDeviceListener {
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean onGenericMotionEvent(MotionEvent event) {
|
public boolean onGenericMotionEvent(MotionEvent event) {
|
||||||
lastSeenToolType = event.getToolType(0);
|
lastSeenToolType = getEventToolType(event);
|
||||||
|
|
||||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && gestureDetector.onGenericMotionEvent(event)) {
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && gestureDetector.onGenericMotionEvent(event)) {
|
||||||
// The gesture detector has handled the event.
|
// The gesture detector has handled the event.
|
||||||
|
@ -310,11 +315,17 @@ public class GodotInputHandler implements InputManager.InputDeviceListener {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
int sources = device.getSources();
|
// Device may be an external keyboard; store the device id
|
||||||
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q &&
|
||||||
|
device.supportsSource(InputDevice.SOURCE_KEYBOARD) &&
|
||||||
|
device.isExternal() &&
|
||||||
|
device.getKeyboardType() == InputDevice.KEYBOARD_TYPE_ALPHABETIC) {
|
||||||
|
mHardwareKeyboardIds.add(deviceId);
|
||||||
|
}
|
||||||
|
|
||||||
// Device may not be a joystick or gamepad
|
// Device may not be a joystick or gamepad
|
||||||
if ((sources & InputDevice.SOURCE_GAMEPAD) != InputDevice.SOURCE_GAMEPAD &&
|
if (!device.supportsSource(InputDevice.SOURCE_GAMEPAD) &&
|
||||||
(sources & InputDevice.SOURCE_JOYSTICK) != InputDevice.SOURCE_JOYSTICK) {
|
!device.supportsSource(InputDevice.SOURCE_JOYSTICK)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -359,6 +370,8 @@ public class GodotInputHandler implements InputManager.InputDeviceListener {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onInputDeviceRemoved(int deviceId) {
|
public void onInputDeviceRemoved(int deviceId) {
|
||||||
|
mHardwareKeyboardIds.remove(deviceId);
|
||||||
|
|
||||||
// Check if the device has not been already removed
|
// Check if the device has not been already removed
|
||||||
if (mJoystickIds.indexOfKey(deviceId) < 0) {
|
if (mJoystickIds.indexOfKey(deviceId) < 0) {
|
||||||
return;
|
return;
|
||||||
|
@ -440,50 +453,52 @@ public class GodotInputHandler implements InputManager.InputDeviceListener {
|
||||||
return button;
|
return button;
|
||||||
}
|
}
|
||||||
|
|
||||||
static boolean isMouseEvent(MotionEvent event) {
|
private static int getEventToolType(MotionEvent event) {
|
||||||
return isMouseEvent(event.getSource());
|
return event.getPointerCount() > 0 ? event.getToolType(0) : MotionEvent.TOOL_TYPE_UNKNOWN;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static boolean isMouseEvent(int eventSource) {
|
static boolean isMouseEvent(MotionEvent event) {
|
||||||
boolean mouseSource = ((eventSource & InputDevice.SOURCE_MOUSE) == InputDevice.SOURCE_MOUSE) || ((eventSource & InputDevice.SOURCE_STYLUS) == InputDevice.SOURCE_STYLUS);
|
int toolType = getEventToolType(event);
|
||||||
|
int eventSource = event.getSource();
|
||||||
|
|
||||||
|
switch (toolType) {
|
||||||
|
case MotionEvent.TOOL_TYPE_FINGER:
|
||||||
|
return false;
|
||||||
|
|
||||||
|
case MotionEvent.TOOL_TYPE_MOUSE:
|
||||||
|
case MotionEvent.TOOL_TYPE_STYLUS:
|
||||||
|
case MotionEvent.TOOL_TYPE_ERASER:
|
||||||
|
return true;
|
||||||
|
|
||||||
|
case MotionEvent.TOOL_TYPE_UNKNOWN:
|
||||||
|
default:
|
||||||
|
boolean mouseSource =
|
||||||
|
((eventSource & InputDevice.SOURCE_MOUSE) == InputDevice.SOURCE_MOUSE) ||
|
||||||
|
((eventSource & (InputDevice.SOURCE_TOUCHSCREEN | InputDevice.SOURCE_STYLUS)) == InputDevice.SOURCE_STYLUS);
|
||||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
|
||||||
mouseSource = mouseSource || ((eventSource & InputDevice.SOURCE_MOUSE_RELATIVE) == InputDevice.SOURCE_MOUSE_RELATIVE);
|
mouseSource = mouseSource ||
|
||||||
|
((eventSource & InputDevice.SOURCE_MOUSE_RELATIVE) == InputDevice.SOURCE_MOUSE_RELATIVE);
|
||||||
}
|
}
|
||||||
return mouseSource;
|
return mouseSource;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static boolean handleMotionEvent(final MotionEvent event) {
|
static boolean handleMotionEvent(final MotionEvent event) {
|
||||||
|
return handleMotionEvent(event, event.getActionMasked());
|
||||||
|
}
|
||||||
|
|
||||||
|
static boolean handleMotionEvent(final MotionEvent event, int eventActionOverride) {
|
||||||
|
return handleMotionEvent(event, eventActionOverride, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
static boolean handleMotionEvent(final MotionEvent event, int eventActionOverride, boolean doubleTap) {
|
||||||
if (isMouseEvent(event)) {
|
if (isMouseEvent(event)) {
|
||||||
return handleMouseEvent(event);
|
return handleMouseEvent(event, eventActionOverride, doubleTap);
|
||||||
|
}
|
||||||
|
return handleTouchEvent(event, eventActionOverride, doubleTap);
|
||||||
}
|
}
|
||||||
|
|
||||||
return handleTouchEvent(event);
|
private static float getEventTiltX(MotionEvent event) {
|
||||||
}
|
|
||||||
|
|
||||||
static boolean handleMotionEvent(int eventSource, int eventAction, int buttonsMask, float x, float y) {
|
|
||||||
return handleMotionEvent(eventSource, eventAction, buttonsMask, x, y, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
static boolean handleMotionEvent(int eventSource, int eventAction, int buttonsMask, float x, float y, boolean doubleTap) {
|
|
||||||
return handleMotionEvent(eventSource, eventAction, buttonsMask, x, y, 0, 0, doubleTap);
|
|
||||||
}
|
|
||||||
|
|
||||||
static boolean handleMotionEvent(int eventSource, int eventAction, int buttonsMask, float x, float y, float deltaX, float deltaY, boolean doubleTap) {
|
|
||||||
if (isMouseEvent(eventSource)) {
|
|
||||||
return handleMouseEvent(eventAction, buttonsMask, x, y, deltaX, deltaY, doubleTap, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
return handleTouchEvent(eventAction, x, y, doubleTap);
|
|
||||||
}
|
|
||||||
|
|
||||||
static boolean handleMouseEvent(final MotionEvent event) {
|
|
||||||
final int eventAction = event.getActionMasked();
|
|
||||||
final float x = event.getX();
|
|
||||||
final float y = event.getY();
|
|
||||||
final int buttonsMask = event.getButtonState();
|
|
||||||
|
|
||||||
final float pressure = event.getPressure();
|
|
||||||
|
|
||||||
// Orientation is returned as a radian value between 0 to pi clockwise or 0 to -pi counterclockwise.
|
// Orientation is returned as a radian value between 0 to pi clockwise or 0 to -pi counterclockwise.
|
||||||
final float orientation = event.getOrientation();
|
final float orientation = event.getOrientation();
|
||||||
|
|
||||||
|
@ -493,8 +508,39 @@ public class GodotInputHandler implements InputManager.InputDeviceListener {
|
||||||
float tiltMult = (float)Math.sin(tilt);
|
float tiltMult = (float)Math.sin(tilt);
|
||||||
|
|
||||||
// To be consistent with expected tilt.
|
// To be consistent with expected tilt.
|
||||||
final float tiltX = (float)-Math.sin(orientation) * tiltMult;
|
return (float)-Math.sin(orientation) * tiltMult;
|
||||||
final float tiltY = (float)Math.cos(orientation) * tiltMult;
|
}
|
||||||
|
|
||||||
|
private static float getEventTiltY(MotionEvent event) {
|
||||||
|
// Orientation is returned as a radian value between 0 to pi clockwise or 0 to -pi counterclockwise.
|
||||||
|
final float orientation = event.getOrientation();
|
||||||
|
|
||||||
|
// Tilt is zero is perpendicular to the screen and pi/2 is flat on the surface.
|
||||||
|
final float tilt = event.getAxisValue(MotionEvent.AXIS_TILT);
|
||||||
|
|
||||||
|
float tiltMult = (float)Math.sin(tilt);
|
||||||
|
|
||||||
|
// To be consistent with expected tilt.
|
||||||
|
return (float)Math.cos(orientation) * tiltMult;
|
||||||
|
}
|
||||||
|
|
||||||
|
static boolean handleMouseEvent(final MotionEvent event) {
|
||||||
|
return handleMouseEvent(event, event.getActionMasked());
|
||||||
|
}
|
||||||
|
|
||||||
|
static boolean handleMouseEvent(final MotionEvent event, int eventActionOverride) {
|
||||||
|
return handleMouseEvent(event, eventActionOverride, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
static boolean handleMouseEvent(final MotionEvent event, int eventActionOverride, boolean doubleTap) {
|
||||||
|
return handleMouseEvent(event, eventActionOverride, event.getButtonState(), doubleTap);
|
||||||
|
}
|
||||||
|
|
||||||
|
static boolean handleMouseEvent(final MotionEvent event, int eventActionOverride, int buttonMaskOverride, boolean doubleTap) {
|
||||||
|
final float x = event.getX();
|
||||||
|
final float y = event.getY();
|
||||||
|
|
||||||
|
final float pressure = event.getPressure();
|
||||||
|
|
||||||
float verticalFactor = 0;
|
float verticalFactor = 0;
|
||||||
float horizontalFactor = 0;
|
float horizontalFactor = 0;
|
||||||
|
@ -516,15 +562,11 @@ public class GodotInputHandler implements InputManager.InputDeviceListener {
|
||||||
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) {
|
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) {
|
||||||
sourceMouseRelative = event.isFromSource(InputDevice.SOURCE_MOUSE_RELATIVE);
|
sourceMouseRelative = event.isFromSource(InputDevice.SOURCE_MOUSE_RELATIVE);
|
||||||
}
|
}
|
||||||
return handleMouseEvent(eventAction, buttonsMask, x, y, horizontalFactor, verticalFactor, false, sourceMouseRelative, pressure, tiltX, tiltY);
|
return handleMouseEvent(eventActionOverride, buttonMaskOverride, x, y, horizontalFactor, verticalFactor, doubleTap, sourceMouseRelative, pressure, getEventTiltX(event), getEventTiltY(event));
|
||||||
}
|
}
|
||||||
|
|
||||||
static boolean handleMouseEvent(int eventAction, int buttonsMask, float x, float y) {
|
static boolean handleMouseEvent(int eventAction, boolean sourceMouseRelative) {
|
||||||
return handleMouseEvent(eventAction, buttonsMask, x, y, 0, 0, false, false);
|
return handleMouseEvent(eventAction, 0, 0f, 0f, 0f, 0f, false, sourceMouseRelative, 1f, 0f, 0f);
|
||||||
}
|
|
||||||
|
|
||||||
static boolean handleMouseEvent(int eventAction, int buttonsMask, float x, float y, float deltaX, float deltaY, boolean doubleClick, boolean sourceMouseRelative) {
|
|
||||||
return handleMouseEvent(eventAction, buttonsMask, x, y, deltaX, deltaY, doubleClick, sourceMouseRelative, 1, 0, 0);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static boolean handleMouseEvent(int eventAction, int buttonsMask, float x, float y, float deltaX, float deltaY, boolean doubleClick, boolean sourceMouseRelative, float pressure, float tiltX, float tiltY) {
|
static boolean handleMouseEvent(int eventAction, int buttonsMask, float x, float y, float deltaX, float deltaY, boolean doubleClick, boolean sourceMouseRelative, float pressure, float tiltX, float tiltY) {
|
||||||
|
@ -563,37 +605,39 @@ public class GodotInputHandler implements InputManager.InputDeviceListener {
|
||||||
}
|
}
|
||||||
|
|
||||||
static boolean handleTouchEvent(final MotionEvent event) {
|
static boolean handleTouchEvent(final MotionEvent event) {
|
||||||
|
return handleTouchEvent(event, event.getActionMasked());
|
||||||
|
}
|
||||||
|
|
||||||
|
static boolean handleTouchEvent(final MotionEvent event, int eventActionOverride) {
|
||||||
|
return handleTouchEvent(event, eventActionOverride, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
static boolean handleTouchEvent(final MotionEvent event, int eventActionOverride, boolean doubleTap) {
|
||||||
final int pointerCount = event.getPointerCount();
|
final int pointerCount = event.getPointerCount();
|
||||||
if (pointerCount == 0) {
|
if (pointerCount == 0) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
final float[] positions = new float[pointerCount * 3]; // pointerId1, x1, y1, pointerId2, etc...
|
final float[] positions = new float[pointerCount * 6]; // pointerId1, x1, y1, pressure1, tiltX1, tiltY1, pointerId2, etc...
|
||||||
|
|
||||||
for (int i = 0; i < pointerCount; i++) {
|
for (int i = 0; i < pointerCount; i++) {
|
||||||
positions[i * 3 + 0] = event.getPointerId(i);
|
positions[i * 6 + 0] = event.getPointerId(i);
|
||||||
positions[i * 3 + 1] = event.getX(i);
|
positions[i * 6 + 1] = event.getX(i);
|
||||||
positions[i * 3 + 2] = event.getY(i);
|
positions[i * 6 + 2] = event.getY(i);
|
||||||
|
positions[i * 6 + 3] = event.getPressure(i);
|
||||||
|
positions[i * 6 + 4] = getEventTiltX(event);
|
||||||
|
positions[i * 6 + 5] = getEventTiltY(event);
|
||||||
}
|
}
|
||||||
final int action = event.getActionMasked();
|
|
||||||
final int actionPointerId = event.getPointerId(event.getActionIndex());
|
final int actionPointerId = event.getPointerId(event.getActionIndex());
|
||||||
|
|
||||||
return handleTouchEvent(action, actionPointerId, pointerCount, positions, false);
|
switch (eventActionOverride) {
|
||||||
}
|
|
||||||
|
|
||||||
static boolean handleTouchEvent(int eventAction, float x, float y, boolean doubleTap) {
|
|
||||||
return handleTouchEvent(eventAction, 0, 1, new float[] { 0, x, y }, doubleTap);
|
|
||||||
}
|
|
||||||
|
|
||||||
static boolean handleTouchEvent(int eventAction, int actionPointerId, int pointerCount, float[] positions, boolean doubleTap) {
|
|
||||||
switch (eventAction) {
|
|
||||||
case MotionEvent.ACTION_DOWN:
|
case MotionEvent.ACTION_DOWN:
|
||||||
case MotionEvent.ACTION_CANCEL:
|
case MotionEvent.ACTION_CANCEL:
|
||||||
case MotionEvent.ACTION_UP:
|
case MotionEvent.ACTION_UP:
|
||||||
case MotionEvent.ACTION_MOVE:
|
case MotionEvent.ACTION_MOVE:
|
||||||
case MotionEvent.ACTION_POINTER_UP:
|
case MotionEvent.ACTION_POINTER_UP:
|
||||||
case MotionEvent.ACTION_POINTER_DOWN: {
|
case MotionEvent.ACTION_POINTER_DOWN: {
|
||||||
GodotLib.dispatchTouchEvent(eventAction, actionPointerId, pointerCount, positions, doubleTap);
|
GodotLib.dispatchTouchEvent(eventActionOverride, actionPointerId, pointerCount, positions, doubleTap);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -294,11 +294,13 @@ JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_dispatchTouchEvent(JN
|
||||||
|
|
||||||
Vector<AndroidInputHandler::TouchPos> points;
|
Vector<AndroidInputHandler::TouchPos> points;
|
||||||
for (int i = 0; i < pointer_count; i++) {
|
for (int i = 0; i < pointer_count; i++) {
|
||||||
jfloat p[3];
|
jfloat p[6];
|
||||||
env->GetFloatArrayRegion(position, i * 3, 3, p);
|
env->GetFloatArrayRegion(position, i * 6, 6, p);
|
||||||
AndroidInputHandler::TouchPos tp;
|
AndroidInputHandler::TouchPos tp;
|
||||||
tp.pos = Point2(p[1], p[2]);
|
|
||||||
tp.id = (int)p[0];
|
tp.id = (int)p[0];
|
||||||
|
tp.pos = Point2(p[1], p[2]);
|
||||||
|
tp.pressure = p[3];
|
||||||
|
tp.tilt = Vector2(p[4], p[5]);
|
||||||
points.push_back(tp);
|
points.push_back(tp);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue