Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Denote progress by border Android

I need to denote progress by the border of view. E.g. Initially view will not have any border at all, when 50% progress is reached, only 50% of view will get border.Find the attached image. I did lot of googling but no luck.The view I used is textview.

enter image description here

Edited

The following code, cuts the edges of bitmap. What I've done in this code is - 1. Bg is set to Black Hexagon 2. And I've taken hollow green bordered hexagon & revealing this hollow hexagon, so that it will look like border is getting accumulated.

public class MyView extends View {

private Bitmap mBitmap;
private Paint mPaint;
private RectF mOval;
private float mAngle = 135;
private Paint mTextPaint;
private Bitmap bgBitmap;

public MyView(Context context) {
    super(context);
    doInit();
}


/**
 * @param context
 * @param attrs
 * @param defStyleAttr
 */
public MyView(Context context, AttributeSet attrs, int defStyleAttr) {
    super(context, attrs, defStyleAttr);
    // TODO Auto-generated constructor stub
    doInit();
}


/**
 * @param context
 * @param attrs
 */
public MyView(Context context, AttributeSet attrs) {
    super(context, attrs);
    // TODO Auto-generated constructor stub
    doInit();
}

private void doInit() {
    // use your bitmap insted of R.drawable.ic_launcher
    mBitmap = BitmapFactory.decodeResource(getResources(), R.drawable.hexagon_border);
    bgBitmap = BitmapFactory.decodeResource(getResources(), R.drawable.view_message_small_hexagon);
    mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
    mOval = new RectF();
    mTextPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
    mTextPaint.setTextSize(48);
    mTextPaint.setTextAlign(Align.CENTER);
    mTextPaint.setColor(0xffffaa00);
    mTextPaint.setTypeface(Typeface.DEFAULT_BOLD);
}

@Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
    Matrix m = new Matrix();
    RectF src = new RectF(0, 0, mBitmap.getWidth(), mBitmap.getHeight());
    RectF dst = new RectF(0, 0, w, h);
    m.setRectToRect(src, dst, ScaleToFit.CENTER);
    Shader shader = new BitmapShader(mBitmap, TileMode.CLAMP, TileMode.CLAMP);
    shader.setLocalMatrix(m);
    mPaint.setShader(shader);
    m.mapRect(mOval, src);
}

@Override
protected void onDraw(Canvas canvas) {
    //canvas.drawColor(0xff0000aa);
    Matrix matrix = new Matrix();
    canvas.drawBitmap(bgBitmap, matrix, null);
    canvas.drawArc(mOval, -90, mAngle, true, mPaint);
}

@Override
public boolean onTouchEvent(MotionEvent event) {
    float w2 = getWidth() / 2f;
    float h2 = getHeight() / 2f;
    mAngle = (float) Math.toDegrees(Math.atan2(event.getY() - h2, event.getX() - w2));
    mAngle += 90 + 360;
    mAngle %= 360;
    invalidate();
    return true;
}

}

like image 859
Vishal Pawale Avatar asked Jan 13 '14 19:01

Vishal Pawale


2 Answers

try this SO answer:

public class MyView extends View {

    private Bitmap mBitmap;
    private Paint mPaint;
    private RectF mOval;
    private float mAngle = 135;
    private Paint mTextPaint;

    public MyView(Context context) {
        super(context);
        // use your bitmap insted of R.drawable.ic_launcher
        mBitmap = BitmapFactory.decodeResource(getResources(), R.drawable.ic_launcher);
        mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
        mOval = new RectF();
        mTextPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
        mTextPaint.setTextSize(48);
        mTextPaint.setTextAlign(Align.CENTER);
        mTextPaint.setColor(0xffffaa00);
        mTextPaint.setTypeface(Typeface.DEFAULT_BOLD);
    }

    @Override
    protected void onSizeChanged(int w, int h, int oldw, int oldh) {
        Matrix m = new Matrix();
        RectF src = new RectF(0, 0, mBitmap.getWidth(), mBitmap.getHeight());
        RectF dst = new RectF(0, 0, w, h);
        m.setRectToRect(src, dst, ScaleToFit.CENTER);
        Shader shader = new BitmapShader(mBitmap, TileMode.CLAMP, TileMode.CLAMP);
        shader.setLocalMatrix(m);
        mPaint.setShader(shader);
        m.mapRect(mOval, src);
    }

    @Override
    protected void onDraw(Canvas canvas) {
        canvas.drawColor(0xff0000aa);
        canvas.drawArc(mOval, -90, mAngle, true, mPaint);
        canvas.drawText("click me", getWidth() / 2, getHeight() / 2, mTextPaint);
    }

    @Override
    public boolean onTouchEvent(MotionEvent event) {
        float w2 = getWidth() / 2f;
        float h2 = getHeight() / 2f;
        mAngle = (float) Math.toDegrees(Math.atan2(event.getY() - h2, event.getX() - w2));
        mAngle += 90 + 360;
        mAngle %= 360;
        invalidate();
        return true;
    }
}
like image 131
Dheeraj Bhaskar Avatar answered Oct 13 '22 12:10

Dheeraj Bhaskar


Getting a good circular progress spinner is difficult in itself. The ProgressWheel is a good custom View that does this. You should be able to modify the ProgressWheel's onDraw() class to do something very similar to what you want.

like image 32
Brian Attwell Avatar answered Oct 13 '22 12:10

Brian Attwell