Jawascript
Jawascript

Reputation: 703

Dynamically Resizable Grid With Handles Android

I have a grid I'm drawing onto a Canvas with 4 handles at each corner. When I drag a handle in any direction I need to re-size the cells inside my grid. Right now the cells are drawn, and they resize but they draw relative to the top left handle and end up going all over my screen. They never stay inside the box I draw on my canvas. Furthermore they scale, but they do not scale perspective, only size.

Here is what I have so far

private void drawGrid() {
    Path path = new Path();
    int gridSize = 5;
    float gridCellSize = 40;
    float topLeftX = 0;
    float topLeftY = 0;
    float topRightX = 0;
    float topRightY = 0;
    float bottomRightX = 0;
    float bottomRightY = 0;
    float bottomLeftX = 0;
    float bottomLeftY = 0;

    for (int i = 0; i < mHandles.size(); i++) {
        Circle c = mHandles.get(i);
        int index = mHandles.indexOf(c);
        switch (index) {
        case 0:
            path.moveTo(c.getX(), c.getY());
            topLeftX = c.getX();
            topLeftY = c.getY();
            break;
        case 1:
            path.lineTo(c.getX(), c.getY());
            topRightX = c.getX();
            topRightY = c.getY();
            break;
        case 2:
            path.lineTo(c.getX(), c.getY());
            bottomRightX = c.getX();
            bottomRightY = c.getY();
            break;
        case 3:
            path.lineTo(c.getX(), c.getY());
            bottomLeftX = c.getX();
            bottomLeftY = c.getY();
            break;
        }
    }

    path.close();

    float topXWidth = (topLeftX - topRightX);
    float leftXHeight = (topLeftX - bottomLeftX);
    gridCellSize = (float) (topXWidth / gridSize) * (leftXHeight / gridSize);

    mPaint.setColor(Color.YELLOW);
    mPaint.setAlpha(TRANSPARENCY);

    for (int i = 0; i < gridSize; i++) {
        for (int j = 0; j < gridSize; j++) {
            int left = (int) (topLeftX + (i * (gridCellSize + 2)));
            int top = (int) (topLeftY + (j * (gridCellSize + 2)));
            int right = (int) (left + gridCellSize);
            int bottom = (int) (top + gridCellSize);
            mCanvas.drawRect(new Rect(left, top, right, bottom), mPaint);
        }
    }

    mCanvas.drawPath(path, mPaint);
    mCanvas.drawPath(path, mStrokePaint);

    mCirclePaint.setColor(Color.YELLOW);
    for (Circle c : mCircleList) {
        mCanvas.drawCircle(c.getX(), c.getY(), RADIUS, mCirclePaint);
        mCanvas.drawCircle(c.getX(), c.getY(), RADIUS, mCircleStrokePaint);
    }

    mImageView.invalidate();
}

After this method is run a box is drawn with perfectly sized boxes 5x5 across my grid, however if I move my handle my boxes are being drawn with no reference to the container. The result is this

        

As you can see, the boxes that are supposed to be inside my grid are actually all over the place. I need it to stretch and adjust like this

Any and all help is appreciated, if you need any clarification please let me know!

Upvotes: 3

Views: 565

Answers (1)

M-Wajeeh
M-Wajeeh

Reputation: 17304

This will get you started:

enter image description here

The code:

import android.annotation.TargetApi;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Matrix;
import android.graphics.Paint;
import android.os.Build;
import android.util.AttributeSet;
import android.view.View;

/**
 * Created by Muhammad Wajeeh on 01-Dec-14.
 */
public class PolyGrid extends View {
    private Paint mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
    private Matrix mMatrix = new Matrix();

    public PolyGrid(Context context) {
        super(context);
    }

    public PolyGrid(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    public PolyGrid(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
    }

    @TargetApi(Build.VERSION_CODES.LOLLIPOP)
    public PolyGrid(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
        super(context, attrs, defStyleAttr, defStyleRes);
    }

    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        canvas.save();
        final int w = getMeasuredWidth();
        final int h = getMeasuredHeight();

        float[] src = {0, 0, w, 0, w, h, 0, h};
        float[] dst = {0, 0, 2*w/3F, h/3F, 2*w/3F, 2*h/3F, 0, h};
        mMatrix.setPolyToPoly(src, 0, dst, 0, src.length >> 1);// magic happens here
        canvas.concat(mMatrix);

        mPaint.setColor(Color.GRAY);
        mPaint.setStrokeWidth(20);
        mPaint.setStyle(Paint.Style.STROKE);

        final float gridSizeH = w / 4F;
        final float gridSizeV = h / 4F;
        for (int i = 0; i <= 4; i++) {
            // draw horizontal and vertical lines normally
            float y = i * gridSizeV;
            float x = i * gridSizeH;
            canvas.drawLine(0, y, w, y, mPaint);
            canvas.drawLine(x, 0, x, h, mPaint);
        }
        canvas.restore();
    }
}

Upvotes: 2

Related Questions