move fling gesture detector to MapEventLayer

This commit is contained in:
Hannes Janetzek 2013-07-08 11:48:35 +02:00
parent 4d9d678669
commit 7229d8d596
6 changed files with 212 additions and 67 deletions

View File

@ -52,5 +52,10 @@ public class AndroidMotionEvent extends MotionEvent {
return mEvent.getPointerCount();
}
@Override
public long getTime() {
return mEvent.getEventTime();
}
}

View File

@ -2,7 +2,10 @@ package org.oscim.gdx;
import org.oscim.backend.input.MotionEvent;
public class GdxMotionEvent extends MotionEvent {
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.InputProcessor;
public class GdxMotionEvent extends MotionEvent implements InputProcessor{
@Override
public int getAction() {
@ -34,4 +37,50 @@ public class GdxMotionEvent extends MotionEvent {
return 0;
}
@Override
public long getTime() {
return 0;
}
// -------- InputProcessor ----------
@Override
public boolean keyDown(int keycode) {
return false;
}
@Override
public boolean keyUp(int keycode) {
return false;
}
@Override
public boolean keyTyped(char character) {
return false;
}
@Override
public boolean touchDown(int screenX, int screenY, int pointer, int button) {
return false;
}
@Override
public boolean touchUp(int screenX, int screenY, int pointer, int button) {
return false;
}
@Override
public boolean touchDragged(int screenX, int screenY, int pointer) {
return false;
}
@Override
public boolean mouseMoved(int screenX, int screenY) {
return false;
}
@Override
public boolean scrolled(int amount) {
return false;
}
}

View File

@ -28,6 +28,8 @@ public abstract class MotionEvent {
public static final int ACTION_POINTER_INDEX_MASK = 0xff00;
public static final int ACTION_POINTER_INDEX_SHIFT = 8;
public abstract long getTime();
public abstract int getAction();
public abstract float getX();

View File

@ -25,6 +25,7 @@ public abstract class InputLayer extends Layer {
super(mapView);
}
/**
* By default does nothing (<code>return false</code>). If you handled the
* Event, return <code>true</code>, otherwise return <code>false</code>. If
@ -146,26 +147,26 @@ public abstract class InputLayer extends Layer {
return false;
}
/**
* By default does nothing (<code>return false</code>). If you handled the
* Event, return <code>true</code>, otherwise return <code>false</code>. If
* you returned <code>true</code> none of the following Overlays or the
* underlying {@link MapView} has the chance to handle this event.
*
* @param pEvent1
* ...
* @param pEvent2
* ...
* @param pVelocityX
* ...
* @param pVelocityY
* ...
* @return ...
*/
public boolean onFling(MotionEvent pEvent1, MotionEvent pEvent2,
float pVelocityX, float pVelocityY) {
return false;
}
///**
// * By default does nothing (<code>return false</code>). If you handled the
// * Event, return <code>true</code>, otherwise return <code>false</code>. If
// * you returned <code>true</code> none of the following Overlays or the
// * underlying {@link MapView} has the chance to handle this event.
// *
// * @param pEvent1
// * ...
// * @param pEvent2
// * ...
// * @param pVelocityX
// * ...
// * @param pVelocityY
// * ...
// * @return ...
// */
//public boolean onFling(MotionEvent pEvent1, MotionEvent pEvent2,
// float pVelocityX, float pVelocityY) {
// return false;
//}
/**
* By default does nothing (<code>return false</code>). If you handled the

View File

@ -62,15 +62,20 @@ public class MapEventLayer extends InputLayer {
protected static final float PINCH_TILT_THRESHOLD = 1f;
private final MapViewPosition mMapPosition;
private final VelocityTracker mTracker;
public MapEventLayer(MapView mapView) {
super(mapView);
mMapPosition = mapView.getMapViewPosition();
mTracker = new VelocityTracker();
}
private long mPrevTime;
@Override
public boolean onTouchEvent(MotionEvent e) {
mPrevTime = e.getTime();
int action = getAction(e);
if (action == MotionEvent.ACTION_DOWN) {
@ -82,10 +87,13 @@ public class MapEventLayer extends InputLayer {
mPrevX = e.getX(0);
mPrevY = e.getY(0);
return true; //onActionDown(e);
mTracker.start(mPrevX, mPrevY, e.getTime());
return true;
} else if (action == MotionEvent.ACTION_MOVE) {
return onActionMove(e);
} else if (action == MotionEvent.ACTION_UP) {
onFling(mTracker.getVelocityX(), mTracker.getVelocityY());
return true;
} else if (action == MotionEvent.ACTION_CANCEL) {
mDoubleTap = false;
@ -116,6 +124,8 @@ public class MapEventLayer extends InputLayer {
float width = mMapView.getWidth();
float height = mMapView.getHeight();
mTracker.update(x1, y1, e.getTime());
// return if detect a new gesture, as indicated by a large jump
if (Math.abs(mx) > JUMP_THRESHOLD || Math.abs(my) > JUMP_THRESHOLD)
return true;
@ -133,6 +143,7 @@ public class MapEventLayer extends InputLayer {
}
if (e.getPointerCount() < 2) {
if (mx > 1 || mx < -1 || my > 1 || my < -1) {
mMapPosition.moveMap(mx, my);
mMapView.updateMap(true);
@ -281,9 +292,7 @@ public class MapEventLayer extends InputLayer {
return false;
}
@Override
public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
float velocityY) {
private boolean onFling(float velocityX, float velocityY) {
if (mWasMulti)
return true;
@ -303,7 +312,7 @@ public class MapEventLayer extends InputLayer {
// float move = Math.min(mMapView.getWidth(), mMapView.getHeight()) * 2 / 3;
// mMapPosition.animateTo(vx * move, vy * move, 250);
//} else {
float s = (200 / CanvasAdapter.dpi);
float s = 1; //(200 / CanvasAdapter.dpi);
mMapPosition.animateFling(
Math.round(velocityX * s),
@ -320,4 +329,102 @@ public class MapEventLayer extends InputLayer {
+ " " + mBeginTilt);
}
/*******************************************************************************
* Copyright 2011 See libgdx AUTHORS file.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
******************************************************************************/
class VelocityTracker {
int sampleSize = 10;
float lastX, lastY;
float deltaX, deltaY;
long lastTime;
int numSamples;
float[] meanX = new float[sampleSize];
float[] meanY = new float[sampleSize];
long[] meanTime = new long[sampleSize];
public void start (float x, float y, long timeStamp) {
lastX = x;
lastY = y;
deltaX = 0;
deltaY = 0;
numSamples = 0;
for (int i = 0; i < sampleSize; i++) {
meanX[i] = 0;
meanY[i] = 0;
meanTime[i] = 0;
}
lastTime = timeStamp;
}
public void update (float x, float y, long timeStamp) {
long currTime = timeStamp;
deltaX = x - lastX;
deltaY = y - lastY;
lastX = x;
lastY = y;
long deltaTime = currTime - lastTime;
lastTime = currTime;
int index = numSamples % sampleSize;
meanX[index] = deltaX;
meanY[index] = deltaY;
meanTime[index] = deltaTime;
numSamples++;
}
public float getVelocityX () {
float meanX = getAverage(this.meanX, numSamples);
float meanTime = getAverage(this.meanTime, numSamples) / 1000.0f;
if (meanTime == 0) return 0;
return meanX / meanTime;
}
public float getVelocityY () {
float meanY = getAverage(this.meanY, numSamples);
float meanTime = getAverage(this.meanTime, numSamples) / 1000.0f;
if (meanTime == 0) return 0;
return meanY / meanTime;
}
private float getAverage (float[] values, int numSamples) {
numSamples = Math.min(sampleSize, numSamples);
float sum = 0;
for (int i = 0; i < numSamples; i++) {
sum += values[i];
}
return sum / numSamples;
}
private long getAverage (long[] values, int numSamples) {
numSamples = Math.min(sampleSize, numSamples);
long sum = 0;
for (int i = 0; i < numSamples; i++) {
sum += values[i];
}
if (numSamples == 0) return 0;
return sum / numSamples;
}
private float getSum (float[] values, int numSamples) {
numSamples = Math.min(sampleSize, numSamples);
float sum = 0;
for (int i = 0; i < numSamples; i++) {
sum += values[i];
}
if (numSamples == 0) return 0;
return sum;
}
}
}

View File

@ -29,21 +29,14 @@ import org.oscim.layers.Layer;
import org.oscim.layers.overlay.Overlay.Snappable;
import org.oscim.renderer.RenderLayer;
public class LayerManager extends AbstractList<Layer>
//implements OnGestureListener,
//OnDoubleTapListener
{
public class LayerManager extends AbstractList<Layer> {
private final static String TAG = LayerManager.class.getName();
private final static boolean debugInput = false;
//private final GestureDetector mGestureDetector;
private final CopyOnWriteArrayList<Layer> mLayerList;
LayerManager() {
mLayerList = new CopyOnWriteArrayList<Layer>();
//mGestureDetector = new GestureDetector(context, this);
//mGestureDetector.setOnDoubleTapListener(this);
}
@Override
@ -109,7 +102,6 @@ public class LayerManager extends AbstractList<Layer>
}
}
Layer[] mLayers;
InputLayer[] mInputLayer;
@ -169,12 +161,12 @@ public class LayerManager extends AbstractList<Layer>
action == MotionEvent.ACTION_UP);
}
// if (handleGesture) {
// if (mGestureDetector.onTouchEvent(e))
// return true;
//
// mCancelGesture = false;
// }
// if (handleGesture) {
// if (mGestureDetector.onTouchEvent(e))
// return true;
//
// mCancelGesture = false;
// }
if (onTouchEvent(e))
return true;
@ -253,7 +245,6 @@ public class LayerManager extends AbstractList<Layer>
/* GestureDetector.OnDoubleTapListener */
//@Override
public boolean onDoubleTap(final MotionEvent e) {
if (mDirtyLayers)
@ -269,7 +260,6 @@ public class LayerManager extends AbstractList<Layer>
return false;
}
//@Override
public boolean onDoubleTapEvent(final MotionEvent e) {
if (mDirtyLayers)
updateLayers();
@ -284,7 +274,6 @@ public class LayerManager extends AbstractList<Layer>
return false;
}
//@Override
public boolean onSingleTapConfirmed(final MotionEvent e) {
if (mDirtyLayers)
updateLayers();
@ -300,8 +289,6 @@ public class LayerManager extends AbstractList<Layer>
}
/* OnGestureListener */
//@Override
public boolean onDown(final MotionEvent pEvent) {
if (mDirtyLayers)
updateLayers();
@ -316,23 +303,22 @@ public class LayerManager extends AbstractList<Layer>
return false;
}
//@Override
public boolean onFling(final MotionEvent pEvent1, final MotionEvent pEvent2,
final float pVelocityX, final float pVelocityY) {
if (mDirtyLayers)
updateLayers();
////@Override
//public boolean onFling(final MotionEvent pEvent1, final MotionEvent pEvent2,
// final float pVelocityX, final float pVelocityY) {
// if (mDirtyLayers)
// updateLayers();
//
// for (InputLayer o : mInputLayer) {
// if (o.onFling(pEvent1, pEvent2, pVelocityX, pVelocityY)) {
// if (debugInput)
// Log.d(TAG, "onFling\t" + o.getClass());
// return true;
// }
// }
// return false;
//}
for (InputLayer o : mInputLayer) {
if (o.onFling(pEvent1, pEvent2, pVelocityX, pVelocityY)) {
if (debugInput)
Log.d(TAG, "onFling\t" + o.getClass());
return true;
}
}
return false;
}
//@Override
public void onLongPress(final MotionEvent pEvent) {
if (mCancelGesture)
return;
@ -345,7 +331,6 @@ public class LayerManager extends AbstractList<Layer>
return;
}
//@Override
public boolean onScroll(final MotionEvent pEvent1, final MotionEvent pEvent2,
final float pDistanceX, final float pDistanceY) {
if (mDirtyLayers)
@ -361,7 +346,6 @@ public class LayerManager extends AbstractList<Layer>
return false;
}
//@Override
public void onShowPress(final MotionEvent pEvent) {
if (mDirtyLayers)
updateLayers();
@ -371,7 +355,6 @@ public class LayerManager extends AbstractList<Layer>
}
//@Override
public boolean onSingleTapUp(final MotionEvent pEvent) {
if (mDirtyLayers)
updateLayers();
@ -386,8 +369,6 @@ public class LayerManager extends AbstractList<Layer>
return false;
}
// /**
// * Gets the optional TilesLayer class.
// *