我尝试了什么:
我在onDraw(Canvas canvas)
中绘制了指定边界的shapeDrawables。
添加Handle Input Gestures,允许视图在任何方向滚动,如此SO post.
中提到的2d滚动视图问题:
当我滚动按onScroll()
GestureDetector shapeDrawable' 绑定更改时的视图!是否有任何方法可以在滚动时更改/更新已显示的shapeDrawable边界?
我已经实现了onTouchEvent(MotionEvent event)
,如果单击画布/视图上显示的Shape drawable,如果单击的x,y包含shapesrawable的边界,则删除drawable。当视图没有滚动时,这个东西工作正常,如果滚动视图绑定无法检测shaperawable因为绑定和x,y参数的变化。
代码:
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Rect;
import android.graphics.drawable.ShapeDrawable;
import android.graphics.drawable.shapes.OvalShape;
import android.graphics.drawable.shapes.RectShape;
import android.graphics.drawable.shapes.Shape;
import android.os.Build;
import android.util.AttributeSet;
import android.view.GestureDetector;
import android.view.MotionEvent;
import android.view.View;
import android.widget.Scroller;
import java.util.*;
public class ShapeDrawableView extends View {
private List<ShapeDrawable> shapes = new ArrayList<ShapeDrawable>();
private Integer[] mColors = { Color.BLACK, Color.BLUE, Color.GREEN,
Color.RED };
// If made programmatically and added with setContentView
public ShapeDrawableView(Context context) {
super(context);
}
private Scroller mScroller;
private GestureDetector mDetector;
public ShapeDrawableView(Context context, AttributeSet attrs) {
super(context, attrs);
mDetector = new GestureDetector(ShapeDrawableView.this.getContext(),
new GestureListener());
if (Build.VERSION.SDK_INT < 11) {
mScroller = new Scroller(getContext());
} else {
mScroller = new Scroller(getContext(), null, true);
}
}
@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
for (ShapeDrawable shape : shapes) {
shape.draw(canvas);
}
}
@Override
public boolean onTouchEvent(MotionEvent event) {
mDetector.onTouchEvent(event);
if (event.getAction() == MotionEvent.ACTION_DOWN) {
int x = (int) event.getX(); // Use getX(int) for multi-finger
// gestures
int y = (int) event.getY();
if (!isDeletingExistingShape(x, y)) {
shapes.add(makeShapeDrawable(x, y));
}
invalidate();
return (true); // Handled touch event
} else {
return (false); // Did not handle touch event
}
}
private boolean isDeletingExistingShape(int x, int y) {
for (ShapeDrawable shape : shapes) {
Rect bounds = shape.getBounds();
if (bounds.contains(x, y)) {
shapes.remove(shape);
return (true);
}
}
return (false);
}
private ShapeDrawable makeShapeDrawable(int x, int y) {
int maxWidth = getWidth() / 10;
int maxHeight = getHeight() / 10;
Shape shape;
if (Math.random() < 0.5) {
shape = new OvalShape();
} else {
shape = new RectShape();
}
ShapeDrawable shapeD = new ShapeDrawable(shape);
int width = RandomUtils.randomInt(maxWidth) + 5;
int height = RandomUtils.randomInt(maxHeight) + 5;
shapeD.setBounds(x - width / 2, y - height / 2, x + width / 2, y
+ height / 2);
shapeD.getPaint().setColor(RandomUtils.randomElement(mColors));
return (shapeD);
}
private class GestureListener extends
GestureDetector.SimpleOnGestureListener {
@Override
public boolean onScroll(MotionEvent e1, MotionEvent e2,
float distanceX, float distanceY) {
// Set the pie rotation directly.
// float scrollTheta = vectorToScalarScroll(
// distanceX,
// distanceY,
// e2.getX() - mPieBounds.centerX(),
// e2.getY() - mPieBounds.centerY());
// setPieRotation(getPieRotation() - (int) scrollTheta /
// FLING_VELOCITY_DOWNSCALE);
scrollBy((int) distanceX, (int) distanceY);
return true;
}
@Override
public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
float velocityY) {
// Set up the Scroller for a fling
/*
* float scrollTheta = vectorToScalarScroll( velocityX, velocityY,
* e2.getX() - mPieBounds.centerX(), e2.getY() -
* mPieBounds.centerY()); mScroller.fling( 0, (int)
* getPieRotation(), 0, (int) scrollTheta /
* FLING_VELOCITY_DOWNSCALE, 0, 0, Integer.MIN_VALUE,
* Integer.MAX_VALUE);
*
* // Start the animator and tell it to animate for the expected
* duration of the fling. if (Build.VERSION.SDK_INT >= 11) {
* mScrollAnimator.setDuration(mScroller.getDuration());
* mScrollAnimator.start(); }
*/
mScroller.fling(getScrollX(), getScrollY(), -(int) velocityX,
-(int) velocityY, 0, (int) 100, 0, (int) 100);
invalidate(); // don't remember if it's needed
return true;
// return true;
}
@Override
public boolean onDown(MotionEvent e) {
// The user is interacting with the pie, so we want to turn on
// acceleration
// so that the interaction is smooth.
/*
* mPieView.accelerate(); if (isAnimationRunning()) {
* stopScrolling(); }
*/
if (!mScroller.isFinished()) { // is flinging
mScroller.forceFinished(true); // to stop flinging on touch
}
return true; // else won't work
// return true;
}
}
}
答案 0 :(得分:1)
只需在onTouchEvent中更新x和y:
x += getScrollX();
y += getScrollY();