起因
有一个需求,需要将xml布局,生成成一张图片。这样可以将图片导出保存,或者在ImageView上自适应的展示。(在布局多变的情况下,不用一直改字体大小啥的)。
百度了一圈,都达不到想要的,然后自己写了一个
功能
- 将xml布局加载成Bitmap
- 将随便什么View加载成Bitmap
- View已经渲染完成显示在页面上
- 加载的xml是ScrollView
- 背景可以透明,保存以后不会有黑色的底
效果
将这个xml,加载生成一个bitmap,然后加载到ImageView上,这样可以随意改变大小,自适应展示。或者可以保存图片到本地。
代码
使用
fun loadImageView(){
var bitmap= ImageUtils.loadBitmap(this,R.layout.window_coupon)
iv_image.setImageBitmap(bitmap)
}
工具类
/**
* 将 Bitmap 保存到SD卡
*
* @param context
* @param mybitmap
* @param
* @return
*/
public static Uri saveBitmapToSdCard(Context context, Bitmap mybitmap) {
Uri uri = null;
//创建位图保存目录
String path = Environment.getExternalStorageDirectory() + "/1000ttt/";
File sd = new File(path);
if (!sd.exists()) {
sd.mkdir();
}
String fileName = "mm_" + System.currentTimeMillis();
File file = new File(path + fileName + ".png");
FileOutputStream fileOutputStream = null;
if (!file.exists()) {
try {
// 判断SD卡是否存在,并且是否具有读写权限
if (Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)) {
fileOutputStream = new FileOutputStream(file);
mybitmap.compress(Bitmap.CompressFormat.PNG, 100, fileOutputStream);
fileOutputStream.flush();
fileOutputStream.close();
//update gallery
Intent intent = new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE);
uri = Uri.fromFile(file);
intent.setData(uri);
context.sendBroadcast(intent);
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
if (Build.VERSION.SDK_INT >= 24) {
try {
uri = Uri.parse(MediaStore.Images.Media.insertImage(context.getContentResolver(), file.getAbsolutePath(), fileName, null));
} catch (FileNotFoundException e) {
e.printStackTrace();
}
} else {
uri = Uri.fromFile(file);
}
return uri;
}
/**
* 获取一个 View 的缓存视图
* (前提是这个View已经渲染完成显示在页面上)
* @param view
* @return
*/
public static Bitmap getCacheBitmapFromView(View view) {
final boolean drawingCacheEnabled = true;
view.setDrawingCacheEnabled(drawingCacheEnabled);
view.buildDrawingCache(drawingCacheEnabled);
final Bitmap drawingCache = view.getDrawingCache();
drawingCache.setConfig(Bitmap.Config.ARGB_8888);
Bitmap bitmap;
if (drawingCache != null) {
bitmap = Bitmap.createBitmap(drawingCache);
bitmap.setConfig(Bitmap.Config.ARGB_8888);
view.setDrawingCacheEnabled(false);
} else {
bitmap = null;
}
return bitmap;
}
public static View loadView(Context context, int viewResId) {
if (context == null || viewResId <= 0) return null;
FrameLayout frameLayout = new FrameLayout(context);
View view = LayoutInflater.from(context).inflate(viewResId, frameLayout, false);
return view;
}
/**
* 从静态资源中,渲染并导出一张Bitmap图片
*
* @param context
* @param viewResId
* @return
*/
public static Bitmap loadBitmap(Context context, int viewResId) {
if (context == null || viewResId <= 0) return null;
return loadBitmap(loadView(context, viewResId));
}
public static Bitmap loadBitmap(View v) {
int measuredWidth = View.MeasureSpec.makeMeasureSpec(v.getLayoutParams().width, View.MeasureSpec.EXACTLY);
int measuredHeight = View.MeasureSpec.makeMeasureSpec(v.getLayoutParams().height, View.MeasureSpec.EXACTLY);
v.measure(measuredWidth, measuredHeight);
v.layout(0, 0, v.getMeasuredWidth(), v.getMeasuredHeight());
v.buildDrawingCache();
Bitmap bitmap = v.getDrawingCache();
return bitmap;
}
/**
* 加载的xml是ScrollView
*
* @param bgResId scrollView的背景
* @return
*/
public static Bitmap loadBitmapScrollView(View v, ScrollView scrollView,int bgResId) {
int measuredWidth = View.MeasureSpec.makeMeasureSpec(v.getLayoutParams().width, View.MeasureSpec.UNSPECIFIED);
int measuredHeight = View.MeasureSpec.makeMeasureSpec(v.getLayoutParams().height, View.MeasureSpec.UNSPECIFIED);
v.measure(measuredWidth, measuredHeight);
v.layout(0, 0, v.getMeasuredWidth(), v.getMeasuredHeight());
int h = 0;
Bitmap bitmap = null;
for (int i = 0; i < scrollView.getChildCount(); i++) {
h += scrollView.getChildAt(i).getHeight();
scrollView.getChildAt(i).setBackgroundResource(bgResId);
}
if(h <= 0){
return null;
}
bitmap = Bitmap.createBitmap(scrollView.getWidth(), h, Bitmap.Config.ARGB_8888);
final Canvas canvas = new Canvas(bitmap);
scrollView.draw(canvas);
return bitmap;
}
补充
1:背景透明(不黑色)
存图片的格式 = png。(jpg会丢弃背景透明的属性);
Bitmap的Config = ARGB_8888(别的会丢失透明度信息,如RGB_565)