Mask ImageView with round corner background
Solution 1
I suggest you to use another method:
One FrameLayout
and two ImageView
can do it.
<FrameLayout>
<ImageView /> your image
<ImageView /> put a image which has a transparent circle in it
</FrameLayout>
then your image can been seen via transparent circle.
Solution 2
The best way is to do it in Canvas
using PorterDuff
operations and/or Shaders
. Let's say your Bitmap
is available and stored in mBitmap
.
Option 1: Using Shaders.
@Override
public void onDraw(Canvas canvas) {
super.onDraw(canvas);
// Load the bitmap as a shader to the paint.
final Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
final Shader shader = new BitmapShader(mBitmap, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);
paint.setShader(shader);
// Draw a circle with the required radius.
final float halfWidth = canvas.getWidth()/2;
final float halfHeight = canvas.getHeight()/2;
final float radius = Math.max(halfWidth, halfHeight);
canvas.drawCircle(halfWidth, halfHeight, radius, paint);
}
Option 2: Using PorterDuff mode.
@Override
public void onDraw(Canvas canvas) {
super.onDraw(canvas);
// Create a circular path.
final float halfWidth = canvas.getWidth()/2;
final float halfHeight = canvas.getHeight()/2;
final float radius = Math.max(halfWidth, halfHeight);
final Path path = new Path();
path.addCircle(halfWidth, halfHeight, radius, Path.Direction.CCW);
final Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.DST_IN));
canvas.drawPath(path, paint);
}
Note:
- It's not good to create objects inside onDraw() calls. Hence you should have your paint and shader initially somewhere else. This could probably be done when you set the image bitmap to the view.
-
Canvas
might need to be saved and restored when it is not backed by a hardware texture. The general ideas around it are not mentioned here. - Remember to add
setWillNotDraw(false);
to the constructor.
Additional References:
-
https://sriramramani.wordpress.com/2012/12/21/shaders/ has information on
Shaders
. -
http://mxr.mozilla.org/mozilla-central/source/mobile/android/base/ShapedButton.java uses
Path
to curved button in Firefox for Android. -
http://sriramramani.wordpress.com/2012/08/27/constructing-squishy-buttons/ has information on
Canvas
saving, restoring and special cases for pre-ICS.
Solution 3
I'd definite recommend Picasso, as others have. This bit of code for one of my Activity classes did the trick for me. It utilized a color I had defined in color.xml and a simple layout (shown below).
ImageView profile_image = (ImageView) findViewById(R.id.profile_image);
mContext = profile_image.getContext();
// ----------------------------------------------------------------
// apply rounding to image
// see: https://github.com/vinc3m1/RoundedImageView
// ----------------------------------------------------------------
Transformation transformation = new RoundedTransformationBuilder()
.borderColor(getResources().getColor(R.color.my_special_orange))
.borderWidthDp(5)
.cornerRadiusDp(50)
.oval(false)
.build();
Picasso.with(mContext)
.load("http://{some_url}.jpg")
.fit()
.transform(transformation)
.into(profile_image);
And the corresponding Layout file:
<LinearLayout
android:orientation="horizontal"
android:layout_width="fill_parent"
android:layout_height="120dp"
android:layout_alignParentTop="true"
android:layout_alignParentStart="true"
android:padding="12dp">
<ImageView
android:id="@+id/profile_image"
android:layout_width="80dp"
android:layout_height="80dp"
android:layout_gravity="center"/>
<LinearLayout
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="80dp"
android:layout_gravity="center"
android:padding="12dp">
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textAppearance="?android:attr/textAppearanceLarge"
android:text="First-Name"
android:id="@+id/profile_first_name"
/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textAppearance="?android:attr/textAppearanceSmall"
android:text="Lastname"
android:id="@+id/profile_last_name" />
</LinearLayout>
</LinearLayout>
</RelativeLayout>
Here's the result:
Solution 4
A RoundedBitmapDrawable
from the v4 Support Library can be applied to an ImageView
to achieve the desired effect:
ImageView imageView = (ImageView)findViewById(R.id.imageView);
Bitmap avatar = BitmapFactory.decodeResource(getResources(), R.drawable.avatar);
RoundedBitmapDrawable roundDrawable = RoundedBitmapDrawableFactory.create(getResources(), avatar);
roundDrawable.setCircular(true);
imageView.setImageDrawable(roundDrawable);
Solution 5
A simple solution and without a black background!
public class CircleImageView extends ImageView
{
public CircleImageView(Context context)
{
super(context);
}
@Override
protected void onDraw(Canvas canvas)
{
// Create a circular path.
final float halfWidth = canvas.getWidth()/2;
final float halfHeight = canvas.getHeight()/2;
final float radius = Math.max(halfWidth, halfHeight);
final Path path = new Path();
path.addCircle(halfWidth, halfHeight, radius, Path.Direction.CCW);
canvas.clipPath(path);
super.onDraw(canvas);
}
}
![GrIsHu](https://i.stack.imgur.com/bdiI3.jpg?s=256&g=1)
GrIsHu
Android Developer Design, Develop and maintain applications(web,mobile), softwares. Develop and test database-driven and object-oriented web applications and web services. Develop and test sophisticated, cross-browser front-end HTML/CSS/Javascript Web GUIs. Develop, configure and maintain database tables for driven applications.
Updated on November 16, 2020Comments
-
GrIsHu over 3 years
I am having a
Custom ListView
which contains anImageView
andTextView
. Everything is working fine.What I want is the image is displayed in list are in round corner. From the Webservice i get the images in rectangle shape. But i want to display it in Round corner
ImageView
as below.Can anyone show me the way how can i mask the image in round corner?
I already tried by creating the drawable file as below and applied it as src in
ImageView
. But nothing working for me.<layer-list xmlns:android="http://schemas.android.com/apk/res/android" > <item> <shape android:shape="oval" > <solid android:color="#FFFFFF" /> <padding android:bottom="10dp" android:left="10dp" android:right="10dp" android:top="10dp" /> <corners android:radius="5dp" /> </shape> </item> <item> <shape android:shape="oval" > <padding android:bottom="5dp" android:left="5dp" android:right="5dp" android:top="5dp" /> <solid android:color="#FFFFFF" /> </shape> </item> </layer-list>
EDITED:
I have Applied below solution:
<FrameLayout android:id="@+id/imagemaskframe" android:layout_width="wrap_content" android:layout_height="wrap_content" android:padding="10dp" > <ImageView android:id="@+id/op_ivpic" android:layout_width="80dp" android:layout_height="80dp" android:layout_gravity="center" android:scaleType="fitXY" /> <ImageView android:id="@+id/iv_mask_op" android:layout_width="80dp" android:layout_height="80dp" android:layout_gravity="center" android:adjustViewBounds="true" android:scaleType="fitXY" android:src="@drawable/imgmask" /> </FrameLayout>