regin,clip Android
canvas 还提供裁剪的功能。
裁剪功能由Canvas提供的一系列的clip...方法 和quickReject方法来完成。 前面已经提到,真正提供可绘制区域的是Canvas内部的mutable bitmap。 Canvas更像是一个图层,我们只能在这上面的图层来绘制东西。
1、首先介绍Region类
Region,中文意思即区域的意思,它表示的是canvas图层上的某一块封闭的区域。
- /**构造方法*/
- public Region() //创建一个空的区域
- public Region(Region region) //拷贝一个region的范围
- public Region(Rect r) //创建一个矩形的区域
- public Region(int left, int top, int right, int bottom) //创建一个矩形的区域
- /**一系列set方法,这些set方法,和上面构造方法形式差不多*/
- public void setEmpty() {
- public boolean set(Region region)
- public boolean set(Rect r)
- public boolean set(int left, int top, int right, int bottom)
- /*往一个Region中添加一个Path只有这种方法,参数clip代表这个整个Region的区域,在在里面裁剪出path范围的区域*/
- public boolean setPath(Path path, Region clip) //用指定的Path和裁剪范围构建一个区域
- /**几个判断方法*/
- public native boolean isEmpty();//判断该区域是否为空
- public native boolean isRect(); //是否是一个矩阵
- public native boolean isComplex();//是否是多个矩阵组合
- /**一系列的getBound方法,返回一个Region的边界*/
- public Rect getBounds()
- public boolean getBounds(Rect r)
- public Path getBoundaryPath()
- public boolean getBoundaryPath(Path path)
- /**一系列的判断是否包含某点 和是否相交*/
- public native boolean contains(int x, int y);//是否包含某点
- public boolean quickContains(Rect r) //是否包含某矩阵
- public native boolean quickContains(int left, int top, int right,
- int bottom) //是否没有包含某矩阵
- public boolean quickReject(Rect r) //是否没和该矩阵相交
- public native boolean quickReject(int left, int top, int right, int bottom); //是否没和该矩阵相交
- public native boolean quickReject(Region rgn); //是否没和该矩阵相交
- /**几个平移变换的方法*/
- public void translate(int dx, int dy)
- public native void translate(int dx, int dy, Region dst);
- public void scale(float scale) //hide
- public native void scale(float scale, Region dst);//hide
- /**一系列组合的方法*/
- public final boolean union(Rect r)
- public boolean op(Rect r, Op op) {
- public boolean op(int left, int top, int right, int bottom, Op op)
- public boolean op(Region region, Op op)
- public boolean op(Rect rect, Region region, Op op)
上面几乎是Region的所有API,很好理解,主要说明一下最后的一组关于Region组合的方式。组合即当前的Region和另外的一个Region组合,可以用不同的Op方式来进行组合。
Op是一个枚举,定义在Region类中。
- 假设用region1 去组合region2
- public enum Op {
- DIFFERENCE(0), //最终区域为region1 与 region2不同的区域
- INTERSECT(1), // 最终区域为region1 与 region2相交的区域
- UNION(2), //最终区域为region1 与 region2组合一起的区域
- XOR(3), //最终区域为region1 与 region2相交之外的区域
- REVERSE_DIFFERENCE(4), //最终区域为region2 与 region1不同的区域
- REPLACE(5); //最终区域为为region2的区域
- }
ApiDemo中已经提供了一个关于组合的例子,在最后面给出。
Android还提供了一个RegionIterator来对Region中的所有矩阵进行迭代,可以使用该类,获得某个Region的所有矩阵。比较简单。
2、什么是裁剪
裁剪Clip,即裁剪Canvas图层,我们绘制的东西,只能在裁剪区域的范围能才能显示出来。
- @Override
- protected void onDraw(Canvas canvas) {
- Paint paint=new Paint();
- canvas.save();
- canvas.clipRect(new Rect(100,100,300,300));
- canvas.drawColor(Color.BLUE);//裁剪区域的rect变为蓝色
- canvas.drawRect(new Rect(0,0,100,100), paint);//在裁剪的区域之外,不能显示
- canvas.drawCircle(150,150, 50, paint);//在裁剪区域之内,能显示
- canvas.restore();
- }
裁剪并不像Matrix变换,它相对于mutable bitmap的坐标是不会改变的。所以超出裁剪区域的绘制不会被显示
3、裁剪的保存和回滚
在之前已经提到了,canvas.save()和canvas.restore()不仅对matrix有效,同样对clip有类似的效果。
4、裁剪的方式
Canvas提供了三种裁剪的方式:
1、最基本的clipRect,裁剪一个矩形
2、clipPath,裁剪Path包括的范围,Path所包括的范围不是空的才有效。
3、clipRegion。
Region在前面已经介绍过了,其实Region就是一个对区域组合的一个封装。但是它和clipRect和clipPath的最大区别在于下面:
- Note that unlike
- clipRect() and clipPath() which transform their arguments by the
- current matrix, clipRegion() assumes its argument is already in the
- coordinate system of the current layer's bitmap, and so not
- transformation is performed.
与clipRect和clipPath要使用当前的matrix进行变换不同。clipRegion不会进行转换。也就是说canvas的matrix对clipRegion没有影响。
- Paint paint=new Paint();
- canvas.scale(0.5f, 0.5f);
- canvas.save();
- canvas.clipRect(new Rect(100,100,200,200));//裁剪区域实际大小为50*50
- canvas.drawColor(Color.RED);
- canvas.restore();
- canvas.drawRect(new Rect(0,0,100,100), paint);//矩形实际大小为50*50
- canvas.clipRegion(new Region(new Rect(300,300,400,400)));//裁剪区域实际大小为100*100
- canvas.drawColor(Color.BLACK);
可以看到,Canvas的变换 对clipRegion没有作用。
ApiDemo中关于组合的例子:
- public class Clipping extends Activity {
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- setContentView(new SampleView(this));
- }
- private static class SampleView extends View {
- private Paint mPaint;
- private Path mPath;
- public SampleView(Context context) {
- super(context);
- setFocusable(true);
- mPaint = new Paint();
- mPaint.setAntiAlias(true);
- mPaint.setStrokeWidth(6);
- mPaint.setTextSize(16);
- mPaint.setTextAlign(Paint.Align.RIGHT);
- mPath = new Path();
- }
- private void drawScene(Canvas canvas) {
- canvas.clipRect(0, 0, 100, 100);
- canvas.drawColor(Color.WHITE);
- mPaint.setColor(Color.RED);
- canvas.drawLine(0, 0, 100, 100, mPaint);
- mPaint.setColor(Color.GREEN);
- canvas.drawCircle(30, 70, 30, mPaint);
- mPaint.setColor(Color.BLUE);
- canvas.drawText("Clipping", 100, 30, mPaint);
- }
- @Override
- protected void onDraw(Canvas canvas) {
- canvas.drawColor(Color.GRAY);
- canvas.save();
- canvas.translate(10, 10);
- drawScene(canvas);
- canvas.restore();
- canvas.save();
- canvas.translate(160, 10);
- canvas.clipRect(10, 10, 90, 90);
- canvas.clipRect(30, 30, 70, 70, Region.Op.DIFFERENCE);
- drawScene(canvas);
- canvas.restore();
- canvas.save();
- canvas.translate(10, 160);
- mPath.reset();
- canvas.clipPath(mPath); // makes the clip empty
- mPath.addCircle(50, 50, 50, Path.Direction.CCW);
- canvas.clipPath(mPath, Region.Op.REPLACE);
- drawScene(canvas);
- canvas.restore();
- canvas.save();
- canvas.translate(160, 160);
- canvas.clipRect(0, 0, 60, 60);
- canvas.clipRect(40, 40, 100, 100, Region.Op.UNION);
- drawScene(canvas);
- canvas.restore();
- canvas.save();
- canvas.translate(10, 310);
- canvas.clipRect(0, 0, 60, 60);
- canvas.clipRect(40, 40, 100, 100, Region.Op.XOR);
- drawScene(canvas);
- canvas.restore();
- canvas.save();
- canvas.translate(160, 310);
- canvas.clipRect(0, 0, 60, 60);
- canvas.clipRect(40, 40, 100, 100, Region.Op.REVERSE_DIFFERENCE);
- drawScene(canvas);
- canvas.restore();
- }
- }
- }
效果图:
5、裁剪的一个小用处
- public class ClippingRegion extends Activity {
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- setContentView(new SampleView(this));
- }
- private class SampleView extends View {
- private Bitmap mBitmap;
- private int limitLength = 0;
- private int width;
- private int heigth;
- private static final int CLIP_HEIGHT = 30;
- private boolean status = HIDE;//显示还是隐藏的状态,最开始为HIDE
- private static final boolean SHOW = true;//显示图片
- private static final boolean HIDE = false;//隐藏图片
- public SampleView(Context context) {
- super(context);
- mBitmap = BitmapFactory.decodeResource(getResources(), R.drawable.image1);
- limitLength = width = mBitmap.getWidth();
- heigth = mBitmap.getHeight();
- }
- @Override
- protected void onDraw(Canvas canvas) {
- Region region = new Region();
- int i = 0;
- while (i * CLIP_HEIGHT <= heigth) {//计算clip的区域
- if (i % 2 == 0) {
- region.union(new Rect(0, i * CLIP_HEIGHT, limitLength, (i + 1) * CLIP_HEIGHT));
- } else {
- region.union(new Rect(width - limitLength, i * CLIP_HEIGHT, width, (i + 1)
- * CLIP_HEIGHT));
- }
- i++;
- }
- canvas.clipRegion(region);
- canvas.drawBitmap(mBitmap, 0, 0, new Paint());
- if (status == HIDE) {//如果此时是隐藏
- limitLength -= 5;
- if(limitLength<=0)
- status=SHOW;
- } else {//如果此时是显示
- limitLength += 5;
- if(limitLength>=width)
- status=HIDE;
- }
- invalidate();
- }
- }
- }
效果就是一直这样交叉的隐藏和显示图片
转自:http://blog.csdn.net/lonelyroamer/article/details/8349601
regin,clip Android相关推荐
- Android输入法遮挡了输入框,使用android:fitsSystemWindows=“true“后界面顶部出现白条解决方案
Android输入法遮挡了输入框,使用android:fitsSystemWindows="true"后界面顶部出现白条解决方案 参考文章: (1)Android输入法遮挡了输入框 ...
- Flutter配置好后,在Android Studio中找不到设备,no devices
Flutter配置好后,在Android Studio中找不到设备,no devices 完成Flutter的Android配置之后,连上设备,运行flutter doctor,发现已经识别了一个可用 ...
- github snap android,GitHub - albuer/heapsnap: HeapSnap 是一个定位内存泄露的工具,适用于Android平台。...
HeapSnap 1.HeapSnap 是什么 HeapSnap 是一个定位内存泄露的工具,适用于Android平台. 主要特性如下: 对系统负载低 不需要修改目标进程的源代码 支持Andoroid上 ...
- 最简单也最难——如何获取到Android控件的高度,获取android控件
最简单也最难--如何获取到Android控件的高度,获取android控件 问题 如何获取一个控件的长和高,相信很多朋友第一眼看见这个问题都会觉得很简单,直接在onCreate里面调用getWidth ...
- (GO_GTD_1)基于OpenCV和QT,建立Android图像处理程序
一.创建新QT工程 一定要是全英文路径,比如"E:\android_qt_opencv\GO_GTD" 由于我们在安装的时候,选择android的工具链,所以在这里会出现以下选择, ...
- video.js android,VideoJS + HTML5自动播放失败,适用于Android 2.3+和IOS 4+
我的VideoJS和HTML5项目针对更新的Web浏览器(较新版本的FireFox和Chrome)以及移动浏览器(Android2.3 +和IOS4 +).VideoJS + HTML5自动播放失败, ...
- android serialport new 软件退出_基于Android9.0,了解Android启动流程
先记住四个进程和三种方式. **四个进程** 1.Launcher进程 2.system_server进程 3.App进程 4.Zygote进程 **三种方式** 1.Binder方式 2.Socke ...
- 谷歌发布最新版安卓Android,谷歌发布安卓 9 正式版,代号 Android Pie
爱搞机 8 月 7 日消息,据外媒报道,北京时间今日凌晨,谷歌开始向用户推送安卓 Android Pie 正式版,除了确定新系统的代号为 Pie(派)之外,谷歌还将原本的安卓 9.0 称作 Andro ...
- java android长连接_基于Java Socket的自定义协议,实现Android与服务器的长连接(一)...
一.基础知识准备 在正式给大家介绍自定义协议之前,我们先对网络传输和协议解析的相关知识点做一个基本的介绍,尽管这些知识点我们在学校里学过,但难免会有所遗忘,这里先做一个简单的介绍,以便对后文的内容理解 ...
最新文章
- Spring 如何初始化泛型类实例
- 澎湖县地产泡沫的破灭
- C++内存管理与分配方式
- 解决Ubuntu下 Could NOT find CURL (missing: CURL_LIBRARY CURL_INCLUDE_DIR)
- 计算机怎么远程桌面,电脑远程桌面如何连接 电脑远程桌面连接方法【详解】...
- android 缓存头像,android 实现类似微信缓存和即时更新好友头像示例
- java和js实现电话号码部分隐藏
- 95后夜猫子报告:三成熬夜到1点 夜间最爱追《乡村爱情》
- Linux学习笔记5 - Shell编程(类似于Windows下的批处理)
- QT将英文星期转为中文星期
- echarts年龄饼图_ECharts中饼图的操作
- linux卸载exe文件怎么恢复,linux中误删除程序包恢复实例
- [iOS]在xcode的iOS虚拟机中对BLE(蓝牙4.0)进行调试
- (教程)教你如何自己办理商标注册事宜
- android关闭本应用的通知声音代码,关于android:当我的应用取消通知时,播放带有FLAG_INSISTENT通知的声音不会停止...
- “赋能开发者”高峰论坛暨西安葡萄城30周年庆典隆重举办
- 2020下半年,最接地气的字节跳动Android面经分享(已收offer
- 操作系统面试题(十二):逻辑地址和物理地址
- 杜洋PCB设计视频教程笔记(陆续更新)
- 开源超级微同城系统源码 含完整程序代码包+数据库+详细搭建教程
热门文章
- ubuntu16.04 护眼神器Redshift
- 阿里天池大数据竞赛(一)用ODPS提取特征
- 编程的宗派(OOP与FP孰优孰劣)--王垠
- 脱水冷冻干燥宠物食品的全球与中国市场2022-2028年:技术、参与者、趋势、市场规模及占有率研究报告
- 探索 Sa-Token (一) SpringBoot 集成 Sa-Token
- React Native 仿 ofo 共享单车 App
- xpath中的position()函数使用
- Tensorflow中的masking和padding
- 华为路由器ospf路由表解读_华为路由如何建立OSPF网络详解
- HCIA Storage部分题库