移动开发最新干货分享---你绝对想知道的-Totoro-截图及图像技术体系,2024年最新面试题目与答案

写在最后

很多人在刚接触这个行业的时候或者是在遇到瓶颈期的时候,总会遇到一些问题,比如学了一段时间感觉没有方向感,不知道该从哪里入手去学习,对此我整理了一些资料

如果你熟练掌握以下列出的知识点,相信将会大大增加你通过前两轮技术面试的几率!这些内容都供大家参考,互相学习。

①「Android面试真题解析大全」PDF完整高清版+②「Android面试知识体系」学习思维导图压缩包,最后觉得有帮助、有需要的朋友可以点个赞

网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。

需要这份系统化学习资料的朋友,可以戳这里获取

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

MediaCodec mcodec = MediaCodec.createEncoderByType(“video/avc”);//创建解码器
Surface surface = codec.createInputSurface();//构造目标Surface
SurfaceControl.setDisplaySurface(display, surface);//通过反射SurfaceControl,将构造的Surface设置到系统
int outputBufferId = codec.dequeueOutputBuffer(bufferInfo, -1);//开始解码
//判断有效帧

Bitmap bitmap = mediaMetadataRetriever.getFrameAtTime(index);//获取屏幕bitmap值
bitmap.compress(Bitmap.CompressFormat.JPEG, quailty, fos);//保存截图

//截图回传到PC接口层

然后就是打包程序,利用系统 app_process 服务,可以避开各种权限弹窗问题,直接运行程序,即可获取到屏幕截图。
目前该方式已全面应用到 Totoro 底层截图方案,可以兼容安卓 5.0-10 版本,但是仍然有改进地方,后续还可从以下几点进一步优化:

  • 视频流有效帧判断逻辑优化,减少截图时间。
  • 目前仍然需要一次手机端的文件保持读写逻辑,后续可考虑读流方式,直接获取图片 Base64 值。
  • 可执行文件参数标准化,可满足多场景技术输出。
B.备用兜底方案

以上 A 方法主要针对 5.0+ 的安卓设备,且针对个别 OPPO、VIVO 设备开启了系统恶意录屏功能,就会造成录屏功能限制,引起截图失败。针对这部分的设备,我们设想 Android 能否像 Linux 系统一样,绕过 Java 层权限限制,直接从C层读取操作系统 framebuffer(Linux 设备/dev/graphics/fb0),来获取屏幕图像。

期间调研了开源的 minicap 录屏方案,发现 Surface 方案在个别设备不能兼容情况下, minicap 依然可以使用,其底层原理就是采用 NDK 开发的工具,直接读取操作系统 framebuffer,为了不重复造轮子,决定把 minicap 工具中的手机端的服务单独剥离出来集成到 Totoro,作为备用兜底方法提供截图能力。

String cmd = String.format(“adb -s %s shell LD_LIBRARY_PATH=/data/local/tmp /data/local/tmp/minicap -P %sx%s@%sx%s/0 -Q 90 -s -t > %s”, deviceId, w, h, w, h, localPathFile);

按照上面命令单独调用 minicap 工具截图,并从流中解析到图片保持到制定目录,经大量测试,该命令并不一定稳定,有时会报格式错误,有时会报流处理错误,所以我们添加了降级方案,如以下命令。

String cmd = String.format(“adb -s %s shell “LD_LIBRARY_PATH=/data/local/tmp /data/local/tmp/minicap -P %sx%s@%sx%s/0 -Q 90 -s -t > /sdcard/.totoro/%s””, deviceId, w, h, w, h, name);

//然后将图片Pull到PC上制定目录

两种技术方案相互降级搭配使用,这样正好弥补了 Java 层 Surface 方案的一些可能失败场景,作为兜底方法集成到了 Totoro 框架中,目前为止暂未发现两种方法都失败场景,保障了截图能力的底盘稳定性。

业务多场景支持

1.基础截图场景

通过以上相关多层技术方案兼容,Totoro 目前可以提供稳定的基础截图能力,业务层无需关注底层的具体技术实现方案或兜底方案,只需要调用一个 Totoro 实验 SDK 暴露的 API 即可。

String path = BizUtils.saveScreen(name);

2.长截屏技术方案

长截图能力一直是业务方提出的痛点需求,一直到 19 年末我们才抽出时间弥补了 Totoro 这块能力缺失。
起先,先调研了行业内其他实现方案,基本思路都是滑动截图,然后合并多张截图,最后生成长截图。然而,难点在多张截图的完美合并,针对移动端的页面截图,存在页头、页尾、小 banner 更新、小红点等多重影响,给长截图的实现增加了不少难度。

可行方案分析:

  1. 直接利用第三方拼接工具。需要添加额外依赖,其在移动端个别极限场景拼接存在问题,维护成本高。
  2. 利用算法部门资源,特征值直接匹配。需要添加算法库,且要推动算法部门不断迭代更新,后续更新可能不及时。
  3. 自己实现一套,难度大,初期成本高。需要兼容移动端页面各种情况,但是后续维护成本低,升级方便且及时。

权衡利弊后,最终我们采用了方案 3,决定自己实现了一套针对移动端截图特征的拼接能力,采用了自研像素行灰度值末尾优先对比技术方案,核心逻辑思路是默认向上滑动生成的图片组,两两从底部优先开始对比行像素的灰度值,找到拼接点和裁剪点。为了减少噪点及个别红点、红线、小 banner、及底部导航栏影响,在不同的对比点及区域添加了对应的参数。其核心代码思路如下:

public static File mergeImg(File imgA, File imgB, String mergedImgPathName) {
int[][] listA = getPX(imgA);//获取像素数组
int samePartEnd = 0, sameBottom = srcALen;//定义查找目标位置
int samePart = mergeLen >> 2;//定义相似颗粒
for (int al = Math.max(0, listA.length - mergeLen + (samePart >> 1)), l = listA.length - 1; l >= al; l–) {
for (int x = mergeLen - (listA.length - l), y = Math.max(0, (samePart >> 1)); x >= y; x–) {
if (compareRowPx(listA[l], listB[x])) {// 对比行灰度相似度
//找到基础对比点
for (int i = 0, partLen = (l == listA.length - 1) ? samePart : samePart >> 1; i < partLen; i++) {
//寻找拼接点
if (compareRowPx(listA[curA], listB[curB])) {
if (i == partLen - 1) {
//相同区域达到阀值,找到拼接点
samePartEnd = x;
sameBottom = l - 1;
break;
} else {
//寻找底部相同区域,如底部导航Tab栏
break;
}
}
if (matchedBottom || samePartEnd > 0) {
//拼接参数找到,提取结束循环
break;
}
}
}
}

String fileSuffixA = getFileRealExt(imgA);//读取二进制流,获取原始图文件真实后缀
String fileSuffixB = getFileRealExt(imgB);
String fileSuffixC = mergedImgPathName.substring(1 + mergedImgPathName.lastIndexOf(“.”));
if (samePartEnd == mergeLen - 1) {
//图片相同,直接返回第一张图片
imgA.renameTo(file);
return file;
}
//开始合并逻辑
int newY = srcALen - (srcALen - sameBottom) + (mergeLen - samePartEnd);
…//读取原始图片值
if (sameBottom > 0) {
// 去除底部导航tab栏
} else {
//没有底部操作tab栏
newA = reader.read(0);
}
…//重新拼接图片
imgNew.setRGB(0, newA.getHeight(), width, newB.getHeight(), imgArrayB, 0, width);
ImageIO.write(imgNew, fileSuffixC, file);
…//其他资源回收
return file;
}

效果图如下:

totoro - 长图.png

该方案目前已全量上线,并且满足了目前业务方需求,在遇到长截图拼接有重叠或缺少问题时,也可以通过调节对比参数,快速优化合并逻辑代码,达到了既定研发目标。

3.局部控件截图

在自动化过程中,有些业务需要获取某个控件的截图, iOS 端可以通过 WDA 相关接口实现,但是安卓端是没有现成方案的。因此,Totoro 采用了按照坐标截图切割方式,结合控件坐标信息,可以在 PC 端实现一套局部控件获取方法。该 API 可以同时适用到
iOS 和安卓双平台,局部控件截图核心实现思路:

src = BizUtils.saveScreen(name);
WebElement element = driver.findElement(By);
…//根据element获取到element的坐标信息
ImageCheckUtils.imageCut( src, dest, x, y, width, height);//根据坐标信息切图,获取到控件截图dest文件

4.多屏幕截屏

目前 Totoro 中只集成了 adb 原生方式,用来为一些支付 IoT 设备,提供多屏幕截图能力。

#附屏幕截屏
adb shell screencap -d /dev/graphics/fb1 fb1.png
#主屏幕截屏
adb shell screencap -d /dev/graphics/fb0 fb0.png

后续根据需求反馈,会调研采用 UIAutomater 或 Surface 方式实现。

图像智能算法分析

Totoro 借助兄弟团队(工程数据技术组)的算法能力,针对截图实现了页面智能分析、检测等能力,完成了图片相关技术体系小闭环。智能算法能力集成可以归类为以下三种。

1.控件分析

Totoro -图片2.png

如上截图所示,可以通过以下 API 获取页面控件信息,可识别控件类型如 button、image、label、progress、switch、more、editView、popUp、checkBox、return、close 等。

2.页面异常检测

异常检测能力可抽象分为通用异常和业务异常,具体说明如下:

  • 通用异常分析,如:黑白屏、加载失败、图片或文字截断,控件排列重叠等常见页面 UI 问题;
  • 业务异常分析,如:业务弹窗、授权弹窗阻断等,且更加不同的业务异常场景需求,可定制化服务。

Totoro 中可通过一个接口获取页面异常信息,业务中通过自动化的检测,完成了之前很多无法实现的自动化场景。

3.业务场景识别

题外话

我在一线互联网企业工作十余年里,指导过不少同行后辈。帮助很多人得到了学习和成长。

我意识到有很多经验和知识值得分享给大家,也可以通过我们的能力和经验解答大家在IT学习中的很多困惑,所以在工作繁忙的情况下还是坚持各种整理和分享。但苦于知识传播途径有限,很多程序员朋友无法获得正确的资料得到学习提升,故此将并将重要的Android进阶资料包括自定义view、性能优化、MVC与MVP与MVVM三大框架的区别、NDK技术、阿里面试题精编汇总、常见源码分析等学习资料。

【Android思维脑图(技能树)】

知识不体系?这里还有整理出来的Android进阶学习的思维脑图,给大家参考一个方向。

希望我能够用我的力量帮助更多迷茫、困惑的朋友们,帮助大家在IT道路上学习和发展~

网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。

需要这份系统化学习资料的朋友,可以戳这里获取

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。**

需要这份系统化学习资料的朋友,可以戳这里获取

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

  • 27
    点赞
  • 35
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值