Android中矩阵Matrix实现平移,旋转,缩放和翻转的用法详细介绍

一,矩阵Matrix的数学原理

矩阵的数学原理涉及到矩阵的运算和变换,是高等代数学中的重要概念。在图形变换中,矩阵起到关键作用,通过矩阵的变换可以改变图形的位置、形状和大小。矩阵的运算是数值分析领域的重要问题,对矩阵进行分解和简化可以简化计算过程。对于一些特殊矩阵,如稀疏矩阵和准对角矩阵,有特定的快速运算算法。

在Matrix Matrix中,矩阵的数学原理同样适用。Matrix提供了缩放、平移、旋转和错切等操作,这些操作对应于特定的矩阵变换。例如,缩放操作对应于矩阵的元素乘以一个标量,平移操作对应于矩阵的元素加上一个偏移量,旋转操作则通过矩阵的置换和缩放来实现。

Matrix的数学原理在实际应用中非常重要。在图形处理、计算机视觉、机器学习等领域,都需要使用到矩阵运算和变换。掌握矩阵的数学原理有助于更好地理解和应用这些技术。

二,3x3矩阵的计算方法:

3x3矩阵的计算方法包括加法、减法、数乘和矩阵乘法。

加法是将两个3x3矩阵对应位置的元素相加,得到一个新的3x3矩阵。减法是将两个3x3矩阵对应位置的元素相减,得到一个新的3x3矩阵。数乘是将一个标量和一个3x3矩阵相乘,得到一个新的3x3矩阵。矩阵乘法是将两个3x3矩阵按照一定的规则相乘,得到一个新的3x3矩阵。

在进行矩阵乘法时,需要按照一定的规则进行计算,即左边矩阵的第一行的元素分别与右边矩阵的第一列的元素相乘,然后求和得到相乘矩阵的第一行的第一个元素。同样地,左边矩阵的第一行的元素分别与右边矩阵的第二列的元素相乘,求和得到相乘矩阵的第一行的第二个元素,以此类推。

另外,还有三阶矩阵乘法的公式:D=a11a22a33+a12a23a31+a13a21a32-a13a22a31-a12a21a33- a11a23a32。这个公式可以帮助我们快速地计算出两个3x3矩阵的乘积。

需要注意的是,在进行矩阵运算时,需要遵循一定的运算规则,如先进行括号内的运算,然后进行加、减、乘等运算,最后进行除法运算。同时,要注意矩阵的维数,即行数和列数,只有当两个矩阵的维数相同时才能进行矩阵运算。

三,四种变换的具体情形

1,平移变换
假定有一个点的坐标是 P_(x_0,y_0)将其移动到P_(x,y) ,再假定在x轴和y轴方向移动的大小分别为:
△x = x - x_0
△y = y - y_0
如下图所示:
在这里插入图片描述不难知道:
x = x_0 + △x
y = y_0 + △y
如果用矩阵来表示的话,就可以写成:
在这里插入图片描述
2,旋转变换
围绕坐标原点旋转

假定有一个点的坐标是 P_(x_0,y_0) ,相对坐标原点顺时针旋转 theta后的情形,同时假定P点离坐标原点的距离为r,如下图:
在这里插入图片描述那么,
在这里插入图片描述如果用矩阵,就可以表示为:
在这里插入图片描述3,缩放变换
理论上而言,一个点是不存在什么缩放变换的,但考虑到所有图像都是由点组成,因此,如果图像在x轴和y轴方向分别放大k1和k2倍的话,那么图像中的所有点的x坐标和y坐标均会分别放大k1和k2倍,即:
x = k_1 x x_0
y = k_2 x y_0

用矩阵表示就是:
在这里插入图片描述4,对称变换(翻转)
事实上,我们还可以利用Matrix,进行对称变换。所谓对称变换,就是经过变化后的图像和原图像是关于某个对称轴是对称的。比如,某点 经过对称变换后得到,
如果对称轴是x轴,那么,
x = x_0
y = -y_0
用矩阵表示就是:
在这里插入图片描述
如果对称轴是y轴,那么,
x = -x_0
y =y_0

用矩阵表示就是:
在这里插入图片描述如果对称轴是y = x,如图:
在这里插入图片描述四,基本方法解析

1,构造函数

public Matrix()
public Matrix(Matrix src)

构造函数有两个,第一个是直接创建一个单位矩阵,第二个是根据提供的矩阵创建一个新的矩阵(采用deep copy)

单位矩阵如下:
在这里插入图片描述2,平移效果

public void setTranslate(float dx, float dy)

设置平移效果,参数分别是x,y上的平移量。
效果图如下:
在这里插入图片描述
在Android中,Matrix 类用于执行各种2D图形变换,包括平移。以下是一个示例代码,展示如何使用 Matrix 实现平移:

Matrix matrix = new Matrix();  
matrix.setTranslate(dx, dy); // dx 和 dy 是平移的距离  // 假设你有一个 Bitmap 对象  
Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.my_image);  // 应用 Matrix 到 Bitmap 上  
Bitmap transformedBitmap = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(), bitmap.getHeight(), matrix, true);  // 现在,transformedBitmap 是平移后的图像

在上述代码中,setTranslate 方法用于设置平移的距离。dx 和 dy 参数分别表示在x轴和y轴方向上的平移距离。然后,通过 createBitmap 方法将应用了平移变换的 Matrix 应用到一个 Bitmap 上,得到平移后的图像。

2,缩放效果

public void setScale(float sx, float sy, float px, float py)
public void setScale(float sx, float sy)

两个方法都是设置缩放到matrix中,sx,sy代表了缩放的倍数,px,py代表缩放的中心。这里跟上面比较类似不做讲解了。

3,旋转效果

public void setRotate(float degrees, float px, float py)
public void setRotate(float degrees)

看一个示例,我们把图像旋转90度,那么90度对应的sin和cos分别是1和0。
在这里插入图片描述
4,对称翻转
在Android中,Matrix类并没有直接提供实现对称的接口。对称变换通常涉及到更复杂的几何变换,包括旋转、平移和缩放等。Matrix类提供了一些基本的方法来实现这些变换,但如果你需要实现更复杂的对称变换,可能需要自定义实现或者使用其他图形处理库。

如果你需要实现对称变换,一种可能的解决方案是先对图像进行对称变换,然后再使用Matrix类的方法进行平移、旋转和缩放等操作。这需要一些几何知识来计算对称变换的矩阵,然后将其应用到图像上。

以下是一个示例代码,展示了如何使用Matrix类实现对称变换:

// 假设你有一个 Bitmap 对象  
Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.my_image);  // 定义对称变换的矩阵  
Matrix matrix = new Matrix();  
matrix.setScale(-1, 1); // 对称变换的矩阵  
matrix.postTranslate(bitmap.getWidth(), 0); // 执行对称变换后的平移  // 应用 Matrix 到 Bitmap 上  
Bitmap symmetricBitmap = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(), bitmap.getHeight(), matrix, true);  // 现在,symmetricBitmap 是对称变换后的图像

在上述代码中,我们首先创建一个 Matrix 对象,并使用 setScale 方法设置对称变换的矩阵。这里我们使用了 -1 和 1 作为缩放因子,分别表示在x轴和y轴方向上的对称变换。然后,我们使用 postTranslate 方法将对称变换后的图像平移到正确的位置。最后,通过 createBitmap 方法将应用了对称变换和平移的 Matrix 应用到一个 Bitmap 上,得到对称变换后的图像。

需要注意的是,这只是一个简单的示例代码,实际的对称变换可能需要更复杂的矩阵计算。如果你需要实现更复杂的对称变换,可能需要使用更高级的图形处理库或者自定义实现。

五,高级方法解析

上面的基本方法中,有关于变换的set方法都可以带来不同的效果,但是每个set都会把上个效果清除掉,例如依次调用了setScale,setTranslate,那么最终只有setTranslate会起作用,那么如何才和将两种效果复合呢。Matrix给我们提供了很多方法。但是主要都是2类:

preXXXX:以pre开头,例如preTranslate
postXXXX:以post开头,例如postScale

他们分别代表了前乘,和后乘。看一段代码:

Matrix matrix = new Matrix();
matrix.setTranslate(100, 1000);
matrix.preScale(0.5f, 0.5f);

这里matrix前乘了一个scale矩阵,换算成数学式如下:
在这里插入图片描述
从上面可以看出,最终得出的matrix既包含了缩放信息也有平移信息。
后乘自然就是matrix在后面,而缩放矩阵在前面,由于矩阵前后乘并不等价,也就导致了他们的效果不同。我们来看看后乘的结果:
在这里插入图片描述可以看到,结果跟上面不同,并且这也不是我们想要的结果,这里缩放没有更改,但是平移被减半了,换句话说,平移的距离也被缩放了。所以需要注意前后乘法的关系。

matrix除了上面的方法外,还有一些其他的方法。

public boolean setRectToRect(RectF src, RectF dst, ScaleToFit stf)

在Android中,setRectToRect 是 Matrix 类的一个方法,用于将一个矩形(源矩形)转换到另一个矩形(目标矩形)。这个方法通常用于图形变换,例如在图像处理或绘图操作中。

该方法接受四个参数:

src:源矩形的左上角坐标(x, y)和其宽度和高度(width, height)。
dst:目标矩形的左上角坐标(x, y)和其宽度和高度(width, height)。
filterMin:缩放过滤模式的最小值。
filterMag:缩放过滤模式的最大值。

这个方法的作用是将源矩形转换为目标矩形,通过矩阵变换实现平移、缩放、旋转等操作。它可以根据需要选择不同的缩放过滤模式,以控制图像的平滑度和质量。

以下是一个示例代码,展示了如何使用 setRectToRect 方法进行图像变换:

Matrix matrix = new Matrix();  
// 设置源矩形的坐标和大小  
float srcLeft = 0;  
float srcTop = 0;  
float srcWidth = 100;  
float srcHeight = 100;  
// 设置目标矩形的坐标和大小  
float dstLeft = 50;  
float dstTop = 50;  
float dstWidth = 200;  
float dstHeight = 200;  
// 设置缩放过滤模式(使用线性插值)  
matrix.setRectToRect(new RectF(srcLeft, srcTop, srcLeft + srcWidth, srcTop + srcHeight),  new RectF(dstLeft, dstTop, dstLeft + dstWidth, dstTop + dstHeight),  Matrix.ScaleToFit.CENTER, Matrix.ScaleToFit.CENTER);  
// 应用矩阵到 Bitmap 上进行变换  
Bitmap transformedBitmap = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(), bitmap.getHeight(), matrix, true);

在上述示例中,我们首先创建了一个 Matrix 对象,并使用 setRectToRect 方法将源矩形转换为目标矩形。这里,我们使用了线性插值作为缩放过滤模式,使图像在变换过程中保持平滑。然后,我们将应用了矩阵变换的 Matrix 应用到一个 Bitmap 上,得到变换后的图像。

ScaleToFit 有如下四个值:

FILL: 可能会变换矩形的长宽比,保证变换和目标矩阵长宽一致。
START:保持坐标变换前矩形的长宽比,并最大限度的填充变换后的矩形。至少有一边和目标矩形重叠。左上对齐。
CENTER: 保持坐标变换前矩形的长宽比,并最大限度的填充变换后的矩形。至少有一边和目标矩形重叠。
END:保持坐标变换前矩形的长宽比,并最大限度的填充变换后的矩形。至少有一边和目标矩形重叠。右下对齐。

你的鼓励将是我创作的最大动力,求大神打赏!!!
在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/633270.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

UG阵列-数字递增

在UG中,我们对一个文本进行阵列,可以得到很多个相同文本,但是如果文本中的数据是递增数列,需要用到表达式 先画一根参考线,标注参考线长度,并记录系统生成对应长度的表达式,例如p15 然后插入一个…

Spring WebSocket实现实时通信的详细教程

简介 WebSocket 是基于TCP/IP协议,独立于HTTP协议的通信协议。WebSocket 连接允许客户端和服务器之间的全双工通信,以便任何一方都可以通过已建立的连接将数据推送到另一方。 我们常用的HTTP是客户端通过「请求-响应」的方式与服务器建立通信的&#x…

互联网加竞赛 基于机器视觉的停车位识别检测

简介 你是不是经常在停车场周围转来转去寻找停车位。如果你的车辆能准确地告诉你最近的停车位在哪里,那是不是很爽?事实证明,基于深度学习和OpenCV解决这个问题相对容易,只需获取停车场的实时视频即可。 该项目较为新颖&#xf…

2023 IoTDB Summit:北京城建智控科技股份有限公司高级研发主管刘喆《IoTDB在城市轨道交通综合监控系统中的应用》...

12 月 3 日,2023 IoTDB 用户大会在北京成功举行,收获强烈反响。本次峰会汇集了超 20 位大咖嘉宾带来工业互联网行业、技术、应用方向的精彩议题,多位学术泰斗、企业代表、开发者,深度分享了工业物联网时序数据库 IoTDB 的技术创新…

(设置非自定义Bean)学习Spring的第六天

一 . 获取Bean的方法详解 , 如下图 : 二 . Spring配置非自定义bean----DruidDatasource 我们举个例子 : 配置Druid数据源交由Spring管理 首先导入在pom文件Druid坐标 然后考虑 : 被配置的Bean的实例化方式是什么 : 无参构造 被配置的Bena是否要注入必要属性 : 四个基本信息…

lvgl chart 清空series数据

lvgl7 可以使用lv_chart_clear_series函数解决,那么lvgl8并没有相对应的series函数清除,反复看lvgl8代码,我发现可以通过设置线条全点值可以达到清除的目的 lv_chart_set_all_value(chart, series, LV_CHART_POINT_NONE); 重新通过lv_chart_…

fastJson和jackson的日期数据处理

目录 1.jackson 2.fastjson 3.总结 1.jackson jackson是spring mvc默认的JSON解析方法,前端的数据序列化处理之后,后端经过反序列化处理可以直接使用实体对象进行接收。后端接口返回实体对象,经过序列化处理后前端可以接收并进行处理。 …

聚类模型评估指标

聚类模型评估指标-轮廓系数 计算样本i到同簇其它样本到平均距离ai,ai越小,说明样本i越应该被聚类到该簇(将ai称为样本i到簇内不相似度);计算样本i到其它某簇Cj的所有样本的平均距离bij,称为样本i与簇Cj的…

企业设计图纸安全、企业设计图纸安全软件

设计图纸对于企业的重要性不言而喻,因此保障设计图纸的安全显得尤为重要。以下是企业设计图纸安全需要注意的几个方面: 访问控制:只有授权人员才能访问设计图纸,需要通过账号密码或者其他验证方式进行身份认证。 加密传输&#…

Windows下安装alipay-sdk-python时,pycrypto安装报错问题处理

1、安装alipay-sdk-python 时,保存内容如下。 Building wheels for collected packages: pycryptoBuilding wheel for pycrypto (setup.py) ... error error: subprocess-exited-with-error python setup.py bdist_wheel did not run successfully.│ exit c…

从零开始了解域名:什么是域名、域名的作用及类别

在互联网时代,域名作为一个网站在互联网上的身份标识,无论是企业或者个人建设网站,获取域名都是其中非常关键的一环。一个好的域名不仅便于记忆,还有助于强化品牌、利于宣传,让用户更好的找到你的网站。在下面的内容中…

基于YOLOv8深度学习的100种中草药智能识别系统【python源码+Pyqt5界面+数据集+训练代码】目标检测、深度学习实战

《博主简介》 小伙伴们好,我是阿旭。专注于人工智能、AIGC、python、计算机视觉相关分享研究。 ✌更多学习资源,可关注公-仲-hao:【阿旭算法与机器学习】,共同学习交流~ 👍感谢小伙伴们点赞、关注! 《------往期经典推…

解锁文字魔法:探索自然语言处理的秘密——从技术揭秘到应用实战!

目录 前言 关键技术——揭密自然语言处理的秘密武器! 领域应用——自然语言处理技术在不同领域的奇妙表演! 超越极限——自然语言处理技术面临的顽强挑战揭秘! 科技VS伦理——自然语言处理技术的发展与伦理社会的纠结较量! 开…

买家福音:亚马逊鲲鹏系统全自动操作助你轻松搞定一切

我一直以来都是亚马逊的忠实用户,但是最近我发现了一款真正令人惊叹的工具,改变了我在平台上的经验。我想分享一下我的感受,最近,我得知并尝试了亚马逊鲲鹏系统,简直是为买家账号管理量身定制的利器。在我账号过多时&a…

yolov8的目标检测、实例分割、关节点估计的原理解析

1 YOLO时间线 这里简单列下yolo的发展时间线,对每个版本的提出有个时间概念。 2 yolov8 的简介 工程链接:https://github.com/ultralytics/ultralytics 2.1 yolov8的特点 采用了anchor free方式,去除了先验设置可能不佳带来的影响借鉴General…

PHP Fatal error: Unparenthesized `a ? b : c ? d : e` is not supported.

这个错误是关于三元运算符的错误 这个错误在php8.0以下的版本好像是没问题呢 PHP Fatal error: Unparenthesized a ? b : c ? d : e is not supported. Use either (a ? b : c) ? d : e or a ? b : (c ? d : e) in /cangku/app/common.php on line 57 这个问题是 程…

一站式获取 PieCloudDB Database 产品、社区及数据库行业全动态

第一部分 PieCloudDB Database 最新动态 PieCloudDB 推出社区版全新版本 11月14日,PieCloudDB 再度升级,推出社区版全新版本,免费面向用户开放下载,新版本将支持单机和多节点部署两种方式。欢迎试用! 下载链接&…

linux docker-compose安装失败解决

1.去github下载到本地 https://github.com/docker/compose/releases/ 2.上传到linux 服务器 mv dokcer-compose-linux-x86_64 /usr/loacal/bin/docker-compose 3.给权限 chmod x /usr/local/bin/docker-compose 4.查看是否安装成功 docker-compose -version 5.卸载 …

第14章_集合与数据结构拓展练习(前序、中序、后序遍历,线性结构,单向链表构建,单向链表及其反转,字符串压缩)

文章目录 第14章_集合与数据结构拓展练习选择填空题1、前序、中序、后序遍历2、线性结构3、其它 编程题4、单向链表构建5、单向链表及其反转6、字符串压缩 第14章_集合与数据结构拓展练习 选择填空题 1、前序、中序、后序遍历 分析: 完全二叉树: 叶结点…

Flink TaskManager内存管理机制介绍与调优总结

内存模型 因为 TaskManager 是负责执行用户代码的角色,一般配置 TaskManager 内存的情况会比较多,所以本文当作重点讲解。根据实际需求为 TaskManager 配置内存将有助于减少 Flink 的资源占用,增强作业运行的稳定性。 TaskManager 内…