I know this question has been asked before but I have struggled to come up with a solution.
I have a custom ImageView with complete rounded corners which is done programmatically.
I have something like this
But I want to get to something like this:
Here is my custom ImageView class.
#SuppressLint("NewApi")
public class MLRoundedImageView extends ImageView {
private Context context;
public MLRoundedImageView(Context context) {
super(context);
this.context = context;
}
public MLRoundedImageView(Context context, AttributeSet attrs) {
super(context, attrs);
this.context = context;
}
public MLRoundedImageView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
this.context = context;
}
#Override
protected void onDraw(Canvas canvas) {
Drawable drawable = getDrawable();
if (drawable == null) {
return;
}
if (getWidth() == 0 || getHeight() == 0) {
return;
}
Bitmap b = ((BitmapDrawable) drawable).getBitmap();
Bitmap bitmap = b.copy(Bitmap.Config.ARGB_8888, true);
int w = getWidth(), h = getHeight();
Bitmap roundBitmap = getCroppedBitmap(bitmap, w);
canvas.drawBitmap(roundBitmap, 0, 0, null);
}
#SuppressLint("NewApi")
public Bitmap getCroppedBitmap(Bitmap bmp, int radius) {
Bitmap sbmp;
if (bmp.getWidth() != radius || bmp.getHeight() != radius) {
float smallest = Math.min(bmp.getWidth(), bmp.getHeight());
float factor = smallest / radius;
sbmp = Bitmap.createScaledBitmap(bmp, (int)(bmp.getWidth() / factor), (int)(bmp.getHeight() / factor), false);
} else {
sbmp = bmp;
}
Bitmap output = Bitmap.createBitmap(radius, radius,
Config.ARGB_8888);
Canvas canvas = new Canvas(output);
final int color = 0xffa19774;
final Paint paint = new Paint();
final Rect rect = new Rect(0, 0, radius, radius);
paint.setAntiAlias(true);
paint.setFilterBitmap(true);
paint.setDither(true);
canvas.drawARGB(0, 0, 0, 0);
paint.setColor(Color.parseColor("#BAB399"));
canvas.drawCircle(radius / 2 + 0.7f,
radius / 2 + 0.7f, radius / 2 + 0.1f, paint);
paint.setXfermode(new PorterDuffXfermode(Mode.SRC_IN));
canvas.drawBitmap(sbmp, rect, rect, paint);
return output;
}
}
I know there is just a few extra I need to add i don't want to recreate the entire class as my project is heavily depended on it.
Thanks in advance!
Use layer list:
http://developer.android.com/guide/topics/resources/drawable-resource.html#LayerList
Basically create a white circle with the dimension you want and use layer list to create it under the picture
Related
I rounded Image View but the picture of Image view not round?
I use eclipse and XML
What do I do? see this picture:
You can use this
Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.image);
RoundedBitmapDrawable circularBitmapDrawable = RoundedBitmapDrawableFactory.create(getResources(), bitmap);
circularBitmapDrawable.setCircular(true);
userImage.setImageDrawable(circularBitmapDrawable);
The problem with your ImageView is that your ImageViews background is Rounded but the Image you set in your android:src="" is not rounded, thats why you are getting a Image like that
I was looking for a rounded ImageView too a few days ago and i found this to make any ImageView rounded without using any Library
public class RoundedImageView extends ImageView {
public RoundedImageView(Context context) {
super(context);
// TODO Auto-generated constructor stub
}
public RoundedImageView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public RoundedImageView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
#Override
protected void onDraw(Canvas canvas) {
Drawable drawable = getDrawable();
if (drawable == null) {
return;
}
if (getWidth() == 0 || getHeight() == 0) {
return;
}
Bitmap b = null;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP
&& drawable instanceof VectorDrawable) {
((VectorDrawable) drawable).draw(canvas);
b = Bitmap.createBitmap(canvas.getWidth(), canvas.getHeight(), Bitmap.Config.ARGB_8888);
Canvas c = new Canvas();
c.setBitmap(b);
drawable.draw(c);
}
else {
b = ((BitmapDrawable) drawable).getBitmap();
}
Bitmap bitmap = b.copy(Bitmap.Config.ARGB_8888, true);
int w = getWidth(), h = getHeight();
Bitmap roundBitmap = getCroppedBitmap(bitmap, w);
canvas.drawBitmap(roundBitmap, 0,0, null);
}
public static Bitmap getCroppedBitmap(Bitmap bmp, int radius) {
Bitmap sbmp;
if(bmp.getWidth() != radius || bmp.getHeight() != radius)
sbmp = Bitmap.createScaledBitmap(bmp, radius, radius, false);
else
sbmp = bmp;
Bitmap output = Bitmap.createBitmap(sbmp.getWidth(),
sbmp.getHeight(), Config.ARGB_8888);
Canvas canvas = new Canvas(output);
final int color = 0xffa19774;
final Paint paint = new Paint();
final Rect rect = new Rect(0, 0, sbmp.getWidth(), sbmp.getHeight());
paint.setAntiAlias(true);
paint.setFilterBitmap(true);
paint.setDither(true);
canvas.drawARGB(0, 0, 0, 0);
paint.setColor(Color.parseColor("#BAB399"));
canvas.drawCircle(sbmp.getWidth() / 2+0.7f, sbmp.getHeight() / 2+0.7f,
sbmp.getWidth() / 2+0.1f, paint);
paint.setXfermode(new PorterDuffXfermode(Mode.SRC_IN));
canvas.drawBitmap(sbmp, rect, rect, paint);
return output;
}
}
But if you want to use a Library check this out https://github.com/vinc3m1/RoundedImageView
Use image as .png format then only image background transparent and image show inside the round.
Well I have implemented imageview to Collapsing toolbar using the answer provided by Sanjeet Ajnabee on Anchor ImageView to Collapsing Toolbar . The implementation worked fine but now what i want is to add the edit button inside the profile picture so that i can browse the gallery from that button. please help.
This is my code
public class FloatingActionImageView extends FloatingActionButton {
public FloatingActionImageView(Context context) {
super(context);
}
public FloatingActionImageView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public FloatingActionImageView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
public static Bitmap getCroppedBitmap(Bitmap bmp, int radius) {
Bitmap sBmp;
if (bmp.getWidth() != radius || bmp.getHeight() != radius) {
float smallest = Math.min(bmp.getWidth(), bmp.getHeight());
float factor = smallest / radius;
sBmp = Bitmap.createScaledBitmap(bmp, (int) (bmp.getWidth() / factor), (int) (bmp.getHeight() / factor), false);
} else {
sBmp = bmp;
}
Bitmap output = Bitmap.createBitmap(radius, radius,
Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(output);
final Paint paint = new Paint();
final Rect rect = new Rect(0, 0, radius + 5, radius + 5);
paint.setAntiAlias(true);
paint.setFilterBitmap(true);
paint.setDither(true);
canvas.drawARGB(0, 0, 0, 0);
paint.setColor(Color.parseColor("#BAB399"));
canvas.drawCircle(radius / 2,
radius / 2, radius / 2, paint);
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
canvas.drawBitmap(sBmp, rect, rect, paint);
return output;
}
#Override
protected void onDraw(#NonNull Canvas canvas) {
Drawable drawable = getDrawable();
if (drawable == null) {
return;
}
if (getWidth() == 0 || getHeight() == 0) {
return;
}
Bitmap b = ((BitmapDrawable) drawable).getBitmap();
Bitmap bitmap = null;
if (b != null) {
bitmap = b.copy(Bitmap.Config.ARGB_8888, true);
} else {
BitmapDrawable bitmapDrawable = null;
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.LOLLIPOP) {
bitmapDrawable = ((BitmapDrawable) getResources().getDrawable(R.drawable.ic_hospital, null));
} else {
bitmapDrawable = ((BitmapDrawable) getResources().getDrawable(R.drawable.ic_hospital));
}
if (bitmapDrawable != null) {
bitmap = bitmapDrawable.getBitmap();
}
}
int w = getWidth();
Bitmap roundBitmap = getCroppedBitmap(bitmap, w);
canvas.drawBitmap(roundBitmap, 0, 0, null);
}
}
And this is my layout
<com.example.cripes.rsnepal.FloatingActionImageView
android:layout_height="100dp"
android:layout_width="100dp"
app:layout_anchor="#id/appbarProfile"
app:layout_anchorGravity="bottom|end"
android:src="#drawable/ic_hospital"
android:layout_margin="#dimen/fab_margin"
android:clickable="true" />
How to create a layout like shown in image?
I think you can use android:rotation="-45" to put over the image a crossed component and make this effect.
Use this code :
1. Create TriangleImageView.java class in Java folder :
public class TriangleImageView extends ImageView {
public TriangleImageView(Context ctx, AttributeSet attrs) {
super(ctx, attrs);
}
#Override
protected void onDraw(Canvas canvas) {
Drawable drawable = getDrawable();
if (drawable == null) {
return;
}
if (getWidth() == 0 || getHeight() == 0) {
return;
}
Bitmap b = ((BitmapDrawable) drawable).getBitmap();
Bitmap bitmap = b.copy(Bitmap.Config.ARGB_8888, true);
int w = getWidth(), h = getHeight();
Bitmap roundBitmap = getRoundedCroppedBitmap(bitmap, w);
canvas.drawBitmap(roundBitmap, 0, 0, null);
}
public static Bitmap getRoundedCroppedBitmap(Bitmap bitmap, int radius) {
Bitmap finalBitmap;
if (bitmap.getWidth() != radius || bitmap.getHeight() != radius)
finalBitmap = Bitmap.createScaledBitmap(bitmap, radius, radius,
false);
else
finalBitmap = bitmap;
Bitmap output = Bitmap.createBitmap(finalBitmap.getWidth(),
finalBitmap.getHeight(), Config.ARGB_8888);
Canvas canvas = new Canvas(output);
Paint paint = new Paint();
final Rect rect = new Rect(0, 0, finalBitmap.getWidth(),
finalBitmap.getHeight());
Point point1_draw = new Point(75, 0);
Point point2_draw = new Point(0, 180);
Point point3_draw = new Point(180, 180);
Path path = new Path();
path.moveTo(point1_draw.x, point1_draw.y);
path.lineTo(point2_draw.x, point2_draw.y);
path.lineTo(point3_draw.x, point3_draw.y);
path.lineTo(point1_draw.x, point1_draw.y);
path.close();
canvas.drawARGB(0, 0, 0, 0);
paint.setColor(Color.parseColor("#BAB399"));
canvas.drawPath(path, paint);
paint.setXfermode(new PorterDuffXfermode(Mode.SRC_IN));
canvas.drawBitmap(finalBitmap, rect, rect, paint);
return output;
}
}
In Acitivity Use this code :
private imageViewTriangle;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
imageViewTriangle=(ImageView)findViewById(R.id.imageView_triangle);
Bitmap icon = BitmapFactory.decodeResource(getResources(), R.drawable.images);
imageViewTriangle.setImageBitmap(icon);
}
Output is :
Modify it as your need.
Note : ImageView is define in comment because it give me trouble to improve formatting ..
As stated above you can restructure the custom image class as the code below
public class ProfileImageView extends AppCompatImageView{
public ProfileImageView(Context context) {
super(context);
}
public ProfileImageView(Context context, #Nullable AttributeSet attrs) {
super(context, attrs);
}
public ProfileImageView(Context context, #Nullable AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
#Override
protected void onDraw(Canvas canvas) {
Drawable drawable = getDrawable();
if (drawable == null) {
return;
}
if (getWidth() == 0 || getHeight() == 0) {
return;
}
Bitmap b = ((BitmapDrawable) drawable).getBitmap();
Bitmap bitmap = b.copy(Bitmap.Config.ARGB_8888, true);
int w = getWidth(), h = getHeight();
Bitmap roundBitmap = getRoundedCroppedBitmap(bitmap, w,this.getLayoutParams().width,this.getLayoutParams().height);
canvas.drawBitmap(roundBitmap, 0, 0, null);
}
public static Bitmap getRoundedCroppedBitmap(Bitmap bitmap, int radius, int dimension_w, int dimension_h) {
Bitmap finalBitmap;
if (bitmap.getWidth() != radius || bitmap.getHeight() != radius)
finalBitmap = Bitmap.createScaledBitmap(bitmap, radius, radius,
false);
else
finalBitmap = bitmap;
Bitmap output = Bitmap.createBitmap(finalBitmap.getWidth(),
finalBitmap.getHeight(), Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(output);
Paint paint = new Paint();
final Rect rect = new Rect(0, 0, finalBitmap.getWidth(),
finalBitmap.getHeight());
Log.e("Profile",""+dimension_w);
Point point1_draw = new Point(0, 0);
Point point2_draw = new Point(dimension_w, 0);
Point point3_draw = new Point(dimension_w, (dimension_h/2));
Point point4_draw = new Point(0, dimension_h);
Path path = new Path();
path.moveTo(point1_draw.x, point1_draw.y);
path.lineTo(point2_draw.x, point2_draw.y);
path.lineTo(point3_draw.x, point3_draw.y);
path.lineTo(point4_draw.x, point4_draw.y);
path.lineTo(point1_draw.x, point1_draw.y);
path.close();
canvas.drawARGB(0, 0, 0, 0);
paint.setColor(Color.parseColor("#BAB399"));
canvas.drawPath(path, paint);
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
canvas.drawBitmap(finalBitmap, rect, rect, paint);
return output;
}
}
Sample screen shot
I made this Custom Drawable that should clip any Drawable in circle. But with my implementation, the drawable passed is being the output in the original form not in the circular form.
public class CircularDrawable extends Drawable {
Paint mPaint,xfermodePaint;
Drawable mDrawable;
int[] vinylCenter = new int[2];
int radius;
Bitmap src;
PorterDuffXfermode xfermode;
Rect rect;
Canvas testCanvas;
public CircularDrawable(Drawable drawable) {
mDrawable = drawable;
mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
mPaint.setColor(0xffffffff);
mPaint.setStyle(Paint.Style.FILL);
xfermodePaint = new Paint(Paint.ANTI_ALIAS_FLAG);
xfermode=new PorterDuffXfermode(PorterDuff.Mode.SRC_IN);
xfermodePaint.setXfermode(xfermode);
testCanvas=new Canvas();
}
#Override
public void setBounds(Rect bounds) {
super.setBounds(bounds);
mDrawable.setBounds(bounds);
}
#Override
public void setBounds(int left, int top, int right, int bottom) {
super.setBounds(left, top, right, bottom);
mDrawable.setBounds(left, top, right, bottom);
}
#Override
protected void onBoundsChange(Rect bounds) {
super.onBoundsChange(bounds);
vinylCenter[0] = bounds.width() / 2;
vinylCenter[1] = bounds.height() / 2;
radius = (bounds.right - bounds.left) / 2;
src = Bitmap.createBitmap(bounds.width(), bounds.height(), Bitmap.Config.ARGB_8888);
testCanvas.setBitmap(src);
}
#Override
public void draw(Canvas canvas) {
canvas.save();
canvas.drawARGB(0, 0, 0, 0);
canvas.drawCircle(vinylCenter[0],vinylCenter[1],radius,mPaint);
mDrawable.draw(testCanvas);
canvas.drawBitmap(src,0f,0f,xfermodePaint);
}
#Override
public void setAlpha(int alpha) {/*ignored*/}
#Override
public void setColorFilter(ColorFilter colorFilter) {/*ignored*/}
#Override
public int getOpacity() {
/*ignored*/
return 0;
}
}
What is my mistake?
Also I am using a SquareImageview to display this drawable that just makes the view square in onMeasure.
This question is not meant for Circular imageview.
You already have optimized implementation for circular drawable in Support library v4:
Google reference
/**
* A Drawable that wraps a bitmap and can be drawn with rounded corners. You can create a
* RoundedBitmapDrawable from a file path, an input stream, or from a
* {#link android.graphics.Bitmap} object.
* <p>
* Also see the {#link android.graphics.Bitmap} class, which handles the management and
* transformation of raw bitmap graphics, and should be used when drawing to a
* {#link android.graphics.Canvas}.
* </p>
*/
public abstract class RoundedBitmapDrawable extends Drawable ....
The canvas doesnt have alpha channel on by default when using Porter/Duff xfermode mode (As per my experience with my this in android). That is the reason the whole image(src) is being the output. Porter/Duff xfermode acts based on Alpha Channel.
In many implementation of Circular Drawable 2 Canvas are taken, out of which one is given RGB image bitmap and other is given only alpha channel bitmap with circular mask. Porter/Duff xfermodeis applied and the result is drawn on the main canvas.
My mistake is that I am not specifying the draw function's canvas that alpha channel is to be considered on using the layer on the canvas for xfermode.
The draw function will become
#Override
public void draw(Canvas canvas) {
int sc = canvas.saveLayer(null, null,
Canvas.HAS_ALPHA_LAYER_SAVE_FLAG |
);
canvas.drawCircle(vinylCenter[0],vinylCenter[1],radius,mPaint);
mDrawable.draw(testCanvas);
canvas.drawBitmap(src,0f,0f,xfermodePaint);
canvas.restoreToCount(sc);
}
Saving the Layer to indicate alpha channel with the flag and then using the xfermode. Finally restoring it to its save count.
So basically I use this method to get rounded corner images
public static Bitmap getRoundedCornerBitmap(Bitmap bitmap, int pixels) {
Bitmap output = Bitmap.createBitmap(bitmap.getWidth(), bitmap.getHeight(), Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(output);
final int color = 0xff424242;
final Paint paint = new Paint();
final Rect rect = new Rect(0, 0, bitmap.getWidth(), bitmap.getHeight());
final RectF rectF = new RectF(rect);
final float roundPx = pixels;
paint.setAntiAlias(true);
canvas.drawARGB(0, 0, 0, 0);
paint.setColor(color);
canvas.drawRoundRect(rectF, roundPx, roundPx, paint);
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
canvas.drawBitmap(bitmap, rect, rect, paint);
return output;
but like you pointed out sometimes it does not work, well it does work, but what happens most of the time is your imageview might have its scaletype set to centerCrop and other types, what I do is I first compress my image height to the same height and width as my imageview so that the entire image will fit in the imageview and no scaling will take place or I just calculate how much of the corner height to make rounded using this function based on the height
private int calculatePercentage(int percentage, int target)
{
int k = (int)(target*(percentage/100.0f));
return k;
}
so I use my code like: new Bitmap(getRoundedCornerBitmap(bmp, calculatePercentage(5, bmp.getHeight()))); where 5 is 5 of the image height this gives me same curves for all images be it some images are bigger than others
`
For rounded imageview you can use this code
public class RoundedImageView extends ImageView {
public RoundedImageView(Context context) {
super(context);
// TODO Auto-generated constructor stub
}
public RoundedImageView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public RoundedImageView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
#Override
protected void onDraw(Canvas canvas) {
Drawable drawable = getDrawable();
if (drawable == null) {
return;
}
if (getWidth() == 0 || getHeight() == 0) {
return;
}
Bitmap b = ((BitmapDrawable) drawable).getBitmap();
Bitmap bitmap = b.copy(Bitmap.Config.ARGB_8888, true);
int w = getWidth();//, h = getHeight();
Bitmap roundBitmap = getCroppedBitmap(bitmap, w);
canvas.drawBitmap(roundBitmap, 0, 0, null);
}
public static Bitmap getCroppedBitmap(Bitmap bmp, int radius)
{
Bitmap sbmp;
if (bmp.getWidth() != radius || bmp.getHeight() != radius)
sbmp = Bitmap.createScaledBitmap(bmp, radius, radius, false);
else
sbmp = bmp;
Bitmap output = Bitmap.createBitmap(sbmp.getWidth(), sbmp.getHeight(),Config.ARGB_8888);
Canvas canvas = new Canvas(output);
// final int color = 0xffa19774;
final Paint paint = new Paint();
final Rect rect = new Rect(0, 0, sbmp.getWidth(), sbmp.getHeight());
paint.setAntiAlias(true);
paint.setFilterBitmap(true);
paint.setDither(true);
canvas.drawARGB(0, 0, 0, 0);
// paint.setColor(Color.parseColor("#BAB399"));
paint.setColor(Color.parseColor("#FF0000"));
canvas.drawCircle(sbmp.getWidth() / 2 + 0.7f, sbmp.getHeight() / 2 + 0.7f, sbmp.getWidth() / 2 + 0.1f, paint);
paint.setXfermode(new PorterDuffXfermode(Mode.SRC_IN));
canvas.drawBitmap(sbmp, rect, rect, paint);
return output;
}
}
For circular imageview use the below code
public class RoundedImageView extends ImageView {
public RoundedImageView(Context context) {
super(context);
}
public RoundedImageView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public RoundedImageView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
#Override
protected void onDraw(Canvas canvas) {
BitmapDrawable drawable = (BitmapDrawable) getDrawable();
if (drawable == null) {
return;
}
if (getWidth() == 0 || getHeight() == 0) {
return;
}
Bitmap fullSizeBitmap = drawable.getBitmap();
int scaledWidth = getMeasuredWidth();
int scaledHeight = getMeasuredHeight();
/*
* scaledWidth = scaledWidth/2; scaledHeight = scaledHeight/2;
*/
Bitmap mScaledBitmap;
if (scaledWidth == fullSizeBitmap.getWidth()
&& scaledHeight == fullSizeBitmap.getHeight()) {
mScaledBitmap = fullSizeBitmap;
} else {
mScaledBitmap = Bitmap.createScaledBitmap(fullSizeBitmap,
scaledWidth, scaledHeight, true /* filter */);
}
// Bitmap roundBitmap = getRoundedCornerBitmap(mScaledBitmap);
// Bitmap roundBitmap = getRoundedCornerBitmap(getContext(),
// mScaledBitmap, 10, scaledWidth, scaledHeight, false, false,
// false, false);
// canvas.drawBitmap(roundBitmap, 0, 0, null);
Bitmap circleBitmap = getCircledBitmap(mScaledBitmap);
canvas.drawBitmap(circleBitmap, 0, 0, null);
}
public Bitmap getRoundedCornerBitmap(Context context, Bitmap input,
int pixels, int w, int h, boolean squareTL, boolean squareTR,
boolean squareBL, boolean squareBR) {
Bitmap output = Bitmap.createBitmap(w, h, Config.ARGB_8888);
Canvas canvas = new Canvas(output);
final float densityMultiplier = context.getResources()
.getDisplayMetrics().density;
final int color = 0xff424242;
final Paint paint = new Paint();
final Rect rect = new Rect(0, 0, w, h);
final RectF rectF = new RectF(rect);
// make sure that our rounded corner is scaled appropriately
final float roundPx = pixels * densityMultiplier;
paint.setAntiAlias(true);
canvas.drawARGB(0, 0, 0, 0);
paint.setColor(color);
canvas.drawRoundRect(rectF, roundPx, roundPx, paint);
// draw rectangles over the corners we want to be square
if (squareTL) {
canvas.drawRect(0, 0, w / 2, h / 2, paint);
}
if (squareTR) {
canvas.drawRect(w / 2, 0, w, h / 2, paint);
}
if (squareBL) {
canvas.drawRect(0, h / 2, w / 2, h, paint);
}
if (squareBR) {
canvas.drawRect(w / 2, h / 2, w, h, paint);
}
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
canvas.drawBitmap(input, 0, 0, paint);
return output;
}
Bitmap getCircledBitmap(Bitmap bitmap) {
Bitmap result = Bitmap.createBitmap(bitmap.getWidth(),
bitmap.getHeight(), Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(result);
int color = Color.BLUE;
Paint paint = new Paint();
Rect rect = new Rect(0, 0, bitmap.getWidth(), bitmap.getHeight());
paint.setAntiAlias(true);
canvas.drawARGB(0, 0, 0, 0);
paint.setColor(color);
// canvas.drawRoundRect(rectF, roundPx, roundPx, paint);
canvas.drawCircle(bitmap.getWidth() / 2, bitmap.getHeight() / 2,
bitmap.getHeight() / 2, paint);
paint.setXfermode(new PorterDuffXfermode(Mode.SRC_IN));
canvas.drawBitmap(bitmap, rect, rect, paint);
return result;
}
}
Try disabling hardware acceleration if you are using PorterDuffXfermode:
In manifest for whole activity:
<activity android:hardwareAccelerated="false" />
Or on a specific view on which you are using xfermode:
myView.setLayerType(View.LAYER_TYPE_SOFTWARE, null);
I have designed a separate image view class for rounded image. But When I am fetching image from facebook (profile picture). It throws Null Pointer Exception.
Process: com.moblit.fooddragon, PID: 605
java.lang.NullPointerException
at com.moblit.fooddragon.RoundedImageView.onDraw(RoundedImageView.java:44)
at android.view.View.draw(View.java:14508)
at android.view.View.getDisplayList(View.java:13405)
My Rounded Image View Code :
public class RoundedImageView extends ImageView {
public RoundedImageView(Context context) {
super(context);
// TODO Auto-generated constructor stub
}
public RoundedImageView(Context context, AttributeSet attrs) {
super(context, attrs);
}
public RoundedImageView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
#Override
protected void onDraw(Canvas canvas) {
Drawable drawable = getDrawable();
if (drawable == null) {
return;
}
if (getWidth() == 0 || getHeight() == 0) {
return;
}
Bitmap b = ((BitmapDrawable)drawable).getBitmap() ;
Bitmap bitmap = b.copy(Bitmap.Config.ARGB_8888, true);
int w = getWidth(), h = getHeight();
Bitmap roundBitmap = getCroppedBitmap(bitmap, w);
canvas.drawBitmap(roundBitmap, 0,0, null);
}
public static Bitmap getCroppedBitmap(Bitmap bmp, int radius) {
Bitmap sbmp;
if(bmp.getWidth() != radius || bmp.getHeight() != radius)
sbmp = Bitmap.createScaledBitmap(bmp, radius, radius, false);
else
sbmp = bmp;
Bitmap output = Bitmap.createBitmap(sbmp.getWidth(),
sbmp.getHeight(), Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(output);
final int color = 0xffa19774;
final Paint paint = new Paint();
final Rect rect = new Rect(0, 0, sbmp.getWidth(), sbmp.getHeight());
paint.setAntiAlias(true);
paint.setFilterBitmap(true);
paint.setDither(true);
canvas.drawARGB(0, 0, 0, 0);
paint.setColor(Color.parseColor("#BAB399"));
canvas.drawCircle(sbmp.getWidth() / 2+0.7f, sbmp.getHeight() / 2+0.7f,
sbmp.getWidth() / 2+0.1f, paint);
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_IN));
canvas.drawBitmap(sbmp, rect, rect, paint);
return output;
}
and code for fetching facebook profile picture :
ImageRequest imageRequest=new ImageRequest(url,
new Response.Listener<Bitmap>() {
#Override
public void onResponse(Bitmap response) {
Toast.makeText(context,"Got Bitmap",Toast.LENGTH_SHORT).show();
profilePicture=response;
}
},0,0,null,new Response.ErrorListener(){
public void onErrorResponse(VolleyError error) {
}
});
requestQueue.add(imageRequest);
NavigationDrawerFragment.imgAvatar.setImageBitmap(profilePicture);