improve MapViewAnimation
This commit is contained in:
parent
064434896e
commit
555a951d25
@ -32,7 +32,7 @@ import android.os.Handler;
|
|||||||
import android.os.Message;
|
import android.os.Message;
|
||||||
import android.os.SystemClock;
|
import android.os.SystemClock;
|
||||||
import android.util.Log;
|
import android.util.Log;
|
||||||
import android.view.animation.DecelerateInterpolator;
|
import android.view.animation.AccelerateDecelerateInterpolator;
|
||||||
import android.view.animation.LinearInterpolator;
|
import android.view.animation.LinearInterpolator;
|
||||||
import android.widget.Scroller;
|
import android.widget.Scroller;
|
||||||
|
|
||||||
@ -158,7 +158,6 @@ public class MapViewPosition {
|
|||||||
&& pos.tilt == mTilt)
|
&& pos.tilt == mTilt)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
|
|
||||||
pos.lat = mLatitude;
|
pos.lat = mLatitude;
|
||||||
pos.lon = mLongitude;
|
pos.lon = mLongitude;
|
||||||
pos.angle = mRotation;
|
pos.angle = mRotation;
|
||||||
@ -166,7 +165,7 @@ public class MapViewPosition {
|
|||||||
|
|
||||||
// for tiling
|
// for tiling
|
||||||
pos.scale = scale;
|
pos.scale = scale;
|
||||||
pos.zoomLevel = (byte)z;
|
pos.zoomLevel = (byte) z;
|
||||||
|
|
||||||
pos.x = mAbsX * (Tile.TILE_SIZE << z);
|
pos.x = mAbsX * (Tile.TILE_SIZE << z);
|
||||||
pos.y = mAbsY * (Tile.TILE_SIZE << z);
|
pos.y = mAbsY * (Tile.TILE_SIZE << z);
|
||||||
@ -271,7 +270,7 @@ public class MapViewPosition {
|
|||||||
z = FastMath.clamp(z, MIN_ZOOMLEVEL, MAX_ZOOMLEVEL);
|
z = FastMath.clamp(z, MIN_ZOOMLEVEL, MAX_ZOOMLEVEL);
|
||||||
float scale = (float) (mAbsScale / (1 << z));
|
float scale = (float) (mAbsScale / (1 << z));
|
||||||
|
|
||||||
return new MapPosition(mLatitude, mLongitude, (byte)z, scale, mRotation);
|
return new MapPosition(mLatitude, mLongitude, (byte) z, scale, mRotation);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -672,7 +671,7 @@ public class MapViewPosition {
|
|||||||
private boolean mAnimMove;
|
private boolean mAnimMove;
|
||||||
private boolean mAnimFling;
|
private boolean mAnimFling;
|
||||||
private boolean mAnimScale;
|
private boolean mAnimScale;
|
||||||
private final DecelerateInterpolator mDecInterpolator = new DecelerateInterpolator(2);
|
private final AccelerateDecelerateInterpolator mDecInterpolator = new AccelerateDecelerateInterpolator();
|
||||||
|
|
||||||
public synchronized void animateTo(BoundingBox bbox) {
|
public synchronized void animateTo(BoundingBox bbox) {
|
||||||
double dx = MercatorProjection.longitudeToX(bbox.getMaxLongitude())
|
double dx = MercatorProjection.longitudeToX(bbox.getMaxLongitude())
|
||||||
@ -680,7 +679,6 @@ public class MapViewPosition {
|
|||||||
double dy = MercatorProjection.latitudeToY(bbox.getMinLatitude())
|
double dy = MercatorProjection.latitudeToY(bbox.getMinLatitude())
|
||||||
- MercatorProjection.latitudeToY(bbox.getMaxLatitude());
|
- MercatorProjection.latitudeToY(bbox.getMaxLatitude());
|
||||||
|
|
||||||
|
|
||||||
double z = Math.min(
|
double z = Math.min(
|
||||||
-LOG4 * Math.log(dx) + (mWidth / Tile.TILE_SIZE),
|
-LOG4 * Math.log(dx) + (mWidth / Tile.TILE_SIZE),
|
||||||
-LOG4 * Math.log(dy) + (mHeight / Tile.TILE_SIZE));
|
-LOG4 * Math.log(dy) + (mHeight / Tile.TILE_SIZE));
|
||||||
@ -716,43 +714,29 @@ public class MapViewPosition {
|
|||||||
mAnimFling = false;
|
mAnimFling = false;
|
||||||
mDuration = 500;
|
mDuration = 500;
|
||||||
|
|
||||||
// double mx = MercatorProjection.longitudeToPixelX(geoPoint.getLongitude(),
|
|
||||||
// (byte) ABS_ZOOMLEVEL);
|
|
||||||
// double my = MercatorProjection.latitudeToPixelY(geoPoint.getLatitude(),
|
|
||||||
// (byte) ABS_ZOOMLEVEL);
|
|
||||||
//
|
|
||||||
// double f = Tile.TILE_SIZE << ABS_ZOOMLEVEL;
|
|
||||||
// double x = mAbsX * f;
|
|
||||||
// double y = mAbsY * f;
|
|
||||||
//
|
|
||||||
// mScroller.startScroll((int) x, (int) y, (int) (mx - x), (int) (my - y), (int) mDuration);
|
|
||||||
// mFling = false;
|
|
||||||
|
|
||||||
mHandler.start((int) mDuration);
|
mHandler.start((int) mDuration);
|
||||||
}
|
}
|
||||||
|
|
||||||
public synchronized void animateTo(GeoPoint geoPoint) {
|
public synchronized void animateTo(GeoPoint geoPoint) {
|
||||||
|
|
||||||
double mx = MercatorProjection.longitudeToPixelX(geoPoint.getLongitude(),
|
|
||||||
(byte) ABS_ZOOMLEVEL);
|
|
||||||
double my = MercatorProjection.latitudeToPixelY(geoPoint.getLatitude(),
|
|
||||||
(byte) ABS_ZOOMLEVEL);
|
|
||||||
|
|
||||||
double f = Tile.TILE_SIZE << ABS_ZOOMLEVEL;
|
double f = Tile.TILE_SIZE << ABS_ZOOMLEVEL;
|
||||||
double x = mAbsX * f;
|
|
||||||
double y = mAbsY * f;
|
|
||||||
|
|
||||||
mScroller.startScroll((int) x, (int) y, (int) (mx - x), (int) (my - y), (int) mDuration);
|
mStartX = mAbsX * f;
|
||||||
|
mStartY = mAbsY * f;
|
||||||
|
|
||||||
mAnimFling = false;
|
mEndX = MercatorProjection.longitudeToX(geoPoint.getLongitude()) * f;
|
||||||
|
mEndY = MercatorProjection.latitudeToY(geoPoint.getLatitude()) * f;
|
||||||
|
|
||||||
|
mEndX -= mStartX;
|
||||||
|
mEndY -= mStartY;
|
||||||
|
|
||||||
|
mAnimMove = true;
|
||||||
mAnimScale = false;
|
mAnimScale = false;
|
||||||
mAnimMove = false;
|
mAnimFling = false;
|
||||||
|
|
||||||
mDuration = 300;
|
mDuration = 300;
|
||||||
mHandler.start((int) mDuration);
|
mHandler.start(mDuration);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public synchronized void animateFling(int velocityX, int velocityY,
|
public synchronized void animateFling(int velocityX, int velocityY,
|
||||||
int minX, int maxX, int minY, int maxY) {
|
int minX, int maxX, int minY, int maxY) {
|
||||||
|
|
||||||
@ -767,7 +751,7 @@ public class MapViewPosition {
|
|||||||
//mMapView.mGLView.setRenderMode(GLSurfaceView.RENDERMODE_CONTINUOUSLY);
|
//mMapView.mGLView.setRenderMode(GLSurfaceView.RENDERMODE_CONTINUOUSLY);
|
||||||
|
|
||||||
mDuration = 250;
|
mDuration = 250;
|
||||||
mHandler.start((int) mDuration);
|
mHandler.start(mDuration);
|
||||||
}
|
}
|
||||||
|
|
||||||
public synchronized void animateZoom(float scale) {
|
public synchronized void animateZoom(float scale) {
|
||||||
@ -777,7 +761,7 @@ public class MapViewPosition {
|
|||||||
//mMapView.mGLView.setRenderMode(GLSurfaceView.RENDERMODE_CONTINUOUSLY);
|
//mMapView.mGLView.setRenderMode(GLSurfaceView.RENDERMODE_CONTINUOUSLY);
|
||||||
|
|
||||||
mDuration = 300;
|
mDuration = 300;
|
||||||
mHandler.start((int) mDuration);
|
mHandler.start(mDuration);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void updateAnimation() {
|
public void updateAnimation() {
|
||||||
@ -793,49 +777,42 @@ public class MapViewPosition {
|
|||||||
double dx = mScroller.getCurrX();
|
double dx = mScroller.getCurrX();
|
||||||
double dy = mScroller.getCurrY();
|
double dy = mScroller.getCurrY();
|
||||||
|
|
||||||
if (mAnimFling) {
|
int mx = (int) (dx - mScrollX);
|
||||||
int mx = (int) (dx - mScrollX);
|
int my = (int) (dy - mScrollY);
|
||||||
int my = (int) (dy - mScrollY);
|
|
||||||
|
|
||||||
if (mx >= 1 || my >= 1 || mx <= -1 || my <= -1) {
|
if (mx >= 1 || my >= 1 || mx <= -1 || my <= -1) {
|
||||||
moveMap(mx, my);
|
moveMap(mx, my);
|
||||||
mScrollX = dx;
|
mScrollX = dx;
|
||||||
mScrollY = dy;
|
mScrollY = dy;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
else
|
|
||||||
moveAbs(dx, dy);
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
public synchronized void animateTo(float dx, float dy, float duration) {
|
|
||||||
applyRotation(dx, dy);
|
|
||||||
|
|
||||||
mDuration = duration;
|
|
||||||
mHandler.start((int) mDuration);
|
|
||||||
}
|
|
||||||
|
|
||||||
void onTick(long millisLeft) {
|
void onTick(long millisLeft) {
|
||||||
boolean changed = false;
|
boolean changed = false;
|
||||||
|
|
||||||
|
float adv = (1.0f - millisLeft / mDuration);
|
||||||
|
adv = mDecInterpolator.getInterpolation(adv);
|
||||||
|
|
||||||
if (mAnimScale) {
|
if (mAnimScale) {
|
||||||
float adv = (1.0f - millisLeft / mDuration);
|
if (mEndScale > 0)
|
||||||
adv = mDecInterpolator.getInterpolation(adv);
|
mAbsScale = mStartScale + (mEndScale * (Math.pow(2, adv) - 1));
|
||||||
|
else
|
||||||
//adv *= adv;
|
mAbsScale = mStartScale + (mEndScale * adv);
|
||||||
mAbsScale = mStartScale + (mEndScale * (Math.pow(2, adv)-1));
|
|
||||||
|
|
||||||
//div = mAbsScale / mStartScale;
|
|
||||||
|
|
||||||
if (mAnimMove)
|
|
||||||
moveAbs(mStartX + mEndX * adv, mStartY + mEndY * adv);
|
|
||||||
|
|
||||||
updatePosition();
|
|
||||||
|
|
||||||
changed = true;
|
changed = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (scroll())
|
if (mAnimMove) {
|
||||||
|
moveAbs(mStartX + mEndX * adv, mStartY + mEndY * adv);
|
||||||
|
changed = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (changed) {
|
||||||
|
updatePosition();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mAnimFling && scroll())
|
||||||
changed = true;
|
changed = true;
|
||||||
|
|
||||||
if (changed)
|
if (changed)
|
||||||
@ -843,13 +820,14 @@ public class MapViewPosition {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void onFinish() {
|
void onFinish() {
|
||||||
if (!mAnimFling && !mScroller.isFinished())
|
|
||||||
moveAbs(mScroller.getFinalX(), mScroller.getFinalY());
|
|
||||||
|
|
||||||
if (mStartScale != 0) {
|
if (mAnimMove) {
|
||||||
|
moveAbs(mStartX + mEndX, mStartY + mEndY);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mAnimScale) {
|
||||||
mAbsScale = mStartScale + mEndScale;
|
mAbsScale = mStartScale + mEndScale;
|
||||||
updatePosition();
|
updatePosition();
|
||||||
mStartScale = 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
//mMapView.mGLView.setRenderMode(GLSurfaceView.RENDERMODE_WHEN_DIRTY);
|
//mMapView.mGLView.setRenderMode(GLSurfaceView.RENDERMODE_WHEN_DIRTY);
|
||||||
@ -875,8 +853,8 @@ public class MapViewPosition {
|
|||||||
mMapViewPosition = new WeakReference<MapViewPosition>(mapAnimator);
|
mMapViewPosition = new WeakReference<MapViewPosition>(mapAnimator);
|
||||||
}
|
}
|
||||||
|
|
||||||
public synchronized final void start(int millis) {
|
public synchronized final void start(float millis) {
|
||||||
mMillisInFuture = millis;
|
mMillisInFuture = (int) millis;
|
||||||
MapViewPosition animator = mMapViewPosition.get();
|
MapViewPosition animator = mMapViewPosition.get();
|
||||||
if (animator == null)
|
if (animator == null)
|
||||||
return;
|
return;
|
||||||
|
|||||||
@ -354,16 +354,6 @@ final class TouchHandler implements OnGestureListener, OnDoubleTapListener {
|
|||||||
if (debug)
|
if (debug)
|
||||||
printState("onDown");
|
printState("onDown");
|
||||||
|
|
||||||
// if (fling) {
|
|
||||||
// mScroller.forceFinished(true);
|
|
||||||
//
|
|
||||||
// if (mTimer != null) {
|
|
||||||
// mTimer.cancel();
|
|
||||||
// mTimer = null;
|
|
||||||
// }
|
|
||||||
// fling = false;
|
|
||||||
// }
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -395,25 +385,22 @@ final class TouchHandler implements OnGestureListener, OnDoubleTapListener {
|
|||||||
int w = Tile.TILE_SIZE * 6;
|
int w = Tile.TILE_SIZE * 6;
|
||||||
int h = Tile.TILE_SIZE * 6;
|
int h = Tile.TILE_SIZE * 6;
|
||||||
|
|
||||||
if (mMapView.enablePagedFling) {
|
//if (mMapView.enablePagedFling) {
|
||||||
|
// double a = Math.sqrt(velocityX * velocityX + velocityY * velocityY);
|
||||||
|
//
|
||||||
|
// float vx = (float) (velocityX / a);
|
||||||
|
// float vy = (float) (velocityY / a);
|
||||||
|
//
|
||||||
|
// if (a < 400)
|
||||||
|
// return true;
|
||||||
|
//
|
||||||
|
// float move = Math.min(mMapView.getWidth(), mMapView.getHeight()) * 2 / 3;
|
||||||
|
// mMapPosition.animateTo(vx * move, vy * move, 250);
|
||||||
|
//} else {
|
||||||
|
float s = (300 / mMapView.dpi);
|
||||||
|
|
||||||
double a = Math.sqrt(velocityX * velocityX + velocityY * velocityY);
|
mMapPosition.animateFling(Math.round(velocityX * s), Math.round(velocityY * s), -w, w, -h,
|
||||||
|
h);
|
||||||
float vx = (float) (velocityX / a);
|
|
||||||
float vy = (float) (velocityY / a);
|
|
||||||
|
|
||||||
Log.d(TAG, "velocity: " + a + " " + velocityX + " " + velocityY + " - " + vx + " " + vy);
|
|
||||||
|
|
||||||
if (a < 400)
|
|
||||||
return true;
|
|
||||||
|
|
||||||
float move = Math.min(mMapView.getWidth(), mMapView.getHeight()) * 2 / 3;
|
|
||||||
mMapPosition.animateTo(vx * move, vy * move, 250);
|
|
||||||
} else {
|
|
||||||
float s = (300 / mMapView.dpi);
|
|
||||||
|
|
||||||
mMapPosition.animateFling(Math.round(velocityX * s), Math.round(velocityY * s), -w, w, -h, h);
|
|
||||||
}
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user