camera人脸识别问题之二:【FFD】太阳逆光场景,人像模式后置打开美颜和滤镜,关闭heif拍摄格式对着人脸拍照,成像口红出现位置错误

【关注我,后续持续新增专题博文,谢谢!!!】

上一篇我们讲了

        这一篇我们开始讲 camera人脸识别问题之二:【FFD】太阳逆光场景,人像模式后置打开美颜和滤镜,关闭heif拍摄格式对着人脸拍照,成像口红出现位置错误8667070

目录

一、问题背景

二、问题分析过程

    2.1:基于原理分析

Camera相机人脸识别系列专题分析之六:MTK ISP6S平台人脸识别fdnode流程FdNodeImp.cpp详解Camera相机人脸识别系列专题分析之十:人脸特征检测FFD算法之低功耗libvega_face.so人脸识别检测流程详解Camera相机人脸识别系列专题分析之六:MTK ISP6S平台人脸识别fdnode流程FdNodeImp.cpp详解

    2.2 :开启人脸FFD日志开关和dump开关

Camera相机人脸识别系列专题分析之九:MTK平台FDNode三方FFD算法dump、日志开关、bypass、resize及强制不同三方FFD切换等客制化Camera相机人脸识别系列专题分析之七:MTK ISP6S平台FDNode流程FdNodeImp.cpp调试手段及客制化dump,跳帧,开关,使能,异步控制等等Camera相机人脸识别系列专题分析之九:MTK平台FDNode三方FFD算法dump、日志开关、bypass、resize及强制不同三方FFD切换等客制化

    2.3 : 先分析FFD算法返回的人脸坐标是否正常

    2.4 :确认是否FFD算法返回值存在偏移

    2.5 :确认FFD metadata值是否存在偏移

    2.6 :确认Camera HAL进程FFD是否存在问题

    2.7 :APP分析拿到的meta值

    2.8 :美颜算法输入值是否存在偏移

    2.9 :解决方案


一、问题背景

【操作步骤】【Operation steps】大太阳逆光环境下,后置人像模式--设置--打开机型水印、位置水印、时间水印、在机型水印中编辑添加自定义水印--关闭heif拍摄格式--返回预览--随机滤镜效果--调节美颜到最大美颜,预览拍照
【实际结果】【Actual results】成像口红出现位置错误
【期望结果】【Expected results】无此现象

二、问题分析过程

    2.1:基于原理分析

口红偏移,主要是人脸信息faceInfo坐标不准确导致,而faceInfo坐标涉及从底层到上层多个层面,如下流程:

camera hal进程:FDNode拿到预览YUV(会转换成FFD算法支持的size的YUV) --> YUV传入FFD算法 --> FFD算法返回人脸FFD信息 --> 传递给FDNode --> (有时可能会根据预览分辨率进行转换) --> 写入FFD metadata。

camera APP进程:人脸线程读取FFD metadata --> 解析FFD metadata --> (有时也可能需要转换) --> 传入美颜等等人脸相关算法 --> 美颜算法根据FFD信息进行美颜、口红等等处理。

流程参考:

Camera相机人脸识别系列专题分析之六:MTK ISP6S平台人脸识别fdnode流程FdNodeImp.cpp详解Camera相机人脸识别系列专题分析之十:人脸特征检测FFD算法之低功耗libvega_face.so人脸识别检测流程详解Camera相机人脸识别系列专题分析之六:MTK ISP6S平台人脸识别fdnode流程FdNodeImp.cpp详解

    2.2 :开启人脸FFD日志开关和dump开关

默认情况下,人脸信息太多,打印太多日志,会影响性能,因此人脸相关日志开关默认是关闭的,因此需要打开人脸日志开关,并复现问题来分析。打开日志开关参考:

Camera相机人脸识别系列专题分析之九:MTK平台FDNode三方FFD算法dump、日志开关、bypass、resize及强制不同三方FFD切换等客制化Camera相机人脸识别系列专题分析之七:MTK ISP6S平台FDNode流程FdNodeImp.cpp调试手段及客制化dump,跳帧,开关,使能,异步控制等等Camera相机人脸识别系列专题分析之九:MTK平台FDNode三方FFD算法dump、日志开关、bypass、resize及强制不同三方FFD切换等客制化

    2.3 : 先分析FFD算法返回的人脸坐标是否正常

1:参考HAL3一级日志关键字:相机Camera日志分析之三十一:高通Camx HAL十种流程基础分析关键字汇总(后续持续更新中)

2:复现抓取日志,并搜索"VEGA_FD|VegaFace|CUSTOM_FD|OCAM-FAD| MtkCam/fdNodeImp:"关键字

	行 114497: 01-01 03:05:38.093 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d68, id: 3, score: 0.984863, rect: [(161.333,148.000), (357.333,328.000)]行 115577: 01-01 03:05:38.129 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d69, id: 3, score: 0.984863, rect: [(161.333,148.000), (357.333,328.000)]行 115599: 01-01 03:05:38.129 13827 30357 D VEGA_FD : rect: [160.726807 147.589020 425.102661 328.000000], center(292 237)行 117606: 01-01 03:05:38.198 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d6a, id: 3, score: 0.984863, rect: [(161.333,148.000), (357.333,328.000)]行 117628: 01-01 03:05:38.198 13827 30357 D VEGA_FD : rect: [160.726807 147.589020 425.102661 328.000000], center(292 237)行 119702: 01-01 03:05:38.260 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d6b, id: 3, score: 0.984863, rect: [(161.333,148.000), (357.333,328.000)]行 119724: 01-01 03:05:38.260 13827 30357 D VEGA_FD : rect: [160.726807 147.589020 425.102661 328.000000], center(292 237)行 121201: 01-01 03:05:38.322 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d6c, id: 3, score: 0.984863, rect: [(161.333,148.000), (357.333,328.000)]行 121235: 01-01 03:05:38.322 13827 30357 D VEGA_FD : rect: [160.726807 147.589020 425.102661 328.000000], center(292 237)行 123222: 01-01 03:05:38.394 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d6d, id: 3, score: 0.984863, rect: [(156.000,154.667), (350.667,333.333)]行 123244: 01-01 03:05:38.394 13827 30357 D VEGA_FD : rect: [156.000000 154.346664 418.257202 333.333344], center(287 243)行 125042: 01-01 03:05:38.466 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d6e, id: 3, score: 0.984863, rect: [(152.000,157.333), (345.333,337.333)]行 125064: 01-01 03:05:38.466 13827 30357 D VEGA_FD : rect: [151.392334 157.333344 412.960327 337.630829], center(282 247)行 126854: 01-01 03:05:38.531 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d6f, id: 3, score: 0.984863, rect: [(144.000,157.333), (341.333,336.000)]行 126876: 01-01 03:05:38.532 13827 30357 D VEGA_FD : rect: [144.000000 157.333344 406.241882 336.000000], center(275 246)行 128176: 01-01 03:05:38.596 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d70, id: 3, score: 0.984863, rect: [(142.667,153.333), (340.000,330.667)]行 128204: 01-01 03:05:38.597 13827 30357 D VEGA_FD : rect: [142.095551 152.883286 405.225067 330.690491], center(273 241)行 129917: 01-01 03:05:38.664 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d71, id: 3, score: 0.984863, rect: [(142.667,153.333), (340.000,330.667)]行 129939: 01-01 03:05:38.665 13827 30357 D VEGA_FD : rect: [142.095551 152.883286 405.225067 330.690491], center(273 241)行 131276: 01-01 03:05:38.731 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d72, id: 3, score: 0.984863, rect: [(145.333,157.333), (344.000,336.000)]行 131298: 01-01 03:05:38.732 13827 30357 D VEGA_FD : rect: [145.333344 156.820496 411.290100 336.000000], center(278 246)行 133008: 01-01 03:05:38.795 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d73, id: 3, score: 0.984863, rect: [(153.333,154.667), (352.000,336.000)]行 133031: 01-01 03:05:38.796 13827 30357 D VEGA_FD : rect: [152.978851 154.618484 420.028503 336.000000], center(286 245)行 134433: 01-01 03:05:38.864 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d74, id: 3, score: 0.984863, rect: [(160.000,146.667), (358.667,329.333)]行 134455: 01-01 03:05:38.864 13827 30357 D VEGA_FD : rect: [159.688477 146.666672 427.194214 329.478149], center(293 238)行 136302: 01-01 03:05:38.927 13827 30357 I VegaFace: [vega_face_ret_get_face_rect:vega_face_sdk.cpp(616)] get face rect out, face: 0x20001d75, id: 3, score: 0.984863, rect: [(160.000,138.667), (360.000,320.000)]

rect: [160.726807 147.589020 425.102661 328.000000], center(292 237)类似这种日志rect就是人脸框的左上角和右下角的坐标,center就是人脸的中心位置。

                  .

    2.4 :确认是否FFD算法返回值存在偏移

确认是否FFD算法返回值存在偏移有两种方式:

  1. 我们通过dump FD YUV图结合坐标值去判断坐标是否存在偏移。
  2. 我们复现并观察这些日志打印,移动手机,使其人脸尽可能靠近上下左右4个角,查看center的值是否有偏移,是否为负值。

通过这些方式确认FFD算法返回的坐标值是准确的,并没有偏移,下面我们可以去确认FDNode的坐标或者写入metadata的值是否正常。

    2.5 :确认FFD metadata值是否存在偏移

查看FFD metadata的方式如下:

adb shell dumpsys media.camera。这个命令会dump所有的静态meta和实时meta的各种值。但FFD算法执行到写入meta,中间是有时间差的,而meta里的值会实时被覆盖,因此日志打印和meta的值是频繁更新的,观察起来就不是很方便。meta数据如下:

        com.ffd.face.info (9002004b): int32[1717][6 1 -1 137 ][26 0 0 0 ][1 0 0 0 ][459 442 424 406 ][387 369 351 333 ][315 300 283 270 ][255 244 237 229 ][228 231 234 243 ][255 267 282 297 ][312 330 346 364 ][382 400 417 435 ][451 501 522 528 ][522 511 510 517 ][522 514 493 468 ][447 427 408 376 ][376 375 375 373 ][469 475 472 463 ][463 463 460 469 ][471 463 457 459 ][502 504 501 496 ][493 498 498 496 ][477 462 468 472 ][457 463 465 463 ][411 409 391 388 ][318 333 342 337 ][340 330 313 301 ][295 294 297 304 ][319 319 319 318 ][315 318 319 321 ][468 463 465 481 ][496 510 525 540 ][553 568 580 594 ][604 615 622 627 ][628 628 630 628 ][625 619 610 600 ][588 576 562 549 ][534 519 504 489 ][474 255 255 255 ][256 259 262 267 ][271 279 286 297 ][309 321 334 351 ][369 388 406 423 ][439 453 465 475 ][486 495 502 508 ][511 516 519 522 ][522 522 276 291 ][316 342 366 421 ][447 471 493 507 ][394 393 393 393 ][357 375 393 409 ]

这里的值对应的是代码的数据结构,比如第一行的137就是代表代码里的FFD算法是137点位的。具体坐标值在最下面。

因此我们同样可以复现并观察这些dump meta打印,移动手机,使其人脸尽可能靠近上下左右4个角,查看center的值是否有偏移,是否为负值来判断。

【另外我们可以编写工具实时把137个点位信息绘制到UI界面的人脸上去,这样就更能直观看到是否偏移了】

    2.6 :确认Camera HAL进程FFD是否存在问题

通过上述方式进行不管复现观察分析,确认了底层的FFD坐标信息是正常的,并没有偏移。因此需要APP那边美颜算法进一步分析拿到的meta值是否准确,进一步看哪个阶段的问题。

    2.7 :APP分析拿到的meta值

这个比较简单,camera hal写入meta,app读取meta,一般值都是一样的,没有问题。只是读写的时间有时差。

    2.8 :美颜算法输入值是否存在偏移

最后算法开发开启算法开关分析日志,发现算法输入size是作为B2Y和MFNR的输出尺寸,而3x长焦需要进行downscale(4608x3456->4096x3072), 造成B2Y 输出结果与IPE size不一致,导致最终传入算法的faceInfo不准确,存在偏差。

    2.9 :解决方案

对这个downscale代码逻辑进行修正,避免faceInfo即可。

【关注我,后续持续新增专题博文,谢谢!!!】

下一篇讲解

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

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

相关文章

YOLO-Count:用于文本到图像生成的可微分目标计数

摘要 https://arxiv.org/pdf/2508.00728v1 我们提出了YOLO-Count,一种可微分的开放词汇目标计数模型,旨在解决通用计数挑战并实现文本到图像(T2I)生成的精确数量控制。核心贡献是"基数"图(cardinality map),这是一种新颖的回归目标…

Go 的错误处理方式深度解析—— error vs panic vs recover:机制原理与实战取舍

一、Go 的错误处理哲学Go 的设计哲学鼓励明确的、显式的错误处理方式。它不像 Java 或 Python 使用异常机制,而是采用了返回值 error 的方式,让错误成为程序流程的一部分。Go 的错误处理核心理念是: 错误是值(Errors are values&a…

官方Windows系统部署下载工具实践指南

摘要:本文介绍两款用于获取微软正版系统部署文件的工具,适用于需要快速搭建Windows环境的技术人员。所有工具均基于官方渠道实现,不涉及系统修改或激活功能。一、Windows系统镜像下载方案工具名称:Windows镜像直链下载工具 核心功…

Pandas query() 方法详解

Pandas query() 方法详解query() 是 Pandas 中一个非常强大的方法,它允许你使用字符串表达式来筛选数据行。这种方法比传统的布尔索引更简洁、更易读。基本语法df.query(expr, inplaceFalse, **kwargs)expr: 查询字符串表达式inplace: 是否原地修改 DataFrame (默认…

Linux系统层IO

1.c语言文件操作 fopen:打开文件,模式 "w"(写,覆盖)或 "r"(读)。 fwrite:fwrite(data, size, count, fp),按 size 字节写入 count 次数据。 fread…

QT中的trimmed() 方法(1)

QT中的trimmed() 方法(2) trimmed() 是 Qt 框架 中 QString 类提供的一个方法,用于 去除字符串首尾的空白字符(whitespace characters)。它的作用类似于标准 C 中的 std::string 的 trim 操作,但专为 Qt 的…

动漫软件集合分享

通过网盘分享的文件:动漫软件 链接: https://pan.baidu.com/s/1TD_OmaAZksfFxJ4PW6rS-w?pwd1234 提取码: 1234 打印动漫.apk 当鸟动漫.apk 动漫共和国【OmoFun复活】.apk 咕咕香.apk 黑猫动漫.apk 团次元【推荐】.apk 橘漫.apk 曼波.apk 萌国.apk 趣动漫.apk 三…

Mysql与Ooracle 索引失效场景对比

MySQL 和 Oracle 作为主流关系型数据库,其索引失效的场景既有共性,也因底层优化器、索引类型支持等差异存在不同。以下从常见索引失效场景对比两者的表现及原因:一、索引列上使用函数 / 表达式共性:若直接在索引列上使用函数或表达…

【unity知识】unity使用AABB(轴对齐包围盒)和OBB(定向包围盒)优化碰撞检测

文章目录前言一、AABB(轴对齐包围盒)1、基本概念2、数学表示3、Unity中的实现4、实际应用示例二、OBB(有向包围盒)1、Physics.ComputePenetration (Unity 物理引擎)1.1 基本概念1.2 Unity中的实现1.3 实际应用示例2、OBB (SAT) 手…

Numpy科学计算与数据分析专题

Numpy科学计算与数据分析 1. Numpy入门:数组操作与科学计算基础 2. Numpy入门:多平台安装与基础环境配置 3. Numpy数组创建与应用入门 4. Numpy数组属性入门:形状、维度与大小 5. Numpy数组索引与切片入门 6. Numpy数组操作入门:…

齐护机器人小智AI_MCP图形化编程控制Arduino_ESP32

齐护机器人小智AI_MCP图形化编程控制Arduino_ESP32 齐护AiTall在项目实践里,我们常常期望达成这样一种场景:借助智能体(例如小智 AI)来远程操控其他开发板上的设备,这类似于智能家居系统中智能音箱与各类家电的互动模式…

CPO-SVM分类预测+特征贡献SHAP分析,通过特征贡献分析增强模型透明度,Matlab代码实现,引入SHAP方法打破黑箱限制,提供全局及局部双重解释视角

代码功能 该Matlab代码实现了一个基于CPO-SVM冠豪猪算法优化支持向量机的数据分类模型,结合了SHAP可解释性分析,CPO选择最佳的SVM参数c和g。 SVM模型有两个非常重要的参数C与gamma。其中 C是惩罚系数,即对误差的宽容度。c越高,说明…

Failed to restart docker.service: Unit docker.service is masked.

docker.service 被标记为 "masked" 意味着 systemd 已阻止该服务被启动或运行。这通常发生在 Docker Desktop 安装过程中,因为它使用自己的服务管理机制。以下是解决方法: 解决方案: 解除服务的 mask 状态: bash sudo systemctl unmask docker.service sudo sys…

2025 蓝桥杯C/C++国B 部分题解

P12836 [蓝桥杯 2025 国 B] 翻倍 题目描述 给定 nnn 个正整数 A1,A2,…,AnA_1, A_2, \ldots, A_nA1​,A2​,…,An​,每次操作可以选择任意一个数翻倍。 请输出让序列单调不下降,也就是每个数都不小于上一个数,最少需要操作多少次?…

os标准库

os标准库os包提供了操作系统函数,但和操作系统无关。 os包的接口规定为在所有操作系统中都是一致的。 设计为Unix风格的。1. 权限说明 os标准库有大量的文件操作,在创建文件等操作中,需要指的perm。 在go语言中perm是一个uint32类型 在go语言…

QtC++ 中使用 qtwebsocket 开源库实现基于websocket的本地服务开发详解

前言 当前实时通信功能越来越受到重视,无论是在线聊天、实时数据监控还是多人协作工具,都离不开高效、稳定的实时通信技术。WebSocket 作为一种全双工通信协议,为实时通信提供了良好的解决方案。而在 QtC 开发环境中,qtwebsocket …

小程序实时保存优化

背景。避免数据存储后丢失。要求实时保存。问题:保存时出现卡断,输入的内容会被抹除。问题原因。输入频繁速度块,会影响cpu处理速度。解决方案。用户停止输入500ms后开始保存,否则不保存。这里是保存方法:当500ms以内有…

国产化Excel处理组件Spire.XLS教程:使用 C# 将 DataTable 导出为 Excel 文件

在 C# 中将 DataTable 导出为 Excel 文件,是 .NET 开发中常见的任务,广泛应用于报表生成、日志导出、系统间数据共享等场景。通过使用独立的组件库,开发者可以轻松将 DataTable 数据写入 Excel 文件,并应用格式设置,生…

C语言学习笔记——编译和链接

目录1 C程序的执行流程2 翻译环境2.1 预编译2.2 编译2.2.1 词法分析2.2.2 语法分析2.2.3 语法分析2.3 汇编2.4 链接1 C程序的执行流程 用户编写好的C程序不能直接被计算机识别并执行,在执行前,要先将源文件和头文件进行编译,生成目标文件&am…

Flink-1.19.0源码详解9-ExecutionGraph生成-后篇

《Flink-1.19.0源码详解8-ExecutionGraph生成-前篇》前篇已从Flink集群端调度开始解析ExecutionGraph生成的源码,解析了ExecutionGraph的ExecutionJobVertex节点、ExecutionVertex节点、IntermediateResult数据集、IntermediateResultPartition数据集分区与封装Task…