Android矩阵Matrix动画缩放Bitmap移动手指触点到ImageView中心位置,Kotlin
Android矩阵Matrix动画缩放Bitmap移动手指触点到ImageView中心位置,Kotlin
借鉴 Android双指缩放ScaleGestureDetector检测放大因子大图移动到双指中心点ImageView区域中心,Kotlin(2)-CSDN博客 在此基础上实现手指在屏幕上点击后,动画放大图片,在放大过程中,移动手指触点位置到ImageView的中心。
import android.content.Context
import android.graphics.Bitmap
import android.graphics.Canvas
import android.graphics.Color
import android.graphics.Matrix
import android.graphics.Paint
import android.graphics.RectF
import android.graphics.drawable.BitmapDrawable
import android.os.Bundle
import android.util.AttributeSet
import android.util.Log
import android.view.MotionEvent
import androidx.appcompat.app.AppCompatActivity
import androidx.appcompat.widget.AppCompatImageView
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.delay
import kotlinx.coroutines.launchclass MainActivity : AppCompatActivity() {override fun onCreate(savedInstanceState: Bundle?) {super.onCreate(savedInstanceState)setContentView(R.layout.activity_main)}
}class MyImageView : AppCompatImageView {private var mCurX = 0fprivate var mCurY = 0fprivate var mCanDrawBitmap = falseprivate var W = 0private var H = 0private val SCALE_FACTOR: Float = 5.5fprivate var mOriginBmp: Bitmap? = nullprivate var mCirclePaint = Paint()private var mDeltaScaleFactor: Float = 0fprivate var mAnimScaleBmp: Bitmap? = nullprivate var mCanDrawTouchPoint = falseprivate var mTouchPointX = 0fprivate var mTouchPointY = 0fconstructor(ctx: Context, attrs: AttributeSet) : super(ctx, attrs) {mCirclePaint.style = Paint.Style.STROKEmCirclePaint.strokeWidth = 10fmCirclePaint.isAntiAlias = truemCirclePaint.color = Color.REDmOriginBmp = (this.drawable as BitmapDrawable).bitmap}override fun onSizeChanged(w: Int, h: Int, oldw: Int, oldh: Int) {super.onSizeChanged(w, h, oldw, oldh)W = wH = hLog.d("fly", "W=$W H=$H")}override fun onTouchEvent(event: MotionEvent?): Boolean {if (event == null) {return false}mCurX = event.xmCurY = event.ywhen (event.actionMasked) {MotionEvent.ACTION_DOWN -> {//启动动画。startScaleAnim()}}return false}/*** Bitmap.createScaledBitmap耗时加剧卡顿。* 优化方案,基于原图setRectToRect缩放到给定宽w高h的放大图。*/private fun getScaleBmp(w: Int, h: Int): Bitmap {val bmp = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_8888)val c = Canvas(bmp)c.drawColor(Color.BLUE)val src = RectF(0f, 0f, mOriginBmp!!.width.toFloat(), mOriginBmp!!.height.toFloat())val dst = RectF(0f, 0f, w.toFloat(), h.toFloat())val mx = Matrix()mx.setRectToRect(src, dst, Matrix.ScaleToFit.CENTER)c.drawBitmap(mOriginBmp!!, mx, null)return bmp}private fun startScaleAnim() {val step = 50f //经过step后,完成缩放动画。val delta = (SCALE_FACTOR - 1) / stepCoroutineScope(Dispatchers.IO).launch {//绘制在原图上手的触点。mTouchPointX = mCurXmTouchPointY = mCurYmCanDrawTouchPoint = truemyPostInvalidate()delay(500) //延时,观察手指触点。mCanDrawTouchPoint = falsemCanDrawBitmap = truefor (i in 0 until step.toInt()) {mDeltaScaleFactor = 1f + delta * i/*mAnimScaleBmp = Bitmap.createScaledBitmap(mOriginBmp!!,(W * mDeltaScaleFactor + 1).toInt(), //注意精度损失,造成坐标偏移。(H * mDeltaScaleFactor + 1).toInt(),//注意精度损失,造成坐标偏移。true)*/mAnimScaleBmp = getScaleBmp((W * mDeltaScaleFactor + 0.5).toInt(), (H * mDeltaScaleFactor + 0.5).toInt())//触发重绘。myPostInvalidate()}//for循环完成后,绘制最终图片动画放大完成后的中心圆点。mTouchPointX = W / 2fmTouchPointY = H / 2fmCanDrawTouchPoint = truemyPostInvalidate()}}private fun myPostInvalidate() {this.postInvalidate()}private fun drawTouchPoint(c: Canvas) {c.drawCircle(mTouchPointX, mTouchPointY, 50f, mCirclePaint)}override fun onDraw(canvas: Canvas) {super.onDraw(canvas)if (mCanDrawBitmap) {val mx = Matrix()mx.setScale(mDeltaScaleFactor, mDeltaScaleFactor)mx.setTranslate(W / 2f - mCurX * mDeltaScaleFactor, H / 2f - mCurY * mDeltaScaleFactor)canvas.drawBitmap(mAnimScaleBmp!!, mx, null)}if (mCanDrawTouchPoint) {drawTouchPoint(canvas)}}
}
Android双指缩放ScaleGestureDetector检测放大因子大图移动到双指中心点ImageView区域中心,Kotlin(2)-CSDN博客文章浏览阅读613次,点赞4次,收藏5次。需要注意的,因为在xml布局里面特别设置了ImageView的高度为wrap_content,手指在屏幕触点的位置是放大镜里面放大图片后准确圆心位置,但是,如果ImageView设置成match_parent,则因为ImageView里面的Bitmap被缩放(此处Bitmap其实小于ImageView,被拉伸了),拉伸后的Bitmap水平方向坐标与ImageView一直重合,但竖直方向,Bitmap坐标与ImageView不一致,会造成一种现象,手指触点放大镜放大后,水平方向是正确的,但竖直方向有偏移量。https://blog.csdn.net/zhangphil/article/details/135701608Android矩阵setRectToRect裁剪Bitmap原图Matrix放大,mapRect标记中心区域,Kotlin-CSDN博客文章浏览阅读229次,点赞3次,收藏5次。【代码】Android矩阵setRectToRect裁剪Bitmap原图Matrix放大,mapRect标记中心区域,Kotlin。
https://blog.csdn.net/zhangphil/article/details/135960921
Android ScaleGestureDetector检测双指缩放Bitmap基于Matrix动画移动到双指捏合中心点ImageView区域中心,Kotlin_android的两指捏合-CSDN博客文章浏览阅读256次,点赞5次,收藏11次。需要注意的,因为在xml布局里面特别设置了ImageView的高度为wrap_content,手指在屏幕触点的位置是放大镜里面放大图片后准确圆心位置,但是,如果ImageView设置成match_parent,则因为ImageView里面的Bitmap被缩放(此处Bitmap其实小于ImageView,被拉伸了),拉伸后的Bitmap水平方向坐标与ImageView一直重合,但竖直方向,Bitmap坐标与ImageView不一致,会造成一种现象,手指触点放大镜放大后,水平方向是正确的,但竖直方向有偏移量。_android的两指捏合https://blog.csdn.net/zhangphil/article/details/135705931
相关文章:
Android矩阵Matrix动画缩放Bitmap移动手指触点到ImageView中心位置,Kotlin
Android矩阵Matrix动画缩放Bitmap移动手指触点到ImageView中心位置,Kotlin 借鉴 Android双指缩放ScaleGestureDetector检测放大因子大图移动到双指中心点ImageView区域中心,Kotlin(2)-CSDN博客 在此基础上实现手指在屏幕上点击后&…...
C语言:表达式求值
引言:在笔试中,有一类的题目,题目给出代码,要求分析得出输出结果。这类题目更加考察我们对于运算顺序和运算类型转换的理解。文章介绍了隐式类型转换和操作符注意点,希望增加读者对于表达式求值的理解。 1.隐式类型转…...
GO 的 Web 开发系列(五)—— 使用 Swagger 生成一份好看的接口文档
经过前面的文章,已经完成了 Web 系统基础功能的搭建,也实现了 API 接口、HTML 模板渲染等功能。接下来要做的就是使用 Swagger 工具,为这些 Api 接口生成一份好看的接口文档。 一、写注释 注释是 Swagger 的灵魂,Swagger 是通过…...
【极数系列】Flink集成KafkaSink 实时输出数据(11)
文章目录 01 引言02 连接器依赖2.1 kafka连接器依赖2.2 base基础依赖 03 使用方法04 序列化器05 指标监控06 项目源码实战6.1 包结构6.2 pom.xml依赖6.3 配置文件6.4 创建sink作业 01 引言 KafkaSink 可将数据流写入一个或多个 Kafka topic 实战源码地址,一键下载可用…...
我为什么选择Xamarin开发ios app安卓app
临岁之寒简书作者,转载 Xamarin是一项跨平台开发技术,之前是收费的,而且据说收费不菲,所以使用的人数比较少,在国内几乎无人问津。后来Xamarin被微软收购,现已免费开放,相信今后国内的使用人群会大幅地增长…...
安全基础~通用漏洞4
文章目录 知识补充XSS跨站脚本**原理****攻击类型**XSS-后台植入Cookie&表单劫持XSS-Flash钓鱼配合MSF捆绑上线ctfshow XSS靶场练习 知识补充 SQL注入小迪讲解 文件上传小迪讲解 文件上传中间件解析 XSS跨站脚本 xss平台: https://xss.pt/ 原理 恶意攻击者…...
2024/2/12 图的基础知识 2
目录 查找文献 P5318 【深基18.例3】查找文献 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn) 有向图的拓扑序列 848. 有向图的拓扑序列 - AcWing题库 最大食物链计数 P4017 最大食物链计数 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn) 查找文献 P5318 【深基18.例3】…...
无人机飞行原理,多旋翼无人机飞行原理详解
多旋翼无人机升空飞行的首要条件是动力,有了动力才能驱动旋粪旋转,才能产生克服重力所必需的升力。使旋翼产生升力,进而推动多旋翼无人机升空飞行的一套设备装置称为动力装置,包括多旋翼无人机的发动机以及保证发动机正常工作所必…...
docker本地目录挂载
小命令 1、查看容器详情 docker inspect 容器名称 还是以nginx为例,上篇文章我们制作了nginx静态目录的数据卷,此时查看nginx容器时会展示出来(docker inspect nginx 展示信息太多,这里只截图数据卷挂载信息)&#…...
使用C++从零开始,自己写一个MiniWeb
第一步:新建项目 1、打开VS点击创建新项目 2、选择空项目并点下一步(切记不能选错项目类型) 3、填写项目名称和路径,点击创建即可 新建好后项目是这样的比较干净 4、右击源文件,点击添加,新建http.cpp文件…...
Android Graphics 图像显示系统 - 开篇
“ 随着学习的不断深入和工作经验的积累,欲将之前在博客中整理的Android Graphics知识做进一步整理,并纠正一些理解上的错误,故开设Graphics主题系列文章 ” 序言 由于工作需要,也源于个人兴趣,终于下决心花时间整理一…...
机器学习在各个行业的应用介绍
随着科技的飞速发展,机器学习已经从实验室走向了现实世界,逐渐成为各行各业不可或缺的工具。从金融领域到医疗健康,从零售市场到制造业,机器学习正在改变着我们的工作方式和生活质量。 本文将深入探讨机器学习在以下几个领域的应用…...
【生产实测有效】Windows命令行查看激活状态脚本
Windows查看激活状态关键代码 通过windows server 自带的PowerShell来执行 Get-WmiObject SoftwareLicensingProduct | Select-Object -Property Description, LicenseStatus | findstr "Operating System"|findstr "1$"Get-WmiObject SoftwareLicensingPr…...
简单的Udp服务器
目录 简单的UDP网络程序1.1 UdpServer.hpp1.2 UdpClient.cc1.3 main.cc1.4 makefile1.5 log.hpp 简单的UDP网络程序 1.1 UdpServer.hpp #pragma once#include <iostream> using namespace std;#include <unistd.h> #include <sys/types.h> #include <sy…...
【Linux进程间通信】用管道实现简单的进程池、命名管道
【Linux进程间通信】用管道实现简单的进程池、命名管道 目录 【Linux进程间通信】用管道实现简单的进程池、命名管道为什么要实现进程池?代码实现命名管道创建一个命名管道 理解命名管道匿名管道与命名管道的区别命名管道的打开规则 作者:爱写代码的刚子…...
Linux操作系统基础(九):Linux用户与权限
文章目录 Linux用户与权限 一、文件权限概述 二、终端命令:组管理 三、终端命令:用户管理 1、创建用户 、 设置密码 、删除用户 2、查看用户信息 3、su切换用户 4、sudo 4.1、给指定用户授予权限 4.2、使用 用户 zhangsan登录, 操作管理员命令…...
蓝桥杯——第 5 场 小白入门赛(c++详解!!!)
文章目录 1 十二生肖基本思路: 2 欢迎参加福建省大学生程序设计竞赛基本思路:代码: 3 匹配二元组的数量基本思路:代码: 4 元素交换基本思路:代码: 5 下棋的贝贝基本思路:代码: 6 方程…...
Codeforces Round 303 (Div. 2)C. Kefa and Park(DFS、实现)
文章目录 题面链接题意题解代码总结 题面 链接 C. Kefa and Park 题意 求叶节点数量,叶节点满足,从根节点到叶节点的路径上最长连续1的长度小于m 题解 这道题目主要是实现,当不满足条件时直接返回。 到达叶节点后统计答案,用…...
797. 差分
Problem: 797. 差分 文章目录 思路解题方法复杂度Code 思路 这是一个差分数组的问题。差分数组的主要适用场景是频繁对原始数组的某一个区间进行增减操作。这种操作是区间修改操作,在这种操作下,差分数组只需要对区间的两个端点进行操作,时间…...
2024.2.5 vscode连不上虚拟机,始终waiting for server log
昨天还好好的,吃着火锅,做着毕设,突然就被vscode给劫了。 起初,哥们跟着网上教程有模有样地删除了安装包缓存,还删除了.vscode-server,发现没卵用,之前都是搜那个弹窗报错。 后来发现原来是vsco…...
【Python】 -- 趣味代码 - 小恐龙游戏
文章目录 文章目录 00 小恐龙游戏程序设计框架代码结构和功能游戏流程总结01 小恐龙游戏程序设计02 百度网盘地址00 小恐龙游戏程序设计框架 这段代码是一个基于 Pygame 的简易跑酷游戏的完整实现,玩家控制一个角色(龙)躲避障碍物(仙人掌和乌鸦)。以下是代码的详细介绍:…...
云原生核心技术 (7/12): K8s 核心概念白话解读(上):Pod 和 Deployment 究竟是什么?
大家好,欢迎来到《云原生核心技术》系列的第七篇! 在上一篇,我们成功地使用 Minikube 或 kind 在自己的电脑上搭建起了一个迷你但功能完备的 Kubernetes 集群。现在,我们就像一个拥有了一块崭新数字土地的农场主,是时…...
树莓派超全系列教程文档--(62)使用rpicam-app通过网络流式传输视频
使用rpicam-app通过网络流式传输视频 使用 rpicam-app 通过网络流式传输视频UDPTCPRTSPlibavGStreamerRTPlibcamerasrc GStreamer 元素 文章来源: http://raspberry.dns8844.cn/documentation 原文网址 使用 rpicam-app 通过网络流式传输视频 本节介绍来自 rpica…...
从深圳崛起的“机器之眼”:赴港乐动机器人的万亿赛道赶考路
进入2025年以来,尽管围绕人形机器人、具身智能等机器人赛道的质疑声不断,但全球市场热度依然高涨,入局者持续增加。 以国内市场为例,天眼查专业版数据显示,截至5月底,我国现存在业、存续状态的机器人相关企…...
Neo4j 集群管理:原理、技术与最佳实践深度解析
Neo4j 的集群技术是其企业级高可用性、可扩展性和容错能力的核心。通过深入分析官方文档,本文将系统阐述其集群管理的核心原理、关键技术、实用技巧和行业最佳实践。 Neo4j 的 Causal Clustering 架构提供了一个强大而灵活的基石,用于构建高可用、可扩展且一致的图数据库服务…...
【电力电子】基于STM32F103C8T6单片机双极性SPWM逆变(硬件篇)
本项目是基于 STM32F103C8T6 微控制器的 SPWM(正弦脉宽调制)电源模块,能够生成可调频率和幅值的正弦波交流电源输出。该项目适用于逆变器、UPS电源、变频器等应用场景。 供电电源 输入电压采集 上图为本设计的电源电路,图中 D1 为二极管, 其目的是防止正负极电源反接, …...
日常一水C
多态 言简意赅:就是一个对象面对同一事件时做出的不同反应 而之前的继承中说过,当子类和父类的函数名相同时,会隐藏父类的同名函数转而调用子类的同名函数,如果要调用父类的同名函数,那么就需要对父类进行引用&#…...
redis和redission的区别
Redis 和 Redisson 是两个密切相关但又本质不同的技术,它们扮演着完全不同的角色: Redis: 内存数据库/数据结构存储 本质: 它是一个开源的、高性能的、基于内存的 键值存储数据库。它也可以将数据持久化到磁盘。 核心功能: 提供丰…...
【技巧】dify前端源代码修改第一弹-增加tab页
回到目录 【技巧】dify前端源代码修改第一弹-增加tab页 尝试修改dify的前端源代码,在知识库增加一个tab页"HELLO WORLD",完成后的效果如下 [gif01] 1. 前端代码进入调试模式 参考 【部署】win10的wsl环境下启动dify的web前端服务 启动调试…...
GC1808:高性能音频ADC的卓越之选
在音频处理领域,高质量的音频模数转换器(ADC)是实现精准音频数字化的关键。GC1808,一款96kHz、24bit立体声音频ADC,以其卓越的性能和高性价比脱颖而出,成为众多音频设备制造商的理想选择。 GC1808集成了64倍…...
