How can I write a Drawable resource to a File?

android, drawable, export

Solution

Although the best answer here have a nice approach. It's link only. Here's how you can do the steps:

Convert Drawable to Bitmap

You can do that in at least two different ways, depending on where you're getting the `Drawable` from.

- Drawable is on `res/drawable` folders.

Say you want to use a `Drawable` that is on your drawable folders. You can use the `BitmapFactory#decodeResource` approach. Example below.

Bitmap bm = BitmapFactory.decodeResource(mContext.getResources(), R.drawable.your_drawable);

- You have a `PictureDrawable` object.

If you're getting a `PictureDrawable` from somewhere else "at runtime", you can use the `Bitmap#createBitmap` approach to create your `Bitmap`. Like the example below.

public Bitmap drawableToBitmap(PictureDrawable pd) {
    Bitmap bm = Bitmap.createBitmap(pd.getIntrinsicWidth(), pd.getIntrinsicHeight(), Bitmap.Config.ARGB_8888);
    Canvas canvas = new Canvas(bm);
    canvas.drawPicture(pd.getPicture());
    return bm;
}

Save the Bitmap to disk

Once you have your `Bitmap` object, you can save it to the permanent storage. You'll just have to choose the file format (JPEG, PNG or WEBP).

/**
 * @param dir you can get from many places like Environment.getExternalStorageDirectory() or mContext.getFilesDir() depending on where you want to save the image.
 * @param fileName The file name.
 * @param bm The Bitmap you want to save.
 * @param format Bitmap.CompressFormat can be PNG,JPEG or WEBP.
 * @param quality quality goes from 1 to 100. (Percentage).
 * @return true if the Bitmap was saved successfully, false otherwise.
 */
boolean saveBitmapToFile(File dir, String fileName, Bitmap bm, 
    Bitmap.CompressFormat format, int quality) {
    
    File imageFile = new File(dir,fileName);

    FileOutputStream fos = null;
    try {
        fos = new FileOutputStream(imageFile);

        bm.compress(format,quality,fos);

        fos.close();

        return true;
    }
    catch (IOException e) {
        Log.e("app",e.getMessage());
        if (fos != null) {
            try {
                fos.close();
            } catch (IOException e1) {
                e1.printStackTrace();
            }
        }
    }
    return false;
}

And to get the target directory, try something like:

File dir = new File(Environment.getExternalStorageDirectory() + File.separator + "drawable");

boolean doSave = true;
if (!dir.exists()) {
    doSave = dir.mkdirs();
}

if (doSave) {
    saveBitmapToFile(dir,"theNameYouWant.png",bm,Bitmap.CompressFormat.PNG,100);
}
else {
    Log.e("app","Couldn't create target directory.");
}

Obs: Remember to do this kind of work on a background Thread if you're dealing with large images, or many images, because it can take some time to finish and might block your UI, making your app unresponsive.

Problem

I need to export some `Drawable` resources to a file. For example, I have a function that returns to me a `Drawable` object. I want to write it out to a file in `/sdcard/drawable/newfile.png`. How can i do it?

Original source

Related problems