How to convert a Drawable to a Bitmap?

AndroidBitmapWallpaperAndroid Drawable

Android Problem Overview


I would like to set a certain Drawable as the device's wallpaper, but all wallpaper functions accept Bitmaps only. I cannot use WallpaperManager because I'm pre 2.1.

Also, my drawables are downloaded from the web and do not reside in R.drawable.

Android Solutions


Solution 1 - Android

This piece of code helps.

Bitmap icon = BitmapFactory.decodeResource(context.getResources(),
                                           R.drawable.icon_resource);

Here a version where the image gets downloaded.

String name = c.getString(str_url);
URL url_value = new URL(name);
ImageView profile = (ImageView)v.findViewById(R.id.vdo_icon);
if (profile != null) {
    Bitmap mIcon1 =
        BitmapFactory.decodeStream(url_value.openConnection().getInputStream());
    profile.setImageBitmap(mIcon1);
}

Solution 2 - Android

public static Bitmap drawableToBitmap (Drawable drawable) {
    Bitmap bitmap = null;

    if (drawable instanceof BitmapDrawable) {
        BitmapDrawable bitmapDrawable = (BitmapDrawable) drawable;
        if(bitmapDrawable.getBitmap() != null) {
            return bitmapDrawable.getBitmap();
        }
    }

    if(drawable.getIntrinsicWidth() <= 0 || drawable.getIntrinsicHeight() <= 0) {
        bitmap = Bitmap.createBitmap(1, 1, Bitmap.Config.ARGB_8888); // Single color bitmap will be created of 1x1 pixel
    } else {
        bitmap = Bitmap.createBitmap(drawable.getIntrinsicWidth(), drawable.getIntrinsicHeight(), Bitmap.Config.ARGB_8888);
    }

    Canvas canvas = new Canvas(bitmap);
    drawable.setBounds(0, 0, canvas.getWidth(), canvas.getHeight());
    drawable.draw(canvas);
    return bitmap;
}

Solution 3 - Android

This converts a BitmapDrawable to a Bitmap.

Drawable d = ImagesArrayList.get(0);  
Bitmap bitmap = ((BitmapDrawable)d).getBitmap();

Solution 4 - Android

A Drawable can be drawn onto a Canvas, and a Canvas can be backed by a Bitmap:

(Updated to handle a quick conversion for BitmapDrawables and to ensure that the Bitmap created has a valid size)

public static Bitmap drawableToBitmap (Drawable drawable) {
    if (drawable instanceof BitmapDrawable) {
        return ((BitmapDrawable)drawable).getBitmap();
    }

    int width = drawable.getIntrinsicWidth();
    width = width > 0 ? width : 1;
    int height = drawable.getIntrinsicHeight();
    height = height > 0 ? height : 1;

    Bitmap bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
    Canvas canvas = new Canvas(bitmap); 
    drawable.setBounds(0, 0, canvas.getWidth(), canvas.getHeight());
    drawable.draw(canvas);

    return bitmap;
}

Solution 5 - Android

METHOD 1 : Either you can directly convert to bitmap like this

Bitmap myLogo = BitmapFactory.decodeResource(context.getResources(), R.drawable.my_drawable);

METHOD 2 : You can even convert the resource into the drawable and from that you can get bitmap like this

Bitmap myLogo = ((BitmapDrawable)getResources().getDrawable(R.drawable.logo)).getBitmap();

For API > 22 getDrawable method moved to the ResourcesCompat class so for that you do something like this

Bitmap myLogo = ((BitmapDrawable) ResourcesCompat.getDrawable(context.getResources(), R.drawable.logo, null)).getBitmap();

Solution 6 - Android

android-ktx has Drawable.toBitmap method: https://android.github.io/android-ktx/core-ktx/androidx.graphics.drawable/android.graphics.drawable.-drawable/to-bitmap.html

From Kotlin

val bitmap = myDrawable.toBitmap()

Solution 7 - Android

1) Drawable to Bitmap :

Bitmap mIcon = BitmapFactory.decodeResource(context.getResources(),R.drawable.icon);
// mImageView.setImageBitmap(mIcon);


2) Bitmap to Drawable :

Drawable mDrawable = new BitmapDrawable(getResources(), bitmap);
// mImageView.setDrawable(mDrawable);

Solution 8 - Android

very simple

Bitmap tempBMP = BitmapFactory.decodeResource(getResources(),R.drawable.image);

Solution 9 - Android

The latest androidx core library (androidx.core:core-ktx:1.2.0) now has an extension function: Drawable.toBitmap(...) to convert a Drawable to a Bitmap.

Solution 10 - Android

So after looking (and using) of the other answers, seems they all handling ColorDrawable and PaintDrawable badly. (Especially on lollipop) seemed that Shaders were tweaked so solid blocks of colors were not handled correctly.

I am using the following code now:

public static Bitmap drawableToBitmap(Drawable drawable) {
    if (drawable instanceof BitmapDrawable) {
        return ((BitmapDrawable) drawable).getBitmap();
    }

    // We ask for the bounds if they have been set as they would be most
    // correct, then we check we are  > 0
    final int width = !drawable.getBounds().isEmpty() ?
            drawable.getBounds().width() : drawable.getIntrinsicWidth();

    final int height = !drawable.getBounds().isEmpty() ?
            drawable.getBounds().height() : drawable.getIntrinsicHeight();

    // Now we check we are > 0
    final Bitmap bitmap = Bitmap.createBitmap(width <= 0 ? 1 : width, height <= 0 ? 1 : height,
            Bitmap.Config.ARGB_8888);
    Canvas canvas = new Canvas(bitmap);
    drawable.setBounds(0, 0, canvas.getWidth(), canvas.getHeight());
    drawable.draw(canvas);

    return bitmap;
}

Unlike the others, if you call setBounds on the Drawable before asking to turn it into a bitmap, it will draw the bitmap at the correct size!

Solution 11 - Android

Maybe this will help someone...

From PictureDrawable to Bitmap, use:

private Bitmap pictureDrawableToBitmap(PictureDrawable pictureDrawable){ 
    Bitmap bmp = Bitmap.createBitmap(pictureDrawable.getIntrinsicWidth(), pictureDrawable.getIntrinsicHeight(), Config.ARGB_8888); 
    Canvas canvas = new Canvas(bmp); 
    canvas.drawPicture(pictureDrawable.getPicture()); 
    return bmp; 
}

... implemented as such:

Bitmap bmp = pictureDrawableToBitmap((PictureDrawable) drawable);

Solution 12 - Android

Here is better resolution

public static Bitmap drawableToBitmap (Drawable drawable) {
    if (drawable instanceof BitmapDrawable) {
        return ((BitmapDrawable)drawable).getBitmap();
    }

    Bitmap bitmap = Bitmap.createBitmap(drawable.getIntrinsicWidth(), drawable.getIntrinsicHeight(), Config.ARGB_8888);
    Canvas canvas = new Canvas(bitmap); 
    drawable.setBounds(0, 0, canvas.getWidth(), canvas.getHeight());
    drawable.draw(canvas);

    return bitmap;
}

public static InputStream bitmapToInputStream(Bitmap bitmap) {
    int size = bitmap.getHeight() * bitmap.getRowBytes();
    ByteBuffer buffer = ByteBuffer.allocate(size);
    bitmap.copyPixelsToBuffer(buffer);
    return new ByteArrayInputStream(buffer.array());
}

Code from https://stackoverflow.com/questions/6341770/how-to-read-drawable-bits-as-inputstream/6341899#6341899

Solution 13 - Android

Here is the nice Kotlin version of the answer provided by @Chris.Jenkins here: https://stackoverflow.com/a/27543712/1016462

fun Drawable.toBitmap(): Bitmap {
  if (this is BitmapDrawable) {
    return bitmap
  }

  val width = if (bounds.isEmpty) intrinsicWidth else bounds.width()
  val height = if (bounds.isEmpty) intrinsicHeight else bounds.height()

  return Bitmap.createBitmap(width.nonZero(), height.nonZero(), Bitmap.Config.ARGB_8888).also {
    val canvas = Canvas(it)
    setBounds(0, 0, canvas.width, canvas.height)
    draw(canvas)
  }
}

private fun Int.nonZero() = if (this <= 0) 1 else this

Solution 14 - Android

> Bitmap bitmap = BitmapFactory.decodeResource(context.getResources(), > R.drawable.icon);

This will not work every time for example if your drawable is layer list drawable then it gives a null response, so as an alternative you need to draw your drawable into canvas then save as bitmap, please refer below a cup of code.

public void drawableToBitMap(Context context, int drawable, int widthPixels, int heightPixels) {
    try {
        File file = new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS) + "/", "drawable.png");
        FileOutputStream fOut = new FileOutputStream(file);
        Drawable drw = ResourcesCompat.getDrawable(context.getResources(), drawable, null);
        if (drw != null) {
            convertToBitmap(drw, widthPixels, heightPixels).compress(Bitmap.CompressFormat.PNG, 100, fOut);
        }
        fOut.flush();
        fOut.close();
    } catch (Exception e) {
        e.printStackTrace();
    }
}

private Bitmap convertToBitmap(Drawable drawable, int widthPixels, int heightPixels) {
    Bitmap bitmap = Bitmap.createBitmap(widthPixels, heightPixels, Bitmap.Config.ARGB_8888);
    Canvas canvas = new Canvas(bitmap);
    drawable.setBounds(0, 0, widthPixels, heightPixels);
    drawable.draw(canvas);
    return bitmap;
}

above code save you're drawable as drawable.png in the download directory

Solution 15 - Android

Android provides a non straight foward solution: BitmapDrawable. To get the Bitmap , we'll have to provide the resource id R.drawable.flower_pic to the a BitmapDrawable and then cast it to a Bitmap.

Bitmap bm = ((BitmapDrawable) getResources().getDrawable(R.drawable.flower_pic)).getBitmap();

Solution 16 - Android

Use this code.it will help you for achieving your goal.

 Bitmap bmp=BitmapFactory.decodeResource(getResources(), R.drawable.profileimage);
	if (bmp!=null) {
		Bitmap bitmap_round=getRoundedShape(bmp);
		if (bitmap_round!=null) {
			profileimage.setImageBitmap(bitmap_round);
		}
	}

  public Bitmap getRoundedShape(Bitmap scaleBitmapImage) {
	int targetWidth = 100;
	int targetHeight = 100;
	Bitmap targetBitmap = Bitmap.createBitmap(targetWidth, 
			targetHeight,Bitmap.Config.ARGB_8888);

	Canvas canvas = new Canvas(targetBitmap);
	Path path = new Path();
	path.addCircle(((float) targetWidth - 1) / 2,
			((float) targetHeight - 1) / 2,
			(Math.min(((float) targetWidth), 
					((float) targetHeight)) / 2),
					Path.Direction.CCW);

	canvas.clipPath(path);
	Bitmap sourceBitmap = scaleBitmapImage;
	canvas.drawBitmap(sourceBitmap, 
			new Rect(0, 0, sourceBitmap.getWidth(),
					sourceBitmap.getHeight()), 
					new Rect(0, 0, targetWidth, targetHeight), new Paint(Paint.FILTER_BITMAP_FLAG));
	return targetBitmap;
}

Solution 17 - Android

BitmapFactory.decodeResource() automatically scales the bitmap, so your bitmap may turn out fuzzy. To prevent scaling, do this:

BitmapFactory.Options options = new BitmapFactory.Options();
options.inScaled = false;
Bitmap source = BitmapFactory.decodeResource(context.getResources(),
                                             R.drawable.resource_name, options);

or

InputStream is = context.getResources().openRawResource(R.drawable.resource_name)
bitmap = BitmapFactory.decodeStream(is);

Solution 18 - Android

ImageWorker Library can convert bitmap to drawable or base64 and vice versa.

val bitmap: Bitmap? = ImageWorker.convert().drawableToBitmap(sourceDrawable)

Implementation

In Project Level Gradle

allprojects {
		repositories {
			...
			maven { url 'https://jitpack.io' }
		}
	}

In Application Level Gradle

dependencies {
	        implementation 'com.github.1AboveAll:ImageWorker:0.51'
	}

You can also store and retrieve bitmaps/drawables/base64 images from external.

Check here. https://github.com/1AboveAll/ImageWorker/edit/master/README.md

Solution 19 - Android

if you are using kotlin the use below code. it'll work

// for using image path

val image = Drawable.createFromPath(path)
val bitmap = (image as BitmapDrawable).bitmap

Solution 20 - Android

 // get image path from gallery
protected void onActivityResult(int requestCode, int resultcode, Intent intent) {
    super.onActivityResult(requestCode, resultcode, intent);
  
    if (requestCode == 1) {
        if (intent != null && resultcode == RESULT_OK) {             
            Uri selectedImage = intent.getData();
       
            String[] filePathColumn = {MediaStore.Images.Media.DATA};
            Cursor cursor = getContentResolver().query(selectedImage, filePathColumn, null, null, null);
            cursor.moveToFirst();
            int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
            filePath = cursor.getString(columnIndex);

            //display image using BitmapFactory

            cursor.close(); bmp = BitmapFactory.decodeFile(filepath); 
            iv.setBackgroundResource(0);
            iv.setImageBitmap(bmp);
        }
    }
}

Solution 21 - Android

I've used a few answers on this thread but some of them didn't work as expected (maybe they had worked in older versions) but I wanted to share mine after a few tries and errors, using an extension function:

val markerOption = MarkerOptions().apply {
    position(LatLng(driver.lat, driver.lng))
    icon(R.drawabel.your_drawable.toBitmapDescriptor(context))
    snippet(driver.driverId.toString())
}
mMap.addMarker(markerOption)

This is the extension function:

fun Int.toBitmapDescriptor(context: Context): BitmapDescriptor {
    val vectorDrawable = ResourcesCompat.getDrawable(context.resources, this, context.theme)
    val bitmap = vectorDrawable?.toBitmap(
        vectorDrawable.intrinsicWidth,
        vectorDrawable.intrinsicHeight,
        Bitmap.Config.ARGB_8888
    )
    return BitmapDescriptorFactory.fromBitmap(bitmap!!)
}

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionRobView Question on Stackoverflow
Solution 1 - AndroidPraveenView Answer on Stackoverflow
Solution 2 - AndroidAndréView Answer on Stackoverflow
Solution 3 - AndroidRobView Answer on Stackoverflow
Solution 4 - AndroidkabukoView Answer on Stackoverflow
Solution 5 - AndroidKeyur LakhaniView Answer on Stackoverflow
Solution 6 - AndroidMyDogTomView Answer on Stackoverflow
Solution 7 - AndroidSanjayrajsinhView Answer on Stackoverflow
Solution 8 - AndroidErfan BagheriView Answer on Stackoverflow
Solution 9 - AndroidBalazs BanyaiView Answer on Stackoverflow
Solution 10 - AndroidChris.JenkinsView Answer on Stackoverflow
Solution 11 - AndroidMauroView Answer on Stackoverflow
Solution 12 - AndroidGelldurView Answer on Stackoverflow
Solution 13 - AndroidtasomaniacView Answer on Stackoverflow
Solution 14 - AndroidKishan DongaView Answer on Stackoverflow
Solution 15 - Androidkc ochibiliView Answer on Stackoverflow
Solution 16 - Androidanupam sharmaView Answer on Stackoverflow
Solution 17 - AndroidJohn DoeView Answer on Stackoverflow
Solution 18 - AndroidHimanshu RawatView Answer on Stackoverflow
Solution 19 - AndroidSachidananda SahuView Answer on Stackoverflow
Solution 20 - AndroidAngelView Answer on Stackoverflow
Solution 21 - AndroidAlbertoView Answer on Stackoverflow