diff options
author | langsmith <langstonlmcs@gmail.com> | 2019-09-19 16:12:31 -0700 |
---|---|---|
committer | langsmith <langstonlmcs@gmail.com> | 2019-10-07 15:33:23 -0700 |
commit | 867edcb8a6713479cbbcb939672dc0b881e758b6 (patch) | |
tree | 1d995cb6d6a89204fd5479e6bbecd4c8d6150cf2 | |
parent | 23cebe20fed0e3ebc3328c6345af4e32d86cfcf5 (diff) | |
download | qtlocation-mapboxgl-867edcb8a6713479cbbcb939672dc0b881e758b6.tar.gz |
[android] increased support for keyboard camera movement
3 files changed, 241 insertions, 22 deletions
diff --git a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/MapKeyListener.java b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/MapKeyListener.java index afb80027d9..6b3d409cf2 100644 --- a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/MapKeyListener.java +++ b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/MapKeyListener.java @@ -5,6 +5,7 @@ import android.os.Handler; import android.os.Looper; import android.support.annotation.NonNull; import android.support.annotation.Nullable; +import android.util.Log; import android.view.KeyEvent; import android.view.MotionEvent; import android.view.ViewConfiguration; @@ -20,9 +21,11 @@ import android.view.ViewConfiguration; */ final class MapKeyListener { + private final String TAG = "MapKeyListener"; private final Transform transform; private final UiSettings uiSettings; private final MapGestureDetector mapGestureDetector; + private int bearingIndex = 1; @Nullable private TrackballLongPressTimeOut currentTrackballLongPressTimeOut; @@ -34,16 +37,18 @@ final class MapKeyListener { } /** - * Called when the user presses a key, alse called for repeated keys held down. + * Called when the user presses a key, also called for repeated keys held down. * * @param keyCode the id of the pressed key * @param event the related key event - * @return true if the wevent is handled + * @return true if the event is handled */ boolean onKeyDown(int keyCode, @NonNull KeyEvent event) { // If the user has held the scroll key down for a while then accelerate - // the scroll speed - double scrollDist = event.getRepeatCount() >= 5 ? 50.0 : 10.0; + // the map camera movement speeds + double scrollDist = event.getRepeatCount() >= 5 ? 90.0 : 50.0; + double pitchDist = event.getRepeatCount() >= 5 ? 5.00 : 1.0; + double rotateDist = event.getRepeatCount() >= 5 ? 20.0 : 1.0; // Check which key was pressed via hardware/real key code switch (keyCode) { @@ -62,8 +67,18 @@ final class MapKeyListener { // Cancel any animation transform.cancelTransitions(); - // Move left - transform.moveBy(scrollDist, 0.0, 0 /*no animation*/); + // Check if the shift key is being held down + if (event.isShiftPressed()) { + if (!uiSettings.isRotateGesturesEnabled()) { + return false; + } + transform.setBearing(bearingIndex * rotateDist); + Log.d(TAG, "transform.getBearing() = " + transform.getBearing()); + bearingIndex++; + } else { + // Move map camera left + transform.moveBy(scrollDist, 0.0, 0 /*no animation*/); + } return true; case KeyEvent.KEYCODE_DPAD_RIGHT: @@ -74,8 +89,19 @@ final class MapKeyListener { // Cancel any animation transform.cancelTransitions(); - // Move right - transform.moveBy(-scrollDist, 0.0, 0 /*no animation*/); + // Check if the shift key is being held down + if (event.isShiftPressed()) { + if (!uiSettings.isRotateGesturesEnabled()) { + return false; + } + transform.setBearing(180 - (bearingIndex * rotateDist)); + Log.d(TAG, "transform.getBearing() = " + transform.getBearing()); + bearingIndex++; + } else { + // Move map camera right + transform.moveBy(-scrollDist, 0.0, 0 /*no animation*/); + } + return true; case KeyEvent.KEYCODE_DPAD_UP: @@ -86,8 +112,20 @@ final class MapKeyListener { // Cancel any animation transform.cancelTransitions(); - // Move up - transform.moveBy(0.0, scrollDist, 0 /*no animation*/); + // Check if the shift key is being held down + if (event.isShiftPressed()) { + if (!uiSettings.isTiltGesturesEnabled()) { + return false; + } + + // Increase map camera pitch value + transform.setTilt(transform.getTilt() + pitchDist); + + } else { + // Move map camera target up + transform.moveBy(0.0, scrollDist, 0 /*no animation*/); + } + return true; case KeyEvent.KEYCODE_DPAD_DOWN: @@ -98,10 +136,52 @@ final class MapKeyListener { // Cancel any animation transform.cancelTransitions(); - // Move down - transform.moveBy(0.0, -scrollDist, 0 /*no animation*/); + // Check if the shift key is being held down + if (event.isShiftPressed()) { + if (!uiSettings.isTiltGesturesEnabled()) { + return false; + } + + // Decrease map camera pitch value + transform.setTilt(transform.getTilt() - pitchDist); + + } else { + // Move map target down + transform.moveBy(0.0, -scrollDist, 0 /*no animation*/); + } + return true; + case KeyEvent.KEYCODE_EQUALS: + + // We're interested in the equals sign because most keyboards have the + // + and = symbols on the same key. KeyEvent.KEYCODE_EQUALS fires when + // this key is tapped. + + // Cancel any animation + transform.cancelTransitions(); + + if (!uiSettings.isZoomGesturesEnabled()) { + return false; + } + // Zoom the map camera closer to the map (i.e. increase the map camera zoom level number) + zoomMapCameraIn(); + + return true; + + case KeyEvent.KEYCODE_MINUS: + + // Cancel any animation + transform.cancelTransitions(); + + if (!uiSettings.isZoomGesturesEnabled()) { + return false; + } + + // Pull the map camera out away from the map (i.e. decrease the map camera zoom level number) + zoomMapCameraOut(); + + return true; default: // We are not interested in this key return false; @@ -127,8 +207,7 @@ final class MapKeyListener { } // Zoom out - PointF focalPoint = new PointF(uiSettings.getWidth() / 2, uiSettings.getHeight() / 2); - mapGestureDetector.zoomOutAnimated(focalPoint, true); + zoomMapCameraOut(); return true; default: @@ -163,8 +242,7 @@ final class MapKeyListener { } // Zoom in - PointF focalPoint = new PointF(uiSettings.getWidth() / 2, uiSettings.getHeight() / 2); - mapGestureDetector.zoomInAnimated(focalPoint, true); + zoomMapCameraIn(); return true; } @@ -191,7 +269,7 @@ final class MapKeyListener { transform.cancelTransitions(); // Scroll the map - transform.moveBy(-10.0 * event.getX(), -10.0 * event.getY(), 0 /*no animation*/); + zoomMapCameraIn(); return true; // Trackball was pushed in so start tracking and tell system we are @@ -218,8 +296,7 @@ final class MapKeyListener { // Only handle if we have not already long pressed if (currentTrackballLongPressTimeOut != null) { // Zoom in - PointF focalPoint = new PointF(uiSettings.getWidth() / 2, uiSettings.getHeight() / 2); - mapGestureDetector.zoomInAnimated(focalPoint, true); + zoomMapCameraIn(); } return true; @@ -260,12 +337,27 @@ final class MapKeyListener { // Check if the trackball is still pressed if (!cancelled) { // Zoom out - PointF pointF = new PointF(uiSettings.getWidth() / 2, uiSettings.getHeight() / 2); - mapGestureDetector.zoomOutAnimated(pointF, true); + zoomMapCameraOut(); // Ensure the up action is not run currentTrackballLongPressTimeOut = null; } } } + + /** + * Moves the map camera towards from the map plane. + */ + private void zoomMapCameraIn() { + PointF focalPoint = new PointF(uiSettings.getWidth() / 2, uiSettings.getHeight() / 2); + mapGestureDetector.zoomInAnimated(focalPoint, true); + } + + /** + * Moves the map camera away from the map plane + */ + private void zoomMapCameraOut() { + PointF focalPoint = new PointF(uiSettings.getWidth() / 2, uiSettings.getHeight() / 2); + mapGestureDetector.zoomOutAnimated(focalPoint, true); + } } diff --git a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/MapView.java b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/MapView.java index 4521d2ae60..fcc29b3ae6 100644 --- a/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/MapView.java +++ b/platform/android/MapboxGLAndroidSDK/src/main/java/com/mapbox/mapboxsdk/maps/MapView.java @@ -65,6 +65,7 @@ public class MapView extends FrameLayout implements NativeMapView.ViewCallback { private final MapChangeReceiver mapChangeReceiver = new MapChangeReceiver(); private final MapCallback mapCallback = new MapCallback(); private final InitialRenderCallback initialRenderCallback = new InitialRenderCallback(); + private static final String TAG = "Mbgl-MapView"; @Nullable private NativeMap nativeMapView; @@ -131,9 +132,20 @@ public class MapView extends FrameLayout implements NativeMapView.ViewCallback { // inflate view View view = LayoutInflater.from(context).inflate(R.layout.mapbox_mapview_internal, this); + view.setNextFocusForwardId(R.id.compassView); + view.setNextFocusRightId(R.id.compassView); + view.setNextFocusLeftId(R.id.attributionView); compassView = view.findViewById(R.id.compassView); + compassView.setNextFocusForwardId(R.id.attributionView); + compassView.setNextFocusRightId(R.id.attributionView); + compassView.setNextFocusLeftId(view.getId()); attrView = view.findViewById(R.id.attributionView); attrView.setImageDrawable(BitmapUtils.getDrawableFromRes(getContext(), R.drawable.mapbox_info_bg_selector)); + attrView = view.findViewById(R.id.attributionView); + attrView.setImageDrawable(BitmapUtils.getDrawableFromRes(getContext(), R.drawable.mapbox_info_bg_selector)); + attrView.setNextFocusForwardId(view.getId()); + attrView.setNextFocusRightId(R.id.compassView); + attrView.setNextFocusLeftId(view.getId()); logoView = view.findViewById(R.id.logoView); logoView.setImageDrawable(BitmapUtils.getDrawableFromRes(getContext(), R.drawable.mapbox_logo_icon)); @@ -180,7 +192,6 @@ public class MapView extends FrameLayout implements NativeMapView.ViewCallback { mapGestureDetector = new MapGestureDetector(context, transform, proj, uiSettings, annotationManager, cameraDispatcher); mapKeyListener = new MapKeyListener(transform, uiSettings, mapGestureDetector); - // compass compassView.injectCompassAnimationListener(createCompassAnimationListener(cameraDispatcher)); compassView.setOnClickListener(createCompassClickListener(cameraDispatcher)); diff --git a/platform/android/MapboxGLAndroidSDKTestApp/src/androidTest/java/com/mapbox/mapboxsdk/maps/MapKeyListenerTest.kt b/platform/android/MapboxGLAndroidSDKTestApp/src/androidTest/java/com/mapbox/mapboxsdk/maps/MapKeyListenerTest.kt new file mode 100644 index 0000000000..62506f1b9c --- /dev/null +++ b/platform/android/MapboxGLAndroidSDKTestApp/src/androidTest/java/com/mapbox/mapboxsdk/maps/MapKeyListenerTest.kt @@ -0,0 +1,116 @@ +package com.mapbox.mapboxsdk.maps + +import android.support.test.espresso.Espresso.onView +import android.support.test.espresso.action.EspressoKey +import android.support.test.espresso.action.ViewActions +import android.support.test.espresso.matcher.ViewMatchers.withId +import android.view.KeyEvent +import com.mapbox.mapboxsdk.camera.CameraPosition +import com.mapbox.mapboxsdk.camera.CameraUpdateFactory +import com.mapbox.mapboxsdk.testapp.R +import com.mapbox.mapboxsdk.testapp.activity.BaseTest +import com.mapbox.mapboxsdk.testapp.activity.maplayout.SimpleMapActivity +import org.junit.Assert.assertNotEquals +import org.junit.Before +import org.junit.Test + +class MapKeyListenerTest : BaseTest() { + override fun getActivityClass() = SimpleMapActivity::class.java + + private var maxWidth: Int = 0 + private var maxHeight: Int = 0 + + @Before + fun setup() { + maxWidth = mapView.width + maxHeight = mapView.height + } + + @Test + fun pitchAdjustWithShiftAndUp() { + validateTestSetup() + var initialCameraPosition: CameraPosition? = null + rule.runOnUiThread { + // zoom in so we can move vertically + mapboxMap.moveCamera(CameraUpdateFactory.zoomTo(10.0)) + initialCameraPosition = mapboxMap.cameraPosition + mapboxMap.uiSettings.isTiltGesturesEnabled = true + } + // Tap the up arrow while holding shift on the keyboard directional pad + onView(withId(R.id.mapView)).perform(ViewActions.pressKey( + EspressoKey.Builder() + .withShiftPressed(true) + .withKeyCode(KeyEvent.KEYCODE_DPAD_UP) + .build())) + + rule.runOnUiThread { + assertNotEquals(initialCameraPosition!!.tilt, mapboxMap.cameraPosition.tilt) + } + } + + @Test + fun bearingAdjustWithShiftAndLeft() { + validateTestSetup() + var initialCameraPosition: CameraPosition? = null + rule.runOnUiThread { + initialCameraPosition = mapboxMap.cameraPosition + mapboxMap.uiSettings.isRotateGesturesEnabled = true + } + // Tap the left arrow while holding shift on the keyboard directional pad + onView(withId(R.id.mapView)).perform(ViewActions.pressKey( + EspressoKey.Builder() + .withShiftPressed(true) + .withKeyCode(KeyEvent.KEYCODE_DPAD_LEFT) + .build())) + + rule.runOnUiThread { + assertNotEquals(initialCameraPosition!!.bearing, mapboxMap.cameraPosition.bearing) + } + } + + @Test + fun targetAdjustWithUp() { + validateTestSetup() + var initialCameraPosition: CameraPosition? = null + rule.runOnUiThread { + // zoom in so we can move vertically + mapboxMap.moveCamera(CameraUpdateFactory.zoomTo(4.0)) + initialCameraPosition = mapboxMap.cameraPosition + mapboxMap.uiSettings.isQuickZoomGesturesEnabled = true + } + + // Tap the up arrow on the keyboard directional pad + onView(withId(R.id.mapView)).perform(ViewActions.pressKey( + EspressoKey.Builder() + .withKeyCode(KeyEvent.KEYCODE_DPAD_UP) + .build())) + + rule.runOnUiThread { + assertNotEquals(initialCameraPosition!!.target.latitude, mapboxMap.cameraPosition.target.latitude) + assertNotEquals(initialCameraPosition!!.target.longitude, mapboxMap.cameraPosition.target.longitude) + } + } + + @Test + fun targetAdjustWithDown() { + validateTestSetup() + var initialCameraPosition: CameraPosition? = null + rule.runOnUiThread { + // zoom in so we can move vertically + mapboxMap.moveCamera(CameraUpdateFactory.zoomTo(4.0)) + initialCameraPosition = mapboxMap.cameraPosition + mapboxMap.uiSettings.isQuickZoomGesturesEnabled = true + } + + // Tap the down arrow on the keyboard directional pad + onView(withId(R.id.mapView)).perform(ViewActions.pressKey( + EspressoKey.Builder() + .withKeyCode(KeyEvent.KEYCODE_DPAD_DOWN) + .build())) + + rule.runOnUiThread { + assertNotEquals(initialCameraPosition!!.target.latitude, mapboxMap.cameraPosition.target.latitude) + assertNotEquals(initialCameraPosition!!.target.longitude, mapboxMap.cameraPosition.target.longitude) + } + } +}
\ No newline at end of file |