0

アンドロイドのタッチイベントで長方形を描く方法。キャンバスをタッチすると長方形が描画されますが、新しい場所をタッチすると古い長方形が削除され、新しい場所に新しい長方形が描画されます。しかし、私は触れた場所にすべての長方形を表示したままにしておきたいです。

public class TouchImageView extends ImageView {

    Matrix matrix = new Matrix();

    // We can be in one of these 3 states

    static final int NONE = 0;

    static final int DRAG = 1;

    static final int ZOOM = 2;

    boolean isCheckLoadImage = false;

    public static boolean isDraw = false;

    int mode = NONE;

    private float mPosX;

    private float mPosY;

    public static int numCell1 = 0;

    public static boolean CorrectTouch;

    float boxHeight, boxWidth;

    // Remember some things for zooming

    PointF last = new PointF();

    PointF start = new PointF();

    float minScale = 1f;

    float maxScale = 6f;

    int lastTouchEvent = -1;

    int selectedCell;

    float[] m;

    float scaleWidth, scaleHeight;

    float redundantXSpace, redundantYSpace;

    float width, height;

    static final int CLICK = 3;

    float saveScale = 1f;

    float right, bottom, origWidth, origHeight, bmWidth, bmHeight;

    ScaleGestureDetector mScaleDetector;

    Context context;

    boolean flag = false;


    public TouchImageView(Context context) {

        super(context);

        sharedConstructing(context);

    }

    public TouchImageView(Context context, AttributeSet attrs) {

        super(context, attrs);

        sharedConstructing(context);

    }

    @Override
    protected void onDraw(Canvas canvas) {

        super.onDraw(canvas);

        Paint paint = new Paint();

        paint.setColor(Color.RED);

        paint.setStyle(Paint.Style.STROKE);

        paint.setStrokeWidth(4);

        RectF r = new RectF();

        matrix.mapRect(r);

        boxWidth = scaleWidth / 5;

        boxHeight = scaleHeight / 5;

        float widthOfCell = boxWidth;

        float heightOfCell = boxHeight;

        float[] touchPoint = new float[] { mPosX, mPosY };

        float[] newTouch = new float[] { 0, 0 };

        matrix.mapPoints(newTouch, touchPoint);

        RectF canvasRect = new RectF();

        canvas.getMatrix().mapRect(canvasRect);

        Log.i("canvasRect", "canvasRect.left : " + canvasRect.left
                + " canvasRect.top : " + canvasRect.top);

        Log.i("r", "r.left : " + r.left + " r.top : " + r.top);

        Log.i("Pos", "mPosX : " + mPosX + " mPosY : " + mPosY);

        float newX = mPosX - (r.left);

        float newY = mPosY - (r.top);

        Log.i("new XY", "New X" + newX + " NewY " + newY);

        int myX = (int) (newX / boxWidth); /* Columns */

        int myY = (int) (newY / boxHeight);/* Rows */

        Log.i("my XY", "myX " + myX + " myY " + myY);

        //

        Log.e("GuessImageView", "before grid draw");

        try {

            if (true) {

                if (lastTouchEvent == MotionEvent.ACTION_UP) {

                    numCell1 = 0;

                    boolean doBreak = false;

                    for (float row = 0; !doBreak
                            && row <5; row++) {

                        float y = (row * heightOfCell) + r.top;

                        for (float col = 0; col < 5; col++) {

                            float x = (col * widthOfCell) + r.left;

                            if ((int) col == myX && (int) row == myY) {

                                canvas.drawRect(x, y, x + widthOfCell, y
                                        + heightOfCell, paint);

                                Log.d("Touch X : " + x, "Touch Y : " + y);

                                selectedCell = numCell1;

                                numCell1++;

                                flag = true;

                                doBreak = true;

                                break;

                            }

                            numCell1++;

                        }

                    }

                    if (flag) {

                        isCheckLoadImage = true;

//                      guessImage.checkForWin(selectedCell);

                    }

                    Log.i("Touch ", "Number Of Cell>" + numCell1);

                    lastTouchEvent = -1;

                }

            }

        } catch (ArithmeticException e) {

            e.printStackTrace();

        }

        Log.e("GuessImageView", "after grid draw");

    }

    private void sharedConstructing(Context context) {

        super.setClickable(true);

        this.context = context;

        mScaleDetector = new ScaleGestureDetector(context, new ScaleListener());

        matrix.setTranslate(1f, 1f);

        m = new float[9];

        setImageMatrix(matrix);

        setScaleType(ScaleType.MATRIX);

        setOnTouchListener(new OnTouchListener() {

            @Override
            public boolean onTouch(View v, MotionEvent event) {

                mScaleDetector.onTouchEvent(event);

                matrix.getValues(m);

                float x = m[Matrix.MTRANS_X];

                float y = m[Matrix.MTRANS_Y];

                PointF curr = new PointF(event.getX(), event.getY());

                switch (event.getAction()) {

                case MotionEvent.ACTION_DOWN:

                    last.set(event.getX(), event.getY());

                    start.set(last);

                    mode = DRAG;

                    // isDraw=false;

                    break;

                case MotionEvent.ACTION_MOVE:

                    // Log.i("onTouch", "origWidth : " + origWidth +

                    // " origHeight : " + origHeight);

                    if (mode == DRAG) {

                        // isDraw=false;

                        float deltaX = curr.x - last.x;

                        float deltaY = curr.y - last.y;

                        scaleWidth = Math.round(origWidth * saveScale);

                        scaleHeight = Math.round(origHeight * saveScale);

                        if (scaleWidth < width) {

                            deltaX = 0;

                            if (y + deltaY > 0)

                                deltaY = -y;

                            else if (y + deltaY < -bottom)

                                deltaY = -(y + bottom);

                        } else if (scaleHeight < height) {

                            deltaY = 0;

                            if (x + deltaX > 0)

                                deltaX = -x;

                            else if (x + deltaX < -right)

                                deltaX = -(x + right);

                        } else {

                            if (x + deltaX > 0)

                                deltaX = -x;

                            else if (x + deltaX < -right)

                                deltaX = -(x + right);

                            if (y + deltaY > 0)

                                deltaY = -y;

                            else if (y + deltaY < -bottom)

                                deltaY = -(y + bottom);

                        }

                        matrix.postTranslate(deltaX, deltaY);

                        last.set(curr.x, curr.y);

                    }

                    break;

                case MotionEvent.ACTION_UP: {

                    mode = NONE;

                    int xDiff = (int) Math.abs(curr.x - start.x);

                    int yDiff = (int) Math.abs(curr.y - start.y);

                    if (xDiff < CLICK && yDiff < CLICK) {

                        // isDraw=false;

                        Log.v("ACTION_UP", "ACTION_UP");

                        mPosX = curr.x;

                        mPosY = curr.y;

                        performClick();

//                      if (guessImage.guess_mode) {

                            lastTouchEvent = event.getAction();
                        /*}

                        else {

                            lastTouchEvent = -1;

                        }
*/
                        // invalidate();

                    }

                    break;

                }

                case MotionEvent.ACTION_POINTER_UP:

                    mode = NONE;

                    break;

                }

                setImageMatrix(matrix);

                scaleWidth = Math.round(origWidth * saveScale);

                scaleHeight = Math.round(origHeight * saveScale);

                invalidate();

                return true; // indicate event was handled

            }

        });

    }

    @Override
    public void setImageBitmap(Bitmap bm) {

        super.setImageBitmap(bm);

        if (bm != null) {

            bmWidth = bm.getWidth();

            bmHeight = bm.getHeight();

        }

    }

    public void setMaxZoom(float x) {

        maxScale = x;

    }

    private class ScaleListener extends
            ScaleGestureDetector.SimpleOnScaleGestureListener {

        @Override
        public boolean onScaleBegin(ScaleGestureDetector detector) {

            mode = ZOOM;

            return true;

        }

        @Override
        public boolean onScale(ScaleGestureDetector detector) {

            float mScaleFactor = detector.getScaleFactor();

            float origScale = saveScale;

            saveScale *= mScaleFactor;

            if (saveScale > maxScale) {

                saveScale = maxScale;

                mScaleFactor = maxScale / origScale;

            } else if (saveScale < minScale) {

                saveScale = minScale;

                mScaleFactor = minScale / origScale;

            }

            right = width * saveScale - width
                    - (2 * redundantXSpace * saveScale);

            bottom = height * saveScale - height
                    - (2 * redundantYSpace * saveScale);

            // mPosX = mPosX + right / saveScale;

            // mPosY = mPosY + bottom / saveScale;

            if (origWidth * saveScale <= width
                    || origHeight * saveScale <= height) {

                float xMove = 0, yMove = 0;

                matrix.postScale(mScaleFactor, mScaleFactor, width / 2,
                        height / 2);

                if (mScaleFactor < 1) {

                    matrix.getValues(m);

                    float x = m[Matrix.MTRANS_X];

                    float y = m[Matrix.MTRANS_Y];

                    if (mScaleFactor < 1) {

                        if (Math.round(origWidth * saveScale) < width) {

                            if (y < -bottom) {

                                matrix.postTranslate(0, -(y + bottom));

                                xMove = 0;

                                yMove = -(y + bottom);

                            } else if (y > 0) {

                                matrix.postTranslate(0, -y);

                                xMove = 0;

                                yMove = -y;

                            }

                        } else {

                            if (x < -right) {

                                matrix.postTranslate(-(x + right), 0);

                                xMove = -(x + right);

                                yMove = 0;

                            } else if (x > 0) {

                                matrix.postTranslate(-x, 0);

                                xMove = -(x + right);

                                yMove = 0;

                            }

                        }

                        Log.i("onScale", "mPosX " + mPosX + " mPosX " + mPosX);

                    }

                }

            } else {

                float xMove = 0, yMove = 0;

                matrix.postScale(mScaleFactor, mScaleFactor,
                        detector.getFocusX(), detector.getFocusY());

                matrix.getValues(m);

                float x = m[Matrix.MTRANS_X];

                float y = m[Matrix.MTRANS_Y];

                if (mScaleFactor < 1) {

                    if (x < -right) {

                        matrix.postTranslate(-(x + right), 0);

                        xMove = -(x + right);

                        yMove = 0;

                    } else if (x > 0) {

                        matrix.postTranslate(-x, 0);

                        xMove = -x;

                        yMove = 0;

                    }

                    if (y < -bottom) {

                        matrix.postTranslate(0, -(y + bottom));

                        xMove = 0;

                        yMove = -(y + bottom);

                    } else if (y > 0) {

                        matrix.postTranslate(0, -y);

                        xMove = 0;

                        yMove = -y;

                    }

                }

                Log.i("onScale", "mPosX " + mPosX + " mPosX " + mPosX);

            }

            return true;

        }

    }

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {

        if (!isCheckLoadImage) {

            width = MeasureSpec.getSize(widthMeasureSpec);

            height = MeasureSpec.getSize(heightMeasureSpec);

            // Fit to screen.

            float scale;

            float scaleX = (float) width / (float) bmWidth;

            float scaleY = (float) height / (float) bmHeight;

            scale = Math.min(scaleX, scaleY);

            matrix.setScale(scale, scale);

            setImageMatrix(matrix);

            saveScale = 1f;

            // Center the image

            redundantYSpace = (float) height - (scale * (float) bmHeight);

            redundantXSpace = (float) width - (scale * (float) bmWidth);

            redundantYSpace /= (float) 2;

            redundantXSpace /= (float) 2;

            matrix.postTranslate(redundantXSpace, redundantYSpace);

            origWidth = width - 2 * redundantXSpace;

            origHeight = height - 2 * redundantYSpace;

            right = width * saveScale - width
                    - (2 * redundantXSpace * saveScale);

            bottom = height * saveScale - height
                    - (2 * redundantYSpace * saveScale);

            setImageMatrix(matrix);

        }

        super.onMeasure(widthMeasureSpec, heightMeasureSpec);

    }

}
4

2 に答える 2

1

すべてのタッチ位置をメモリに保存し、毎回再描画する必要があります。

このサンプルのように:Androidが画面上にオブジェクトを描画し、ジオメトリデータを取得する

于 2012-11-12T10:37:34.367 に答える
0

これはカード上の私のコードのセクションです。その上に長方形を描画し、長方形のクリックイベントを聞く必要がありました。カードはいくつかのカウントタスク用であり、クライアントは何らかの理由でビュー全体にタッチを拡張することを望んでいました...

 alertCard.setOnTouchListener((v, event) -> {

        Rect outRect = new Rect();
        alertCard.getGlobalVisibleRect(outRect);

        // calculate new bottom, to be used for upper part.
        int bottom = (int) (outRect.bottom * 0.95);

        Rect upperRec = new Rect(outRect.left, outRect.top,outRect.right, bottom);

        int value = part.getMistakes().get(0).getValue();

        if (upperRec.contains( (int) event.getRawX(),(int) event.getRawY()))
        {
           //Implement the touch event...

        }

        return false;
    });
于 2020-07-07T07:41:38.733 に答える