Browse Source

Fixes Android FileDialog

- Go up was not working, simplify was used one time too much
- Added GestureHandler
  - Added doubleTap to recognize open dir
  - Fixed scroll where sometimes the scroll jumped between start and end when pointer was outside or on the edge of the scroll area
Alexander Holland 5 years ago
parent
commit
b1b308411a

+ 0 - 1
platform/android/dir_access_jandroid.cpp

@@ -110,7 +110,6 @@ String DirAccessJAndroid::get_drive(int p_drive) {
 Error DirAccessJAndroid::change_dir(String p_dir) {
 
 	JNIEnv *env = ThreadAndroid::get_env();
-	p_dir = p_dir.simplify_path();
 
 	if (p_dir == "" || p_dir == "." || (p_dir == ".." && current_dir == ""))
 		return OK;

+ 10 - 0
platform/android/java/lib/src/org/godotengine/godot/GodotLib.java

@@ -99,6 +99,16 @@ public class GodotLib {
 	 */
 	public static native void hover(int type, int x, int y);
 
+	/**
+	 * Forward double_tap events from the main thread to the GL thread.
+	 */
+	public static native void double_tap(int x, int y);
+
+	/**
+	 * Forward scroll events from the main thread to the GL thread.
+	 */
+	public static native void scroll(int x, int y);
+
 	/**
 	 * Forward accelerometer sensor events from the main thread to the GL thread.
 	 * @see android.hardware.SensorEventListener#onSensorChanged(SensorEvent)

+ 5 - 0
platform/android/java/lib/src/org/godotengine/godot/GodotView.java

@@ -32,8 +32,10 @@ package org.godotengine.godot;
 import android.annotation.SuppressLint;
 import android.graphics.PixelFormat;
 import android.opengl.GLSurfaceView;
+import android.view.GestureDetector;
 import android.view.KeyEvent;
 import android.view.MotionEvent;
+import org.godotengine.godot.input.GodotGestureHandler;
 import org.godotengine.godot.input.GodotInputHandler;
 import org.godotengine.godot.utils.GLUtils;
 import org.godotengine.godot.xr.XRMode;
@@ -68,6 +70,7 @@ public class GodotView extends GLSurfaceView {
 
 	private final Godot activity;
 	private final GodotInputHandler inputHandler;
+	private final GestureDetector detector;
 	private final GodotRenderer godotRenderer;
 
 	public GodotView(Godot activity, XRMode xrMode, boolean p_use_gl3, boolean p_use_32_bits, boolean p_use_debug_opengl) {
@@ -78,6 +81,7 @@ public class GodotView extends GLSurfaceView {
 
 		this.activity = activity;
 		this.inputHandler = new GodotInputHandler(this);
+		this.detector = new GestureDetector(activity, new GodotGestureHandler(this));
 		this.godotRenderer = new GodotRenderer();
 		init(xrMode, false, 16, 0);
 	}
@@ -90,6 +94,7 @@ public class GodotView extends GLSurfaceView {
 	@Override
 	public boolean onTouchEvent(MotionEvent event) {
 		super.onTouchEvent(event);
+		this.detector.onTouchEvent(event);
 		return activity.gotTouchEvent(event);
 	}
 

+ 106 - 0
platform/android/java/lib/src/org/godotengine/godot/input/GodotGestureHandler.java

@@ -0,0 +1,106 @@
+/*************************************************************************/
+/*  GodotGestureHandler.java                                             */
+/*************************************************************************/
+/*                       This file is part of:                           */
+/*                           GODOT ENGINE                                */
+/*                      https://godotengine.org                          */
+/*************************************************************************/
+/* Copyright (c) 2007-2020 Juan Linietsky, Ariel Manzur.                 */
+/* Copyright (c) 2014-2020 Godot Engine contributors (cf. AUTHORS.md).   */
+/*                                                                       */
+/* Permission is hereby granted, free of charge, to any person obtaining */
+/* a copy of this software and associated documentation files (the       */
+/* "Software"), to deal in the Software without restriction, including   */
+/* without limitation the rights to use, copy, modify, merge, publish,   */
+/* distribute, sublicense, and/or sell copies of the Software, and to    */
+/* permit persons to whom the Software is furnished to do so, subject to */
+/* the following conditions:                                             */
+/*                                                                       */
+/* The above copyright notice and this permission notice shall be        */
+/* included in all copies or substantial portions of the Software.       */
+/*                                                                       */
+/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,       */
+/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF    */
+/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/
+/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY  */
+/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,  */
+/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE     */
+/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.                */
+/*************************************************************************/
+
+package org.godotengine.godot.input;
+
+import android.util.Log;
+import android.view.GestureDetector;
+import android.view.MotionEvent;
+import org.godotengine.godot.GodotLib;
+import org.godotengine.godot.GodotView;
+
+/**
+ * Handles gesture input related events for the {@link GodotView} view.
+ * https://developer.android.com/reference/android/view/GestureDetector.SimpleOnGestureListener
+ */
+public class GodotGestureHandler extends GestureDetector.SimpleOnGestureListener {
+
+	private final GodotView godotView;
+
+	public GodotGestureHandler(GodotView godotView) {
+		this.godotView = godotView;
+	}
+
+	private void queueEvent(Runnable task) {
+		godotView.queueEvent(task);
+	}
+
+	@Override
+	public boolean onDown(MotionEvent event) {
+		super.onDown(event);
+		//Log.i("GodotGesture", "onDown");
+		return true;
+	}
+
+	@Override
+	public boolean onSingleTapConfirmed(MotionEvent event) {
+		super.onSingleTapConfirmed(event);
+		return true;
+	}
+
+	@Override
+	public void onLongPress(MotionEvent event) {
+		//Log.i("GodotGesture", "onLongPress");
+	}
+
+	@Override
+	public boolean onDoubleTap(MotionEvent event) {
+		//Log.i("GodotGesture", "onDoubleTap");
+		final int x = Math.round(event.getX());
+		final int y = Math.round(event.getY());
+		queueEvent(new Runnable() {
+			@Override
+			public void run() {
+				GodotLib.double_tap(x, y);
+			}
+		});
+		return true;
+	}
+
+	@Override
+	public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
+		//Log.i("GodotGesture", "onScroll");
+		final int x = Math.round(distanceX);
+		final int y = Math.round(distanceY);
+		queueEvent(new Runnable() {
+			@Override
+			public void run() {
+				GodotLib.scroll(x, y);
+			}
+		});
+		return true;
+	}
+
+	@Override
+	public boolean onFling(MotionEvent event1, MotionEvent event2, float velocityX, float velocityY) {
+		//Log.i("GodotGesture", "onFling");
+		return true;
+	}
+}

+ 14 - 0
platform/android/java_godot_lib_jni.cpp

@@ -835,6 +835,20 @@ JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_hover(JNIEnv *env, jo
 	os_android->process_hover(p_type, Point2(p_x, p_y));
 }
 
+JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_double_tap(JNIEnv *env, jobject obj, jint p_x, jint p_y) {
+	if (step == 0)
+		return;
+
+	os_android->process_double_tap(Point2(p_x, p_y));
+}
+
+JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_scroll(JNIEnv *env, jobject obj, jint p_x, jint p_y) {
+	if (step == 0)
+		return;
+
+	os_android->process_scroll(Point2(p_x, p_y));
+}
+
 /*
  * Android Key codes.
  */

+ 2 - 0
platform/android/java_godot_lib_jni.h

@@ -46,6 +46,8 @@ JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_step(JNIEnv *env, job
 JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_back(JNIEnv *env, jobject obj);
 JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_touch(JNIEnv *env, jobject obj, jint ev, jint pointer, jint count, jintArray positions);
 JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_hover(JNIEnv *env, jobject obj, jint p_type, jint p_x, jint p_y);
+JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_double_tap(JNIEnv *env, jobject obj, jint p_x, jint p_y);
+JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_scroll(JNIEnv *env, jobject obj, jint p_x, jint p_y);
 JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_key(JNIEnv *env, jobject obj, jint p_scancode, jint p_unicode_char, jboolean p_pressed);
 JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_joybutton(JNIEnv *env, jobject obj, jint p_device, jint p_button, jboolean p_pressed);
 JNIEXPORT void JNICALL Java_org_godotengine_godot_GodotLib_joyaxis(JNIEnv *env, jobject obj, jint p_device, jint p_axis, jfloat p_value);

+ 20 - 0
platform/android/os_android.cpp

@@ -502,6 +502,26 @@ void OS_Android::process_hover(int p_type, Point2 p_pos) {
 	}
 }
 
+void OS_Android::process_double_tap(Point2 p_pos) {
+	Ref<InputEventMouseButton> ev;
+	ev.instance();
+	ev->set_position(p_pos);
+	ev->set_global_position(p_pos);
+	ev->set_pressed(true);
+	ev->set_doubleclick(true);
+	ev->set_button_index(1);
+	input->parse_input_event(ev);
+}
+
+void OS_Android::process_scroll(Point2 p_pos) {
+	Ref<InputEventPanGesture> ev;
+	ev.instance();
+	ev->set_position(p_pos);
+	ev->set_delta(p_pos - scroll_prev_pos);
+	input->parse_input_event(ev);
+	scroll_prev_pos = p_pos;
+}
+
 void OS_Android::process_accelerometer(const Vector3 &p_accelerometer) {
 
 	input->set_accelerometer(p_accelerometer);

+ 3 - 0
platform/android/os_android.h

@@ -70,6 +70,7 @@ public:
 private:
 	Vector<TouchPos> touch;
 	Point2 hover_prev_pos; // needed to calculate the relative position on hover events
+	Point2 scroll_prev_pos; // needed to calculate the relative position on scroll events
 
 	bool use_gl2;
 	bool use_apk_expansion;
@@ -187,6 +188,8 @@ public:
 	void process_gyroscope(const Vector3 &p_gyroscope);
 	void process_touch(int p_what, int p_pointer, const Vector<TouchPos> &p_points);
 	void process_hover(int p_type, Point2 p_pos);
+	void process_double_tap(Point2 p_pos);
+	void process_scroll(Point2 p_pos);
 	void process_joy_event(JoypadEvent p_event);
 	void process_event(Ref<InputEvent> p_event);
 	void init_video_mode(int p_video_width, int p_video_height);