当前位置:   article > 正文

layout转Bitmap

layout 转bitmap

业务需求详细描述:最近产品说要在分享的商品图中添加一些其他图片和文字,然后拼接为一张图片,再分享到微信朋友圈,于是我就一脸懵逼了,但是没办法还是得做额!

然后整理了一下思路,主要有这么两条路线:

  1. 自己手动绘制。

  2. 将布局转换为图片。

很显然第一种方式是不合适的,无论是开发前还是开发后,成本都很大,所以果断选择了第二种方式。

一开始的时候,我没有经过大脑思考,果断的使用了getDrawingCache这个方法来解决这个业务需求,大致流程如下:

(1)创建需要显示成图片的布局,代码如下:

  1. <?xml version="1.0" encoding="utf-8"?>
  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
  3. android:id="@+id/picmontage_root"
  4. android:layout_width="match_parent"
  5. android:layout_height="match_parent"
  6. android:orientation="vertical">
  7. <RelativeLayout
  8. android:layout_width="match_parent"
  9. android:layout_height="wrap_content"
  10. android:layout_weight="1"
  11. android:background="@android:color/white">
  12. <ImageView
  13. android:id="@+id/img_shop"
  14. android:layout_width="match_parent"
  15. android:layout_height="match_parent"
  16. android:layout_margin="20dp" />
  17. <RelativeLayout
  18. android:layout_width="wrap_content"
  19. android:layout_height="wrap_content"
  20. android:layout_alignParentBottom="true"
  21. android:layout_centerHorizontal="true"
  22. android:layout_marginBottom="20dp">
  23. <ImageView
  24. android:id="@+id/img_price"
  25. android:layout_width="wrap_content"
  26. android:layout_height="wrap_content"/>
  27. <TextView
  28. android:id="@+id/txt_price"
  29. android:layout_width="wrap_content"
  30. android:layout_height="wrap_content"
  31. android:layout_centerInParent="true" />
  32. </RelativeLayout>
  33. </RelativeLayout>
  34. <LinearLayout
  35. android:layout_width="match_parent"
  36. android:layout_height="wrap_content"
  37. android:background="@android:color/white">
  38. <ImageView
  39. android:id="@+id/img_qrcode"
  40. android:layout_width="wrap_content"
  41. android:layout_height="wrap_content"
  42. android:layout_margin="20dp" />
  43. <LinearLayout
  44. android:layout_width="wrap_content"
  45. android:layout_height="wrap_content"
  46. android:layout_marginBottom="20dp"
  47. android:layout_marginRight="20dp"
  48. android:layout_marginTop="20dp"
  49. android:orientation="vertical">
  50. <TextView
  51. android:layout_width="wrap_content"
  52. android:layout_height="wrap_content"
  53. android:text="黄老五 提子味皇式烤芙条 300g 沙琪玛 休闲办公室零食...\n"
  54. android:textColor="@android:color/black" />
  55. <TextView
  56. android:layout_width="wrap_content"
  57. android:layout_height="wrap_content"
  58. android:text="长按识别二维码或扫一扫购买\n"
  59. android:textColor="@android:color/darker_gray" />
  60. <TextView
  61. android:layout_width="wrap_content"
  62. android:layout_height="wrap_content"
  63. android:text="From 萌店"
  64. android:textColor="@android:color/darker_gray" />
  65. </LinearLayout>
  66. </LinearLayout>
  67. </LinearLayout>

(2)设置图片和文字信息,这里为了方便,直接把文字放到了布局中,设置图片的代码如下所示:

  1. private void addLinearLayout() {
  2. view = View.inflate(this, R.layout.activity_picmontage, null);
  3. LinearLayout picmontageRoot = (LinearLayout) view.findViewById(R.id.picmontage_root);
  4. ImageView shopImg = (ImageView) view.findViewById(R.id.img_shop);
  5. ImageView priceImg = (ImageView) view.findViewById(R.id.img_price);
  6. TextView priceTxt = (TextView) view.findViewById(R.id.txt_price);
  7. ImageView qrcodeImg = (ImageView) view.findViewById(R.id.img_qrcode);
  8. shopImg.setImageResource(R.mipmap.shop);
  9. priceImg.setImageResource(R.mipmap.price);
  10. priceTxt.setText("$ 20.00");
  11. priceTxt.setTextSize(20);
  12. priceTxt.setTextColor(Color.WHITE);
  13. qrcodeImg.setImageResource(R.mipmap.qrcode);
  14. addViewContent.addView(view);
  15. }

(3)然后就可以将布局转换成图片了,代码如下所示:

  1. private void drawingCacheShow() {
  2. Bitmap cacheBitmap = convertViewToBitmap(addViewContent);
  3. //Bitmap cacheBitmap = getMagicDrawingCache(addViewContent);
  4. //addViewContent.removeView(view);
  5. if(cacheBitmap != null) {
  6. Bitmap newBitmap = Bitmap.createBitmap(cacheBitmap);
  7. if (newBitmap != null) {
  8. imgAddViewCache.setImageBitmap(newBitmap);
  9. } else {
  10. Log.i("123", "newBitmap=null");
  11. }
  12. } else {
  13. Log.i("123", "cacheBitmap=null");
  14. }
  15. }
  16. public static Bitmap convertViewToBitmap(View view){
  17. view.measure(
  18. View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED),
  19. View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED));
  20. view.layout(0, 0, view.getMeasuredWidth(), view.getMeasuredHeight());
  21. view.buildDrawingCache();
  22. Bitmap bitmap = view.getDrawingCache();
  23. if (bitmap != null) {
  24. Bitmap.Config cfg = bitmap.getConfig();
  25. Log.d("123", "----------------------- cache.getConfig() = " + cfg);
  26. }
  27. return bitmap;
  28. }

(4)然后发现图片不能正确显示,经过debug之后发现原来是图片过大的缘故,一脸懵逼,虽然使用了这样的压缩算法,但总是不尽如人意:

  1. private void addLinearLayout() {
  2. view = View.inflate(this, R.layout.activity_picmontage, null);
  3. LinearLayout picmontageRoot = (LinearLayout) view.findViewById(R.id.picmontage_root);
  4. ImageView shopImg = (ImageView) view.findViewById(R.id.img_shop);
  5. ImageView priceImg = (ImageView) view.findViewById(R.id.img_price);
  6. TextView priceTxt = (TextView) view.findViewById(R.id.txt_price);
  7. ImageView qrcodeImg = (ImageView) view.findViewById(R.id.img_qrcode);
  8. // 压缩shop
  9. Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.mipmap.shop);
  10. shopImg.setImageBitmap(resizeBm(bitmap, 600));
  11. priceImg.setImageResource(R.mipmap.price);
  12. priceTxt.setText("$ 20.00");
  13. priceTxt.setTextSize(20);
  14. priceTxt.setTextColor(Color.WHITE);
  15. qrcodeImg.setImageResource(R.mipmap.qrcode);
  16. addViewContent.addView(view);
  17. }
  18. private Bitmap resizeBm(Bitmap bitmap, int scaleWidth) {
  19. // 原始宽高
  20. float rawWidth = bitmap.getWidth();
  21. float rawHeight = bitmap.getHeight();
  22. // 新宽高
  23. float newWidth = 0;
  24. float newHeight = 0;
  25. // 将宽度缩放到scaleWidth
  26. if(rawWidth>scaleWidth) {
  27. newWidth = scaleWidth;
  28. newHeight = rawHeight*(scaleWidth/rawWidth);
  29. } else {
  30. newWidth = rawWidth;
  31. newHeight = rawHeight;
  32. }
  33. // 计算缩放比例
  34. float widthScale = newWidth/rawWidth;
  35. float heightScale = newHeight/rawHeight;
  36. Log.i("123", "widthScale="+widthScale+", heightScale="+heightScale);
  37. // 显示
  38. Matrix matrix = new Matrix();
  39. matrix.postScale(widthScale,heightScale);
  40. Bitmap resizeBmp = Bitmap.createBitmap(bitmap,0,0,bitmap.getWidth(),bitmap.getHeight(),matrix,true);
  41. return resizeBmp;
  42. }

之后有了大神的帮助,终于顿悟了,发现了神奇的方法:view.draw(canvas)。然后就很简单了:
这里的第1步和第2步流程与上面的1、2步流程一模一样,我们直接进入第3步,我先给出主界面中的布局:

  1. <?xml version="1.0" encoding="utf-8"?>
  2. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
  3. android:id="@+id/main_root"
  4. android:layout_width="match_parent"
  5. android:layout_height="match_parent"
  6. android:orientation="vertical">
  7. <ScrollView
  8. android:layout_width="match_parent"
  9. android:layout_height="wrap_content">
  10. <LinearLayout
  11. android:layout_width="match_parent"
  12. android:layout_height="wrap_content"
  13. android:orientation="vertical">
  14. <Button
  15. android:layout_width="match_parent"
  16. android:layout_height="wrap_content"
  17. android:onClick="showPic"
  18. android:text="显示绘制的图片" />
  19. <ImageView
  20. android:id="@+id/img"
  21. android:layout_width="wrap_content"
  22. android:layout_height="wrap_content" />
  23. <LinearLayout
  24. android:id="@+id/main_content"
  25. android:visibility="invisible"
  26. android:layout_width="match_parent"
  27. android:layout_height="wrap_content"
  28. android:orientation="vertical"/>
  29. </LinearLayout>
  30. </ScrollView>
  31. </LinearLayout>

(3)然后将该布局添加到主界面中,并设置为invisible,但不能设置为gone,否则不能成功渲染,同样不能生成图片了:

mainContent.addView(v);

(4)最后我们就可以在点击事件里面将布局生成图片了,代码如下:

  1. public void showPic(View view) {
  2. int width = picmontageRoot.getMeasuredWidth();
  3. int height = picmontageRoot.getMeasuredHeight();
  4. Bitmap b = Bitmap.createBitmap(width, height, Bitmap.Config.RGB_565);
  5. Canvas canvas = new Canvas(b);
  6. picmontageRoot.draw(canvas);
  7. img.setImageBitmap(b);
  8. }
声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/weixin_40725706/article/detail/262108
推荐阅读
相关标签
  

闽ICP备14008679号