解决recovery页面反转的问题

1.前言

在android 10.0的系统rom定制化开发工作中,在系统中recoverv的页面也是相关重要的一部分,在系统recovery ta升级等功能,都是需要recoverv功能的,在某些产品定制化中
在recovery的时候,发现居然旋转了180度,接下来分析下recovery关于屏幕显示方向的相关源码,来修改这个功能

2.recovery页面旋转180度问题的解决方案的核心类

     bootable/recovery/minui/include/minui/minui.hboottable/recovery/minui/graphics.cpp

3.recovery页面旋转180度问题的解决方案的核心功能分析和实现

recovery页面旋转180度问题的解决方案的核心功能实现中,Android10.0的Recovery中的相关系统源码中,recoverv是以bootablerecovery下的minui库作为基础,采用的是直接存取framebuffer的万式,来完成recovery中所需的各种UI的绘制。
在recoverv的源码中,跟ui显示相关的代码的大致结构为:
boottable/recovery/minui下resources.cpp,graphics.cpp
其中resources.cpp提供的api主要用于图片资源的读取和加载
graphics.cpp负责具体完成各类ui的绘制既然graphics.cpp是负责各类UI的绘制那么旋转方向的修改 就要从这里入手了。

   #include "graphics.h"#include <stdint.h>#include <stdio.h>#include <stdlib.h>#include <string.h>#include <memory>#include <android-base/properties.h>#include "graphics_adf.h"#include "graphics_drm.h"#include "graphics_fbdev.h"#include "minui/minui.h"...int gr_measure(const GRFont* font, const char* s) {if (font == nullptr) {return -1;}return font->char_width * strlen(s);}int gr_font_size(const GRFont* font, int* x, int* y) {if (font == nullptr) {return -1;}*x = font->char_width;*y = font->char_height;return 0;}// Increments pixel pointer right, with current rotation.static void incr_x(uint32_t** p, int row_pixels) {if (rotation == GRRotation::LEFT) {*p = *p - row_pixels;} else if (rotation == GRRotation::RIGHT) {*p = *p + row_pixels;} else if (rotation == GRRotation::DOWN) {*p = *p - 1;} else {  // GRRotation::NONE*p = *p + 1;}}// Increments pixel pointer down, with current rotation.static void incr_y(uint32_t** p, int row_pixels) {if (rotation == GRRotation::LEFT) {*p = *p + 1;} else if (rotation == GRRotation::RIGHT) {*p = *p - 1;} else if (rotation == GRRotation::DOWN) {*p = *p - row_pixels;} else {  // GRRotation::NONE*p = *p + row_pixels;}}void gr_fill(int x1, int y1, int x2, int y2) {x1 += overscan_offset_x;y1 += overscan_offset_y;x2 += overscan_offset_x;y2 += overscan_offset_y;if (outside(x1, y1) || outside(x2 - 1, y2 - 1)) return;int row_pixels = gr_draw->row_bytes / gr_draw->pixel_bytes;uint32_t* p = PixelAt(gr_draw, x1, y1, row_pixels);uint8_t alpha = static_cast<uint8_t>(((gr_current & alpha_mask) >> 24));if (alpha > 0) {for (int y = y1; y < y2; ++y) {uint32_t* px = p;for (int x = x1; x < x2; ++x) {*px = pixel_blend(alpha, *px);incr_x(&px, row_pixels);}incr_y(&p, row_pixels);}}}int gr_init_font(const char* name, GRFont** dest) {GRFont* font = static_cast<GRFont*>(calloc(1, sizeof(*gr_font)));if (font == nullptr) {return -1;}int res = res_create_alpha_surface(name, &(font->texture));if (res < 0) {free(font);return res;}// The font image should be a 96x2 array of character images.  The// columns are the printable ASCII characters 0x20 - 0x7f.  The// top row is regular text; the bottom row is bold.font->char_width = font->texture->width / 96;font->char_height = font->texture->height / 2;*dest = font;return 0;}int gr_init() {// pixel_format needs to be set before loading any resources or initializing backends.std::string format = android::base::GetProperty("ro.minui.pixel_format", "");if (format == "ABGR_8888") {pixel_format = PixelFormat::ABGR;} else if (format == "RGBX_8888") {pixel_format = PixelFormat::RGBX;} else if (format == "BGRA_8888") {pixel_format = PixelFormat::BGRA;} else {pixel_format = PixelFormat::UNKNOWN;}int ret = gr_init_font("font", &gr_font);if (ret != 0) {printf("Failed to init font: %d, continuing graphic backend initialization without font file\n",ret);}auto backend = std::unique_ptr<MinuiBackend>{ std::make_unique<MinuiBackendAdf>() };gr_draw = backend->Init();if (!gr_draw) {backend = std::make_unique<MinuiBackendDrm>();gr_draw = backend->Init();}if (!gr_draw) {backend = std::make_unique<MinuiBackendFbdev>();gr_draw = backend->Init();}if (!gr_draw) {return -1;}gr_backend = backend.release();int overscan_percent = android::base::GetIntProperty("ro.minui.overscan_percent", 0);overscan_offset_x = gr_draw->width * overscan_percent / 100;overscan_offset_y = gr_draw->height * overscan_percent / 100;gr_flip();gr_flip();if (!gr_draw) {printf("gr_init: gr_draw becomes nullptr after gr_flip\n");return -1;}std::string rotation_str =android::base::GetProperty("ro.minui.default_rotation", "ROTATION_NONE");if (rotation_str == "ROTATION_RIGHT") {gr_rotate(GRRotation::RIGHT);} else if (rotation_str == "ROTATION_DOWN") {gr_rotate(GRRotation::DOWN);} else if (rotation_str == "ROTATION_LEFT") {gr_rotate(GRRotation::LEFT);} else {  // "ROTATION_NONE" or unknown stringgr_rotate(GRRotation::NONE);}rotation = GRRotation::RIGHT;//add codeif (gr_draw->pixel_bytes != 4) {printf("gr_init: Only 4-byte pixel formats supported\n");}return 0;}void gr_rotate(GRRotation rot) {rotation = rot;}

recoverv页面旋转180度问题的解决方案的核心功能实现中,从graphics.cpp中的上述源码中,可以看出 r get width (const GRSurtace?surface)是获取屏幕的宽度
gr get height(const GRSurface* surface) 获取屏幕的高度
gr init font(const char* name.GRFont** dest) 获取字体大小
gr init() 主要是设置RGB 和 屏幕旋转方向,gr cear()清除一些绘制屏幕参数,重新绘制屏幕显示相关的参数接下来看下相关的设置recoverv的方向的相关代码的分析
gr rotate(DEFAULT ROTATION):
在gr init()的方法中中的gr rotate(DEFAULT ROTATION):设置屏幕的方向为默认方向而在minui.h中定义了recoverv方向的相关参数,如下

enum GRRotation {ROTATION_NONE = 0,ROTATION_RIGHT = 1,//90ROTATION_DOWN = 2,//180ROTATION_LEFT = 3,//270};

recovev页面旋转180度问题的解决方案的核心功能实现中,根据GRRotation 的相关参数可以得知,ROTATION RIGHT就是屏幕旋转90度,而ROTATION DOWN就是屏幕旋转180度,而ROTATION LEFT就是屏幕旋转270度,
所以设置横屏上下翻转就需要把屏幕方向修改为ROTATION LEFT就可以了具体修改为:

int gr_init() {....std::string rotation_str =android::base::GetProperty("ro.minui.default_rotation", "ROTATION_NONE");if (rotation_str == "ROTATION_RIGHT") {gr_rotate(GRRotation::RIGHT);} else if (rotation_str == "ROTATION_DOWN") {gr_rotate(GRRotation::DOWN);} else if (rotation_str == "ROTATION_LEFT") {gr_rotate(GRRotation::LEFT);} else { // "ROTATION_NONE" or unknown stringgr_rotate(GRRotation::NONE);}+ rotation = GRRotation::LEFT;//add code....}

recover页面旋转180度问题的解决方案的核心功能实现中,在上述的graphics.cpp中的上述源码中分析得知,在gr init) 主要是设置RGB和 屏幕旋转方向,所以就是根据返回的
rotation的值来判断当前屏幕的旋转方向的,所以通过上述的修改方法,在gr init()
增加rotation = GRRotation:LEFT://add code来作为当前屏幕的旋转方法,就确保旋转180度,就是实现了功能要求

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

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

相关文章

javaee thymeleaf简介

thymeleaf 使用thymeleaf可以实现动静分离&#xff0c;jsp页面是无法直接用浏览器打开的&#xff0c;使用了thymeleaf后&#xff0c;页面是html格式&#xff0c;可以直接用浏览器打开&#xff0c;这样可以方便测试人员进行测试。

【C++】一文带你走入vector

文章目录 一、vector的介绍二、vector的常用接口说明2.1 vector的使用2.2 vector iterator的使用2.3 vector空间增长问题2.4 vector 增删查改 三、总结 ヾ(๑╹◡╹)&#xff89;" 人总要为过去的懒惰而付出代价ヾ(๑╹◡╹)&#xff89;" 一、vector的介绍 vector…

golang gin——文件上传(单文件,多文件)

文件上传 单文件上传 从form-data获取文件 package uploadimport ("github.com/gin-gonic/gin""net/http" ) // 单文件上传&#xff0c;多文件上传 func Upload(c *gin.Context) {file, _ : c.FormFile("file") // file为字段名dst : "…

背包问题学习笔记-混合背包问题

题意描述&#xff1a; 有 N 种物品和一个容量是 V 的背包。物品一共有三类&#xff1a;第一类物品只能用1次&#xff08;01背包&#xff09;&#xff1b; 第二类物品可以用无限次&#xff08;完全背包&#xff09;&#xff1b; 第三类物品最多只能用 si 次&#xff08;多重背包…

nodejs开发环境搭建

Nodejs是一个开源的、跨平台JavaScript运行时环境&#xff0c;其使用V8引擎对JavaScript脚本执行解释&#xff0c;在前后端分离的应用架构设计中&#xff0c;其既能支持web页面服务应用的开发、也能支持后端接口服务应用的开发&#xff0c;类似于Java语言的J2EE运行时环境&…

安装matplotlib__pygame,以pycharm调入模块

安装pip 安装matplotlib 安装完毕&#xff0c;终端输入pip list检查 导入模块出现bug&#xff0c;发现不是matplotlib包的问题&#xff0c;pycharm版本貌似不兼容&#xff0c;用python编辑器可正常绘图&#xff0c;pygame也可正常导入。 ​​​​​​​ pycharm版本问题解决 终…

MarqueeView - 跑马灯

官网 https://github.com/sunfusheng/MarqueeView 项目简介 俗名&#xff1a;可垂直跑、可水平跑的跑马灯&#xff1b; 学名&#xff1a;可垂直翻、可水平翻的翻页公告 Gradle compile com.sunfusheng:MarqueeView:<latest-version> 属性 Attribute 属性 Descrip…

Java开发一些偏冷门的面试题

文章目录 1.进程间的通信&#xff0c;线程间的通信首先可以先回答进程、线程和协程关于线程和进程通信 2.MySQL中的缓存情况&#xff0c;以及缓存命中率查询 主要从别人的面经那里看来的&#xff0c;以及自己被问住的一些面试题。 拿出来给自己做记录&#xff0c;也顺便给大家做…

【Spring笔记02】Spring中的IOC容器和DI依赖注入介绍

这篇文章&#xff0c;主要介绍一下Spring中的IOC容器和DI依赖注入两个概念。 目录 一、IOC控制反转 1.1、什么是IOC 1.2、两种IOC容器 &#xff08;1&#xff09;基于BeanFactory的IOC容器 &#xff08;2&#xff09;基于ApplicationContext的IOC容器 二、DI依赖注入 2.…

stm32-SPI协议

SPI协议详解&#xff08;图文并茂超详细&#xff09; SPI通讯协议 于是我们想有没有更好一点的串行通讯方式&#xff1b;相比较于UART&#xff0c;SPI的工作方式略有不同。 SPI是一个同步的数据总线&#xff0c;也就是说它是用单独的数据线和一个单独的时钟信号来保证发送端和…

RT1 RT2 RTX() 学习

RT-1&#xff1a; 初生代的 ‘视觉-语言-动作模型’ 作品 RT-2: RT1使用130k条机器人遥操作数据训练&#xff0c;展示出了其处理多种任务的能力和很强的泛化能力。但其通用性仍受限于数据集的大小。 若想要得到一个表现出当前LLMs能力的机器人大模型&#xff0c;收集数以亿计…

MySQL中的 增 删 查 改(CRUD)

目录 新增 insert into 表名 value(数据&#xff0c;数据),.......&#xff1b; insert into 表名&#xff08;列1&#xff0c;列2.....&#xff09; value(数据&#xff0c;数据),.......&#xff1b; datatime 类型的数据如何插入&#xff1f; 查询 select * from 表名…

动态调整系统主题色(4): CssVar 与 Variant 方案的探索

动态调整系统主题色(4): CssVar 与 Variant 方案的探索 动态调整系统主题色(4): CssVar 与 Variant 方案的探索 前言方案的介绍与比较 CssVar (CSS 变量方案)CSS 变量方案与 tailwindcss 的结合Variant 方案 2种方案在小程序上的示例之前的几篇 前言 这篇已经是动态调整系统…

Docker 的数据管理与Docker 镜像的创建

------------------Docker 的数据管理--------------------- 管理 Docker 容器中数据主要有两种方式&#xff1a;数据卷&#xff08;Data Volumes&#xff09;和数据卷容器&#xff08;DataVolumes Containers&#xff09;。 1&#xff0e;数据卷 数据卷是一个供容器使用的特殊…

什么是Vue的JSX语法?如何使用JSX语法

Vue的JSX语法&#xff1a;更接近JavaScript的模板语言 Vue.js是一个流行的JavaScript框架&#xff0c;用于构建交互式的Web应用程序。虽然Vue通常使用模板语法来构建用户界面&#xff0c;但它也提供了JSX语法的支持&#xff0c;使开发人员能够更接近JavaScript的表达方式来构建…

分享几个优秀开源免费管理后台模版,建议收藏!

大家好&#xff0c;我是 jonssonyan 今天和大家分享一些免费开源的后台管理页面&#xff0c;帮助大家快速搭建前端页面。为什么要用模板&#xff1f;道理很简单&#xff0c;原因是方便我们快速开发。我们不应该花太多的时间在页面调整上&#xff0c;而应该把精力放在核心逻辑和…

re学习(37)DASCTF 2023 0X401七月暑期挑战赛 controflow

程序通过改变栈里面的返回地址来控制程序的控制流 从而达到混淆的效果 左侧有许多被hook的函数 在每个函数开头设置断点 然后观察程序的运行流程 会发现输入的数据会进行 异或 相加 异或 相减 相乘 异或等操作 要注意部分运算的索引是 从[10]开始的 具体思路参考&#xf…

黑豹程序员-架构师学习路线图-百科:JSON替代XML

文章目录 1、数据交换之王2、XML的起源3、JSON诞生4、什么是JSON 1、数据交换之王 最早多个软件之间使用txt进行信息交互&#xff0c;缺点&#xff1a;纯文本&#xff0c;无法了解其结构&#xff1b;之后使用信令&#xff0c;如&#xff1a;电话的信令&#xff08;拨号、接听、…

三十、【进阶】B-Trees的演变过程

1、索引结构 &#xff08;1&#xff09;二叉树 &#xff08;2&#xff09;B-Tree树 B-Tree树最大度数为5&#xff0c;代表每一个节点最多存储4个key(每个节点最多存储4个数据)&#xff0c;5个指针(可以指向5个子节点)。 2、演变过程&#xff08;最大度数为5&#xff09; &…

数据挖掘(3)特征化

从数据分析角度&#xff0c;DM分为两类&#xff0c;描述式数据挖掘&#xff0c;预测式数据挖掘。描述式数据挖掘是以简介概要的方式描述数据&#xff0c;并提供数据的一般性质。预测式数据挖掘分析数据建立模型并试图预测新数据集的行为。 DM的分类&#xff1a; 描述式DM&#…