Android下的图形处理
•Android系统下的图片都是32位的位图
•Android下加载图片的大小是和图片的分辨率有关系的,因为每个像素点都要被存入到内存,所以,往往我们看图片只有1M多,但是放到手机上就会OOM异常 out of Memery
Android图片操作技巧
1. 如何在Android中加载大图片防止OOM异常呢??
具体步骤如下:
1.获取图片的信息类
ExifInterface exif = new ExifInterface("图片地址");
2.获取图片的宽高信息
int width = exif.getAttributeInt(ExifInterface.TAG_IMAGE_WIDTH, 0);int height = exif.getAttributeInt(ExifInterface.TAG_IMAGE_LENGTH, 0);
3.获取到当前设备屏幕宽高
WindowManager wm = (WindowManager) getSystemService(WINDOW_SERVICE);int screenWidth = wm.getDefaultDisplay().getWidth();int screenHeight = wm.getDefaultDisplay().getHeight();
4.创建一个选项条件
Options opts = new Options();
5.根据图片宽高和屏幕宽高的比例,确定图片缩放的值,这里通常会优先选择值比较大的,也可以选两者之间的中间值,然后设置进去
opts.inSampleSize = ?; //设置采样率
6.把图片创建出来
Bitmap bitmap = BitmapFactory.decodeFile("图片路径", opts);
小结:
只要选择合适的采样率inSampleSize去加载图片就不会发生OOM异常了!
2. Android中图片变换的步骤
将图片加载到Android应用中之后,免不了会对图片进行一系列变换操作,比如:平移,缩放,旋转…
下面推荐一个常规的操作步骤:
1.加载图片到内存中,获取bitmap对象
Bitmap srcBitmap = BitmapFactory.decodeFile("图片路径");
2.创建一个空的bitmap对象,大小和原来bitmap一样
Bitmap copyedBitmap = Bitmap.createBitmap(srcBitmap.getWidth(), srcBitmap.getHeight(), srcBitmap.getConfig());
3.创建画板
Canvas canvas = new Canvas("空白的bitmap");
4.创建画笔
Paint paint = new Paint();
5.创建matrix 矩阵,我们可以利用这个矩阵来做到图片的缩放,平移等操作
Matrix matrix = new Matrix(); //1. 按比例扩大扩展缩放matrix.setScale(x轴比例, y轴比例);//2. 平移matrix.setTranslate(x轴偏移量, y轴偏移量);//3. 旋转matrix.setRotate(旋转角度, 围绕x轴点旋转, 围绕y轴点旋转);//4. 镜面效果matrix.setScale(-1, 1); //左右效果matrix.postTranslate(srcBitmap.getWidth(), 0);//如果想添加多个属性,后面的要用post,如果调用set会把前面的覆盖//5. 倒影效果matrix.setScale(1, -1); //上下效果matrix.postTranslate(0, srcBitmap.getHeight());
6.作画
canvas.drawBitmap(原图, matrix, paint);
步骤小结:
1. 获取图片资源
2. 创建一个空白的原图副本,大小和原图一样
3. 创建画板
4. 创建画笔
5. 创建Matrix矩阵,设置对图片需要做的操作
6. 将步骤5操作后的图片画到画板上
应用:
市面上有一款经典的小游戏,叫做”撕衣服”, 这款游戏的实现原理就是遵循以上步骤实现的!!
核心API是:
bitmap.setPixel(x坐标,y坐标,要设置的颜色);//根据xy轴设置bitmap对应像素点的颜色值为透明
实现原理:
1.利用相对布局放两张图片,上面一张图片正常穿着衣服,下面一张图片不穿衣服.2.通过以上API对上面一张图片进行操作,接触到的点全部变为透明,最终显示效果你懂得!!
<案例实现:美女撕衣服>
- 首先看看实现的效果(请保持平和的心态):
- 具体代码:
1.layout下的布局文件activity_main.xml
<LinearLayout 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" android:orientation="vertical" tools:context=".MainActivity" > <RelativeLayout android:layout_width="match_parent" android:layout_height="match_parent" > <ImageView android:id="@+id/iv_after" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerInParent="true" android:src="@drawable/after9" /> <ImageView android:id="@+id/iv_pre" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerInParent="true" /> RelativeLayout>LinearLayout>
2.res/drawable-hdpi目录下放置图片资源和音效文件
3.包com.yashiro.dragclose包里面的MainActivtiy.java文件
package com.yashiro.dragclose;import android.app.Activity;import android.graphics.Bitmap;import android.graphics.BitmapFactory;import android.graphics.Canvas;import android.graphics.Color;import android.graphics.Matrix;import android.graphics.Paint;import android.media.AudioManager;import android.media.SoundPool;import android.os.Bundle;import android.view.MotionEvent;import android.view.View;import android.view.View.OnTouchListener;import android.widget.ImageView;public class MainActivity extends Activity { private ImageView iv_pre; private Bitmap alterBitmap; private SoundPool soundPool; private int soundId; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); iv_pre=(ImageView) findViewById(R.id.iv_pre); //加载音效 soundPool=new SoundPool(1, AudioManager.STREAM_MUSIC, 0); //找到音效文件 soundId=soundPool.load(this, R.drawable.higirl, 1); //获取原图的路径 Bitmap bitmap=BitmapFactory.decodeResource(getResources(), R.drawable.pre9); //创建原图配置的空白副本 // 修改位图的配置信息(带有透明度alpha,兼容Android2.3低版本)Bitmap.Config.ARGB_8888 alterBitmap=Bitmap.createBitmap(bitmap.getWidth(),bitmap.getHeight(),bitmap.getConfig().ARGB_8888); //创建画板 final Canvas canvas=new Canvas(alterBitmap); //创建画笔 Paint paint=new Paint(); //将原图临摹到画板上 canvas.drawBitmap(bitmap, new Matrix(), paint); //将临摹后的图像放到界面上 iv_pre.setImageBitmap(alterBitmap); //设置图片的触摸事件. 触摸之处都是透明的 iv_pre.setOnTouchListener(new OnTouchListener() { //定义触摸到时的坐标 int x; int y; @Override public boolean onTouch(View v, MotionEvent event) { switch (event.getAction()) { case MotionEvent.ACTION_DOWN: case MotionEvent.ACTION_MOVE: //播放音效 soundPool.play(soundId, 1.0f, 1.0f, 0, 0, 1.1f); x=(int) event.getX(); y=(int) event.getY(); //触摸到的地方都是透明的. 用半径为10的原点操作 dragClose(x,y,10); break; case MotionEvent.ACTION_UP: break; } return true; //空间自己处理,事件结束就销毁 } /** * 撕衣服的方法 */ private void dragClose(int x,int y, int radius) { for(int i=-radius;i1;i++){ for (int j = -radius; j < radius+1; j++) { if (Math.sqrt(i*i+j*j)<=radius) { if ((x+i)0&&(y+j)0) { alterBitmap.setPixel(x+i, y+j, Color.TRANSPARENT); } } } } iv_pre.setImageBitmap(alterBitmap); } }); }}
案例小结:
1.严格按照Android图片变换的5步获取到图片资源并进行透明处理
2.利用iv_pre.setOnTouchListener(listener), 这个触摸监听事件,实现所触之处皆为透明.
3.最后将上层透明操作之后的图片设置到下层图片之上.
4.利用SoundPool实现触摸图片时发出音效的效果. 感觉很赞呀!!
以上,请各位大侠们指点,点拨~~~
更多相关文章
- android中android:src和android:background区别
- Android(安卓)Fresco图片加载库基础使用详解
- Android(安卓)Studio 之 Gradle与Project Structure详解
- Android(安卓)Studio中创建Kotlin For Android项目
- 【Android(安卓)4.0】Android(安卓)Icon Set的使用
- Android常见问题总结(五)
- Android(安卓)图像存储在SD卡ContentResolver
- Android开发——Android搜索框架(一)
- Android线程池使用