Android Round Corner ImageView
Making round corners on the image by using a mask Put an ImageView and a mask view in a RelativeLayout. Make the mask view round corners and put it on top of the ImageView.
The layout:
The drawable round_corners_mask.xml
Apply round corner image transformation when loading the image through Picasso.
The round corner transformation class. RoundCornersTransformation.java
import android.graphics.Bitmap; import android.graphics.Bitmap.Config; import android.graphics.BitmapShader; import android.graphics.Canvas; import android.graphics.Paint; import android.graphics.Path; import android.graphics.RectF; import android.graphics.Shader; // enables hardware accelerated rounded corners // original idea here : http://www.curious-creature.org/2012/12/11/android-recipe-1-image-with-rounded-corners/ // https://gist.github.com/aprock/6213395 // https://gist.github.com/amardeshbd/06b491d4adb568b1b226a20d4953a180 public class RoundCornersTransformation implements com.squareup.picasso.Transformation { private final int radius; // dp private final int margin; // dp private String KEY = ""; private boolean topCorners = true; private boolean bottomCorners = true; /** * Creates rounded transformation for all corners. * * @param radius radius is corner radii in dp * @param margin margin is the board in dp */ public RoundCornersTransformation(final int radius, final int margin) { this.radius = radius; this.margin = margin; if (KEY.isEmpty()) KEY = "rounded_" + radius + margin; } /** * Creates rounded transformation for top or bottom corners. * * @param radius radius is corner radii in dp * @param margin margin is the board in dp * @param topCornersOnly Rounded corner for top corners only. * @param bottomCornersOnly Rounded corner for bottom corners only. */ public RoundCornersTransformation(final int radius, final int margin, boolean topCornersOnly, boolean bottomCornersOnly) { this(radius, margin); topCorners = topCornersOnly; bottomCorners = bottomCornersOnly; KEY = "rounded_" + radius + margin + topCorners + bottomCorners; } @Override public Bitmap transform(final Bitmap source) { final Paint paint = new Paint(); paint.setAntiAlias(true); paint.setShader(new BitmapShader(source, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP)); Bitmap output = Bitmap.createBitmap(source.getWidth(), source.getHeight(), Config.ARGB_8888); Canvas canvas = new Canvas(output); if(topCorners && bottomCorners) { // Uses native method to draw symmetric rounded corners canvas.drawRoundRect(new RectF(margin, margin, source.getWidth() - margin, source.getHeight() - margin), radius, radius, paint); } else { // Uses custom path to generate rounded corner individually canvas.drawPath(RoundedRect(margin, margin, source.getWidth() - margin, source.getHeight() - margin, radius, radius, topCorners, topCorners, bottomCorners, bottomCorners), paint); } if (source != output) { source.recycle(); } return output; } @Override public String key() { return "rounded_" + radius + margin; // return KEY; } /** * Prepares a path for rounded corner selectively. * Source taken from http://stackoverflow.com/a/35668889/6635889 * @param leftX The X coordinate of the left side of the rectangle * @param topY The Y coordinate of the top of the rectangle * @param rightX The X coordinate of the right side of the rectangle * @param bottomY The Y coordinate of the bottom of the rectangle * @param rx The x-radius of the oval used to round the corners * @param ry The y-radius of the oval used to round the corners * @param topLeft * @param topRight * @param bottomRight * @param bottomLeft * @return */ public static Path RoundedRect(float leftX, float topY, float rightX, float bottomY, float rx, float ry, boolean topLeft, boolean topRight, boolean bottomRight, boolean bottomLeft) { Path path = new Path(); if (rx < 0) rx = 0; if (ry < 0) ry = 0; float width = rightX - leftX; float height = bottomY - topY; if (rx > width / 2) rx = width / 2; if (ry > height / 2) ry = height / 2; float widthMinusCorners = (width - (2 * rx)); float heightMinusCorners = (height - (2 * ry)); path.moveTo(rightX, topY + ry); if (topRight) path.rQuadTo(0, -ry, -rx, -ry);//top-right corner else{ path.rLineTo(0, -ry); path.rLineTo(-rx,0); } path.rLineTo(-widthMinusCorners, 0); if (topLeft) path.rQuadTo(-rx, 0, -rx, ry); //top-left corner else{ path.rLineTo(-rx, 0); path.rLineTo(0,ry); } path.rLineTo(0, heightMinusCorners); if (bottomLeft) path.rQuadTo(0, ry, rx, ry);//bottom-left corner else{ path.rLineTo(0, ry); path.rLineTo(rx,0); } path.rLineTo(widthMinusCorners, 0); if (bottomRight) path.rQuadTo(rx, 0, rx, -ry); //bottom-right corner else{ path.rLineTo(rx,0); path.rLineTo(0, -ry); } path.rLineTo(0, -heightMinusCorners); path.close();//Given close, last lineto can be removed. return path; } }
Using the transformation with Picasso.
Picasso.with(this) .load("http://www.gettyimages.ca/gi-resources/images/Homepage/Hero/UK/CMS_Creative_164657191_Kingfisher.jpg") .transform(new RoundCornersTransformation(20, 20, true, true)) .into(anImageView);
Making round corners by overriding the onDraw method of the ImageView. RoundCornersImageView.java
import android.annotation.TargetApi; import android.content.Context; import android.graphics.Canvas; import android.graphics.Path; import android.graphics.RectF; import android.os.Build; import android.util.AttributeSet; import android.widget.ImageView; public class RoundCornersImageView extends ImageView { public RoundCornersImageView(Context context) { super(context); } public RoundCornersImageView(Context context, AttributeSet attrs) { super(context, attrs); } public RoundCornersImageView(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); } @TargetApi(Build.VERSION_CODES.LOLLIPOP) public RoundCornersImageView(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) { super(context, attrs, defStyleAttr, defStyleRes); } @Override protected void onLayout(boolean changed, int left, int top, int right, int bottom) { super.onLayout(changed, left, top, right, bottom); } @Override protected boolean setFrame(int l, int t, int r, int b) { return super.setFrame(l, t, r, b); } @Override protected void onDraw(Canvas canvas) { float radius = getContext().getResources().getDimension(R.dimen.round_corner_radius); Path path = new Path(); RectF rect = new RectF(0, 0, this.getWidth(), this.getHeight()); path.addRoundRect(rect, radius, radius, Path.Direction.CW); canvas.clipPath(path); super.onDraw(canvas); } }
Use it like this:
Making a custom ImageView with options to choose the corners to be rounded.
attrs.xml
RoundishImageView.java
import android.content.Context; import android.content.res.TypedArray; import android.graphics.Canvas; import android.graphics.Path; import android.graphics.RectF; import android.util.AttributeSet; import android.util.Log; import android.widget.ImageView; public class RoundishImageView extends ImageView { public static final int CORNER_NONE = 0; public static final int CORNER_TOP_LEFT = 1; public static final int CORNER_TOP_RIGHT = 2; public static final int CORNER_BOTTOM_RIGHT = 4; public static final int CORNER_BOTTOM_LEFT = 8; public static final int CORNER_ALL = 15; private final RectF cornerRect = new RectF(); private final Path path = new Path(); private int cornerRadius; private int roundedCorners; public RoundishImageView(Context context) { this(context, null); } public RoundishImageView(Context context, AttributeSet attrs) { this(context, attrs, 0); } public RoundishImageView(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.RoundishImageView); cornerRadius = a.getDimensionPixelSize(R.styleable.RoundishImageView_cornerRadius, 0); roundedCorners = a.getInt(R.styleable.RoundishImageView_roundedCorners, CORNER_NONE); a.recycle(); } public void setCornerRadius(int radius) { cornerRadius = radius; setPath(); invalidate(); } public int getRadius() { return cornerRadius; } public void setRoundedCorners(int corners) { roundedCorners = corners; setPath(); invalidate(); } public int getRoundedCorners() { return roundedCorners; } @Override protected void onSizeChanged(int w, int h, int oldw, int oldh) { super.onSizeChanged(w, h, oldw, oldh); setPath(); } @Override protected void onDraw(Canvas canvas) { if (!path.isEmpty()) { canvas.clipPath(path); } super.onDraw(canvas); } private void setPath() { path.rewind(); if (cornerRadius >= 1f && roundedCorners != CORNER_NONE) { final int width = getWidth(); final int height = getHeight(); final float twoRadius = cornerRadius * 2; cornerRect.set(-cornerRadius, -cornerRadius, cornerRadius, cornerRadius); if (isRounded(CORNER_TOP_LEFT)) { cornerRect.offsetTo(0f, 0f); path.arcTo(cornerRect, 180f, 90f); } else { path.moveTo(0f, 0f); } if (isRounded(CORNER_TOP_RIGHT)) { cornerRect.offsetTo(width - twoRadius, 0f); path.arcTo(cornerRect, 270f, 90f); } else { path.lineTo(width, 0f); } if (isRounded(CORNER_BOTTOM_RIGHT)) { cornerRect.offsetTo(width - twoRadius, height - twoRadius); path.arcTo(cornerRect, 0f, 90f); } else { path.lineTo(width, height); } if (isRounded(CORNER_BOTTOM_LEFT)) { cornerRect.offsetTo(0f, height - twoRadius); path.arcTo(cornerRect, 90f, 90f); } else { path.lineTo(0f, height); } path.close(); } } private boolean isRounded(int corner) { return (roundedCorners & corner) == corner; } }
Use it like this:
Search within Codexpedia
Custom Search
Search the entire web
Custom Search
Related Posts