图片涂鸦马赛克
之前写的项目了,因为有小伙伴问到处理后如何保存的问题我把方法加到代码里了。(最近项目时间紧未经测试>o<)
最近项目里用到了马赛克效果,就是对手指划过的区域打码。效果如下:

关于图片模糊其实我是采用偷懒的做法,先缩小后放大....,代码很少就不解释了。

布局中使用:

 
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:id="@+id/activity_main" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" android:paddingBottom="@dimen/activity_vertical_margin" android:paddingLeft="@dimen/activity_horizontal_margin" android:paddingRight="@dimen/activity_horizontal_margin" android:paddingTop="@dimen/activity_vertical_margin"> <你的路径.MosaicView android:id="@+id/mosaicView" android:layout_width="match_parent" android:layout_height="match_parent" android:src="@mipmap/renwu"/> </LinearLayout>

MosaicView代码:

package 你的包名;import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.DiscretePathEffect;
import android.graphics.Matrix;
import android.graphics.Paint;
import android.graphics.Path;
import android.graphics.PorterDuff;
import android.graphics.PorterDuffXfermode;
import android.graphics.RectF;
import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.widget.ImageView;import java.util.ArrayList;/*** Created on 2017/8/3.*/public class MosaicView extends ImageView {private Bitmap mMosaicBmp;private Paint mPaint;private ArrayList<DrawPath> mPaths;private DrawPath mLastPath;private RectF mBitmapRectF;private PorterDuffXfermode mDuffXfermode;private float tempX,tempY;private final float mTargetWidth = 20.0f;public MosaicView(Context context) {super(context);init();}public MosaicView(Context context, AttributeSet attrs) {super(context, attrs);init();}public MosaicView(Context context, AttributeSet attrs, int defStyleAttr) {super(context, attrs, defStyleAttr);init();}private void init() {mPaint = new Paint();mPaint.setAntiAlias(true);mPaint.setDither(true);mPaint.setStyle(Paint.Style.STROKE);//描边mPaint.setTextAlign(Paint.Align.CENTER);//居中mPaint.setStrokeCap(Paint.Cap.ROUND);//圆角mPaint.setStrokeJoin(Paint.Join.ROUND);//拐点圆角//正常效果mPaint.setStrokeWidth(32);
//        //抖动效果
//        mPaint.setStrokeWidth(2f);
//        mPaint.setPathEffect(new DiscretePathEffect(0.35f, 40));//mPaths = new ArrayList<>();mBitmapRectF = new RectF();//叠加效果mDuffXfermode = new PorterDuffXfermode(PorterDuff.Mode.SRC_IN);}/*** 清除操作* */public void clear() {mPaths.clear();invalidate();}/*** 撤销* */public void undo() {int size  = mPaths.size();if (size > 0) {mPaths.remove(size-1);invalidate();}}private float mScale;/*** 获取处理后的图片* */public Bitmap getImageBitmap() {Bitmap bitmap;if ((getDrawable() instanceof BitmapDrawable)) {BitmapDrawable drawable = (BitmapDrawable) getDrawable();bitmap = drawable.getBitmap().copy(Bitmap.Config.ARGB_8888, true);} else {bitmap = Bitmap.createBitmap(getWidth(), getHeight(), Bitmap.Config.ARGB_8888);}int width = bitmap.getWidth();mScale = (float) width / mMosaicBmp.getWidth();Canvas canvas = new Canvas(bitmap);canvas.save();canvas.scale(mScale, mScale);drawOnLayer(canvas);canvas.restore();return bitmap;}private int drawOnLayer(Canvas canvas) {int canvasWidth = canvas.getWidth();int canvasHeight = canvas.getHeight();//新图层int layerId;layerId = canvas.saveLayer(0, 0, canvasWidth/mScale, canvasHeight/mScale, null, Canvas.ALL_SAVE_FLAG);canvas.save();canvas.translate(-mBitmapRectF.left, -mBitmapRectF.top);for (DrawPath drawPath : mPaths) {//滑过的区域drawPath.draw(canvas);}mPaint.setXfermode(mDuffXfermode);//设置叠加模式canvas.drawBitmap(mMosaicBmp, mBitmapRectF.left, mBitmapRectF.top, mPaint);//画出重叠区域canvas.restore();mPaint.setXfermode(null);return layerId;}@Overridepublic void setImageDrawable(Drawable drawable) {super.setImageDrawable(drawable);if (drawable != null && drawable instanceof BitmapDrawable) {scaleBitmap(((BitmapDrawable) drawable).getBitmap());}}@Overridepublic void setImageBitmap(Bitmap bm) {super.setImageBitmap(bm);scaleBitmap(bm);}// 生成小图private void scaleBitmap(Bitmap bm) {int width = bm.getWidth();float scale = mTargetWidth / width;Matrix matrix = new Matrix();matrix.postScale(scale, scale);mMosaicBmp = Bitmap.createBitmap(bm, 0, 0, width, bm.getHeight(),matrix, true);}/*** 得到图片展示区域*/private RectF getBitmapRect() {final Drawable drawable = getDrawable();if (drawable == null) {return new RectF();}// Get image matrix values and place them in an array.final float[] matrixValues = new float[9];getImageMatrix().getValues(matrixValues);// Extract the scale and translation values from the matrix.final float scaleX = matrixValues[Matrix.MSCALE_X];final float scaleY = matrixValues[Matrix.MSCALE_Y];final float transX = matrixValues[Matrix.MTRANS_X] + getPaddingLeft();final float transY = matrixValues[Matrix.MTRANS_Y] + getPaddingTop();// Get the width and height of the original bitmap.final int drawableIntrinsicWidth = drawable.getIntrinsicWidth();final int drawableIntrinsicHeight = drawable.getIntrinsicHeight();// Calculate the dimensions as seen on screen.final int drawableDisplayWidth = Math.round(drawableIntrinsicWidth * scaleX);final int drawableDisplayHeight = Math.round(drawableIntrinsicHeight * scaleY);// Get the Rect of the displayed image within the ImageView.final float left = Math.max(transX, 0);final float top = Math.max(transY, 0);final float right = Math.min(left + drawableDisplayWidth, getWidth());final float bottom = Math.min(top + drawableDisplayHeight, getHeight());return new RectF(left, top, right, bottom);}@Overrideprotected void onLayout(boolean changed, int left, int top, int right, int bottom) {super.onLayout(changed, left, top, right, bottom);if (mMosaicBmp != null) {mBitmapRectF = getBitmapRect();Matrix mosaicMatrix = new Matrix();mosaicMatrix.setTranslate(mBitmapRectF.left, mBitmapRectF.top);float scaleX = (mBitmapRectF.right - mBitmapRectF.left) / mMosaicBmp.getWidth();float scaleY = (mBitmapRectF.bottom - mBitmapRectF.top) / mMosaicBmp.getHeight();mosaicMatrix.postScale(scaleX, scaleY);// 生成整张模糊图片mMosaicBmp = Bitmap.createBitmap(mMosaicBmp, 0, 0, mMosaicBmp.getWidth(), mMosaicBmp.getHeight(),mosaicMatrix, true);}}@Overrideprotected void onDraw(Canvas canvas) {super.onDraw(canvas);if(!mPaths.isEmpty()){int canvasWidth = canvas.getWidth();int canvasHeight = canvas.getHeight();//新图层int layerId = canvas.saveLayer(0, 0, canvasWidth, canvasHeight, null, Canvas.ALL_SAVE_FLAG);canvas.clipRect(mBitmapRectF); //限定区域for(DrawPath drawPath:mPaths){//滑过的区域drawPath.draw(canvas);}mPaint.setXfermode(mDuffXfermode);//设置叠加模式canvas.drawBitmap(mMosaicBmp, mBitmapRectF.left, mBitmapRectF.top, mPaint);//画出重叠区域mPaint.setXfermode(null);canvas.restoreToCount(layerId);}}@Overridepublic boolean onTouchEvent(MotionEvent event) {switch (event.getAction()){case MotionEvent.ACTION_DOWN:float downX = event.getX();float downY = event.getY();mLastPath = new DrawPath();//每次手指下去都是一条新的路径mLastPath.moveTo(downX,downY);mPaths.add(mLastPath);invalidate();tempX = downX;tempY = downY;break;case MotionEvent.ACTION_MOVE:float moveX = event.getX();float moveY = event.getY();if (Math.abs(moveX - tempX) > 5 || Math.abs(moveY - tempY) > 5) {mLastPath.quadTo(tempX,tempY,moveX,moveY);invalidate();}tempX = moveX;tempY = moveY;break;case MotionEvent.ACTION_UP:mLastPath.up();break;}return true;}/*** 封装一条路径*/class  DrawPath{Path path;float downX;float downY;boolean quaded;DrawPath() {path = new Path();}void moveTo(float x, float y) {downX = x;downY = y;path.moveTo(x, y);}void quadTo(float x1, float y1, float x2, float y2) {quaded = true;path.quadTo(x1, y1, x2, y2);}void up() {if (!quaded) {//画点path.lineTo(downX, downY+0.1f);invalidate();}}void draw(Canvas canvas) {if(path!=null){canvas.drawPath(path, mPaint);}}}
}

Android马赛克效果MosaicView相关推荐

  1. 安卓马赛克view_Android马赛克效果MosaicView

    图片涂鸦马赛克 之前写的项目了,因为有小伙伴问到处理后如何保存的问题我把方法加到代码里了.(最近项目时间紧未经测试>o 最近项目里用到了马赛克效果,就是对手指划过的区域打码.效果如下: 关于图片 ...

  2. Android图片编辑马赛克效果

    1:activity代码 public class MosaicActivity extends Activity implements View.OnClickListener {private D ...

  3. android 马赛克 代码,Android_Android 马赛克(Mosaics)效果,前几天看见开源项目效果好赞 - phpStudy...

    Android 马赛克(Mosaics)效果 前几天看见开源项目效果好赞,看了下代码,实现大致就是在原界面之上覆盖一成自定义的View,获取到点击的那个View的内容(Bitmap),然后在覆盖的那个 ...

  4. Java中实现六种图像处理的效果(灰度化、马赛克效果、去背景实现、珠纹化实现、黑白版画效果、油画效果)

    ** Java中实现六种图像处理的效果(灰度化.马赛克效果.去背景实现.珠纹化实现.黑白版画效果.油画效果) ** 本文的编程的思想: 先将实现这六种效果的方法写入一个名为pic_performanc ...

  5. Java中的实现马赛克效果以及灰度效果----整张图片

    ** Java中的实现马赛克效果以及灰度效果-----整张图片 ** 实现该效果的思路: 我们知道图片是由一个一个的像素组成的,比如一张图片的分辨率为800 * 800,则它是由800个像素 * 80 ...

  6. PHP实现图片马赛克效果

    原理: 对图片中选定区域的每一像素,增加若干宽度及高度,来生成矩型.而每一像素的矩型重叠在一起,就形成了马赛克效果.本例使用GD库的imagecolorat获取像素颜色,使用imagefilledre ...

  7. Android 抽屉效果Demo

    2019独角兽企业重金招聘Python工程师标准>>> Android 抽屉效果Demo. 转载:http://www.adobex.com/android/source/detai ...

  8. python图片马赛克_Python实现PS滤镜中马赛克效果示例

    本文实例讲述了Python实现PS滤镜中马赛克效果.分享给大家供大家参考,具体如下: 这里利用 Python 实现PS 滤镜中的马赛克效果,具体的算法原理和效果可以参考附录说明,Python示例代码如 ...

  9. PS制作马赛克效果、炫酷光线

    马赛克效果 1.打开人物素材,新建图层,创建一个渐变色 2.混合模式改为叠加,盖印图层Ctrl+shift+Alt+E 3.双击图层,混合模式,取消勾选GB通道 4.Ctrl+J复制图层,然后盖印图层 ...

最新文章

  1. 用Jquery自己开发个代阴影的对话框吧!
  2. 中断(interrupted()、isInterrupted())、Executor的中断
  3. mysql查询男生基本情况_MySQL数据库技术与应用:数据查询
  4. 博弈论 —— matlab
  5. 启明星会议室预定系统 helpdesk系统等 登陆失败的问题与解决方法
  6. bind函数:给对象绑定方法。
  7. 大厂用的分库分表方案和demo源码,都在这里了!
  8. 项目--Asp.net全局变量的设置和读(web.config 和 Gloab)
  9. 德裔美国Delphi程序员霍尔格-弗里克博士访谈
  10. Solaris系统环境变量声明方法
  11. 系列:关于TXT的文件格式
  12. 【pyhton数据预处理】利用pandas模块找出两excel表格差异并进行字段值比较
  13. 分块矩阵在计算机有哪些应用,分块矩阵及其应用
  14. 从游戏中学习产品设计05:反馈篇
  15. 加速磁盘碎片整理的六大技巧
  16. python程序员面试宝典:12个Python程序员面试必备问题与答案
  17. 山东大学项目实训——解决微信小程序无法获得用户信息问题
  18. QCC51XX---固件OTA升级指南
  19. 2.(cesium篇)cesium加载接入百度地图
  20. 2022云南师范大学333教育综合考研真题

热门文章

  1. 自助式BI节省步步高1000张报表,80万人力,充分为业务赋能
  2. Shell脚本中的return,exit 0,以及 父进程获取子进程的变量
  3. iPhone手机记事用什么软件哪个好?
  4. SQL注入之——宽字节与二阶注入
  5. iOS 开源项目介绍之UI篇
  6. 代码随想录打卡第二天
  7. 蝶形、同址和变址计算
  8. zCrud组件(vue2封装增删查改到一个组件)
  9. C# DataTable(System.Data)
  10. 互相关性定理(Cross-Correlation Theorem)与卷积定理(Convolution Theorem)