关于View转化成bitmap保存成图片
产品今天说项目分享时要分享出一张 封面图片 + 几行文字 + 二维码图片 的图片。
思索了一下 封面图片和二维码图片让后台给接口得到地址, 主要还是找个方式得到一个包含这些内容的图片。于是就想能不能将View转化成bitmap对象
然后就走了一遍各个前辈的路 整理了下原理和思路。
根据产品的需求 我要实现的步骤 把所有需要的集合在一个View里 —— View转化成bitmap —— 分享出去(第三方分享bitmap对象)
接着搞个demo 实验一下
要转化的view 大致长这样
view_photo.xml
- <?xml version="1.0" encoding="utf-8"?>
- <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:layout_width="match_parent"
- android:layout_height="match_parent"
- android:orientation="vertical" >
- <ScrollView
- android:id="@+id/textView"
- android:layout_width="match_parent"
- android:layout_height="match_parent" >
- <LinearLayout
- android:layout_width="match_parent"
- android:layout_height="match_parent"
- android:orientation="vertical" >
- <!--封面图片 -->
- <ImageView
- android:layout_width="400dp"
- android:layout_height="400dp"
- android:background="@drawable/ic_launcher"
- android:layout_gravity="center_horizontal" />
- <TextView
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:text="文字 文字"
- android:layout_gravity="center_horizontal" />
- <Button
- android:id="@+id/button"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:text="假装是二维码图片"
- android:layout_gravity="center_horizontal" />
- </LinearLayout>
- </ScrollView>
- </LinearLayout>
最关键的View转bitmap
好像是有两种方法
- view.setDrawingCacheEnabled(true);
- view.buildDrawingCache(); //启用DrawingCache并创建位图
- Bitmap bitmap = Bitmap.createBitmap(view.getDrawingCache()); //创建一个DrawingCache的拷贝,因为DrawingCache得到的位图在禁用后会被回收
- view.setDrawingCacheEnabled(false); //禁用DrawingCahce否则会影响性能
- private Bitmap loadBitmapFromView(View v) {
- int w = v.getWidth();
- int h = v.getHeight();
- Bitmap bmp = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_8888);
- Canvas c = new Canvas(bmp);
- c.drawColor(Color.WHITE);
- /** 如果不设置canvas画布为白色,则生成透明 */
- v.layout(0, 0, w, h);
- v.draw(c);
- return bmp;
- }
- DisplayMetrics metric = new DisplayMetrics();
- getWindowManager().getDefaultDisplay().getMetrics(metric);
- int width = metric.widthPixels; // 屏幕宽度(像素)
- int height = metric.heightPixels; // 屏幕高度(像素)
- View view = LayoutInflater.from(this).inflate(R.layout.view_photo, null, false);
- layoutView(view, width, height);//去到指定view大小的函数
- //然后View和其内部的子View都具有了实际大小,也就是完成了布局,相当与添加到了界面上。接着就可以创建位图并在上面绘制了:
- private void layoutView(View v, int width, int height) {
- // 指定整个View的大小 参数是左上角 和右下角的坐标
- v.layout(0, 0, width, height);
- int measuredWidth = View.MeasureSpec.makeMeasureSpec(width, View.MeasureSpec.EXACTLY);
- int measuredHeight = View.MeasureSpec.makeMeasureSpec(height, View.MeasureSpec.AT_MOST);
- /** 当然,measure完后,并不会实际改变View的尺寸,需要调用View.layout方法去进行布局。
- * 按示例调用layout函数后,View的大小将会变成你想要设置成的大小。
- */
- v.measure(measuredWidth, measuredHeight);
- v.layout(0, 0, v.getMeasuredWidth(), v.getMeasuredHeight());
- }
在int measuredHeight = View.MeasureSpec.makeMeasureSpec(height, View.MeasureSpec.AT_MOST);
- <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:tools="http://schemas.android.com/tools"
- android:layout_width="match_parent"
- android:layout_height="match_parent"
- tools:context="com.example.aa.MainActivity" >
- <Button
- android:id="@+id/button"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:text=" button" />
- <ImageView
- android:id="@+id/aaa"
- android:layout_below="@+id/button"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- />
- </RelativeLayout>
view_photo.xml 在上面
- public class MainActivity extends Activity {
- ImageView aaa ;
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- setContentView(R.layout.activity_main);
- DisplayMetrics metric = new DisplayMetrics();
- getWindowManager().getDefaultDisplay().getMetrics(metric);
- int width = metric.widthPixels; // 屏幕宽度(像素)
- int height = metric.heightPixels; // 屏幕高度(像素)
- View view = LayoutInflater.from(this).inflate(R.layout.view_photo, null, false);
- layoutView(view, width, height);
- final ScrollView tv = (ScrollView) view.findViewById(R.id.textView);
- aaa = (ImageView) findViewById(R.id.aaa);
- final Runnable runnable = new Runnable() {
- @Override
- public void run() {
- viewSaveToImage(tv);
- }
- };
- Button button = (Button) findViewById(R.id.button);
- button.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- new Handler().post(runnable);
- }
- });
- }
- //然后View和其内部的子View都具有了实际大小,也就是完成了布局,相当与添加到了界面上。接着就可以创建位图并在上面绘制了:
- private void layoutView(View v, int width, int height) {
- // 整个View的大小 参数是左上角 和右下角的坐标
- v.layout(0, 0, width, height);
- int measuredWidth = View.MeasureSpec.makeMeasureSpec(width, View.MeasureSpec.EXACTLY);
- int measuredHeight = View.MeasureSpec.makeMeasureSpec(10000, View.MeasureSpec.AT_MOST);
- /** 当然,measure完后,并不会实际改变View的尺寸,需要调用View.layout方法去进行布局。
- * 按示例调用layout函数后,View的大小将会变成你想要设置成的大小。
- */
- v.measure(measuredWidth, measuredHeight);
- v.layout(0, 0, v.getMeasuredWidth(), v.getMeasuredHeight());
- }
- public void viewSaveToImage(View view) {
- Log.e("ssh","a");
- /**
- * View组件显示的内容可以通过cache机制保存为bitmap
- * 我们要获取它的cache先要通过setDrawingCacheEnable方法把cache开启,
- * 然后再调用getDrawingCache方法就可 以获得view的cache图片了
- * 。buildDrawingCache方法可以不用调用,因为调用getDrawingCache方法时,
- * 若果 cache没有建立,系统会自动调用buildDrawingCache方法生成cache。
- * 若果要更新cache, 必须要调用destoryDrawingCache方法把旧的cache销毁,才能建立新的。
- */
- // view.setDrawingCacheEnabled(true);
- // view.setDrawingCacheQuality(View.DRAWING_CACHE_QUALITY_HIGH);
- //设置绘制缓存背景颜色
- // view.setDrawingCacheBackgroundColor(Color.WHITE);
- // 把一个View转换成图片
- Bitmap cachebmp = loadBitmapFromView(view);
- aaa.setImageBitmap(cachebmp);//直接展示转化的bitmap
- //保存在本地 产品还没决定要不要保存在本地
- FileOutputStream fos;
- try {
- // 判断手机设备是否有SD卡
- boolean isHasSDCard = Environment.getExternalStorageState().equals(
- android.os.Environment.MEDIA_MOUNTED);
- if (isHasSDCard) {
- // SD卡根目录
- File sdRoot = Environment.getExternalStorageDirectory();
- Log.e("ssh",sdRoot.toString());
- File file = new File(sdRoot, "test.png");
- fos = new FileOutputStream(file);
- } else
- throw new Exception("创建文件失败!");
- //压缩图片 30 是压缩率,表示压缩70%; 如果不压缩是100,表示压缩率为0
- cachebmp.compress(Bitmap.CompressFormat.PNG, 90, fos);
- fos.flush();
- fos.close();
- } catch (Exception e) {
- e.printStackTrace();
- }
- view.destroyDrawingCache();
- }
- private Bitmap loadBitmapFromView(View v) {
- int w = v.getWidth();
- int h = v.getHeight();
- Bitmap bmp = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_8888);
- Canvas c = new Canvas(bmp);
- c.drawColor(Color.WHITE);
- /** 如果不设置canvas画布为白色,则生成透明 */
- v.layout(0, 0, w, h);
- v.draw(c);
- return bmp;
- }
- }
demo转化成结果的bitmap和图片
关于View转化成bitmap保存成图片的更多相关文章
- BitmapUtil【缩放bitmap以及将bitmap保存成图片到SD卡中】
版权声明:本文为HaiyuKing原创文章,转载请注明出处! 前言 用于缩放bitmap以及将bitmap保存成图片到SD卡中 效果图 代码分析 bitmapZoomByHeight(Bitmap s ...
- 如何把Excel中的单元格等对象保存成图片
对于Excel中的很多对象,比如单元格(Cell),图形(shape),图表(chart)等等,有时需要将它们保存成一张图片.就像截图一样. 最近做一个Excel相关的项目,项目中遇到一个很变态的需求 ...
- OpenGL中的深度、深度缓存、深度测试及保存成图片
1.深度 所谓深度,就是在openGL坐标系中,像素点Z坐标距离摄像机的距离.摄像机可能放在坐标系的任何位置,那么,就不能简单的说Z数值越大或越小,就是越靠近摄像机. 2.深度缓冲区 深度缓冲区原理就 ...
- javacpp-opencv图像处理之1:实时视频添加文字水印并截取视频图像保存成图片,实现文字水印的字体、位置、大小、粗度、翻转、平滑等操作
欢迎大家积极开心的加入讨论群 群号:371249677 (点击这里进群) javaCV图像处理系列: javaCV图像处理之1:实时视频添加文字水印并截取视频图像保存成图片,实现文字水印的字体.位置. ...
- 修改css的(屏蔽)overflow: hidden;实现浏览器能把网页全图保存成图片
摘要: 1.项目需要,需要对网页内容“下载”保存成全图片 2.QQ浏览器等主流浏览器都支持这种下载保存功能 3.项目需要场景:编写好的项目维护文档,放在服务器上.如果是txt不能带图片可视化,如果wo ...
- Java 将 PPT 形状(表格、文本框、心形、图表等)保存成图片
MS PowerPoint中的表格.文本框.心形.图表.图片等均可以称为形状,将这些形状保存成图片,便可分类储存,方便日后查找,再利用. 本文将介绍如何使用 Spire.Presentation fo ...
- 如何实现批量截取整个网页完整长截图,批量将网页保存成图片web2pic/webshot/screencapture/html2picture
如何实现批量截取整个网页完整长截图,批量将网页保存成图片web2pic/webshot/screencapture [困扰?疑问?]: 您是否正受到:如何将网页保存为图片的困扰?网页很高很长截图截不全 ...
- c# 将byte数组保存成图片
将byte数组保存成图片: 方式一:System.IO.File.WriteAllBytes(@"c:\test.jpg", bytes); 方式二:MemoryStream ms ...
- MVC下 把数据库中的byte[]值保存成图片,并显示在view页面
MVC下 把数据库中的byte[]值转成图片,并显示在view页面 controller中的action方法 //显示图片[AllowAnonymous]public ActionResult Sho ...
随机推荐
- HDU - 5572 An Easy Physics Problem (计算几何模板)
[题目概述] On an infinite smooth table, there's a big round fixed cylinder and a little ball whose volum ...
- Java中获取项目根路径和类加载路径的7种方法
引言 在web项目开发过程中,可能会经常遇到要获取项目根路径的情况,那接下来我就总结一下,java中获取项目根路径的7种方法,主要是通过thisClass和System,线程和request等方法. ...
- 《ASP.NET》数据绑定—DataList实践篇
上篇文章大概讲了DataList的一些基础知识,掌握这些知识在将来的应用中起到非常大的作用,如今我们就開始讲上篇文章中说的基础知识做一个小样例. 首先,我机子的数据库中有一张person表.例如以下图 ...
- leetcode笔记:Contains Duplicate
一. 题目描写叙述 Given an array of integers, find if the array contains any duplicates. Your function shoul ...
- AnimalWindow使用,实现界面动态消失
http://m.blog.csdn.net/blog/shufac/24932279 http://blog.sina.com.cn/s/blog_455245fc01000a42.html Ani ...
- JavaScript 刚開始学习的人应知的 24 条最佳实践
原文:24 JavaScript Best Practices for Beginners (注:阅读原文的时候没有注意公布日期,认为不错就翻译了,翻译到 JSON.parse 那一节认为有点不正确路 ...
- UBUntu 软件 源配置方法
近期公司产品须要添加一个功能,就是版本号自己主动更新.使用apt-get 实现. apt-get 软件源配置的方法,參见本人资源里的共享.以下是代码中作为升级的一部分. FILE *fp; ...
- 【hdu】Mayor's posters(线段树区间问题)
须要离散化处理,线段树的区间改动问题. 须要注意的就是离散化的时候,由于给的数字是一段单位长度,所以须要特殊处理(由于线段的覆盖和点的覆盖是不一样的) 比方:(1,10)(1,4) (6,10) 离散 ...
- mvc4中 @Url.Action 如何读取javascript变量的值
js中 function Search() { var businessDate = GetSelectedBusinessDate("#businessYear", ...
- 键盘HOOK显示按键信息
GetKeyNameText(MapVirtualKey(iKeyValue,0)<<16));//iKeyValue 的值为 VK_ESCAPE 等 LRESULT CALLBACK L ...