文章用到的所有工具及软件成品

前言

前几天我在某宝买了一个智能手环,无奈软件中的表盘太少,所有我想着修改一下app中的资源文件。

反编译APK

这里反编译APK用apktool工具就可以。
apktool 的版本是2.4.1,反编译命令:

apktool d 安装包名

文件分析

反编译后:

\assets\80x160 下面有online ,custom俩个文件夹分布 对应 软件中的在线表盘自定义表盘

在线表盘是bin文件,也就是二进制文件,无奈以我的能力无法逆向解析其构成(如有大佬弄过还请评论指出),应该需要读java的代码。所以我侧重点在 custom 也就是自定义表盘的文件夹。
views文件下存放调用图片路径位置, 例如 0.txt 文件:

[
{
"path": "/background/0.png",
"pos": "0, 0",
"pictype": "background",
"itemtype": 254,
"color": "Black",
"show_num": 1,
"para": 0,
"w": 80,
"h": 160
},
{
"path": "/bluetooth/0",
"pos": "2, 2",
"pictype": "bluetooth",
"itemtype": 8,
"color": "White",
"show_num": 1,
"para": 11,
"w": 8,
"h": 10
},
{
"path": "/battery/0",
"pos": "64, 3",
"pictype": "电池",
"itemtype": 11,
"color": "White",
"show_num": 1,
"para": 0,
"w": 13,
"h": 8
}, {
"path": "/time/0",
"pos": "47, 14",
"pictype": "时",
"itemtype": 4,
"color": "White",
"show_num": 2,
"para": 8,
"w": 32,
"h": 25
}, {
"path": "/time/0",
"pos": "47, 43",
"pictype": "分",
"itemtype": 5,
"color": "White",
"show_num": 2,
"para": 5,
"w": 32,
"h": 25
}, {
"path": "/date/0",
"pos": "40, 73",
"pictype": "日期",
"itemtype": 18,
"color": "White",
"show_num": 5,
"para": 6,
"w": 40,
"h": 10
},
{
"path": "/am_pm/0",
"pos": "65, 85",
"pictype": "AMPM",
"itemtype": 19,
"color": "255, 255, 255",
"show_num": 1,
"para": 0,
"w": 13,
"h": 7
},
{
"path": "/slash/0",
"pos": "58, 73",
"pictype": "图片",
"itemtype": 253,
"color": "White",
"show_num": 1,
"para": 0,
"w": 0,
"h": 0
}
]

列表中包含字典,每一个字典都是一个图片,可以用来显示蓝牙图标,电源图标,小时,分钟等等。。

字段 说明
path 调用的图片路径
pos 图片位置
pictype 说明,这个值可以任意写
itemtype 用来识别对象的关键字段,后面详细解释
color 没啥用,任意填
show_num 显示的数量,例如显示的是俩位,那么就是2,而蓝牙图标一般以一个,那么就是1
para 未知,不过没什么影响
w 图片总的宽度,因为要乘上show_num值
h 图片高度,纵向

多个图片的path都是指定到目录,图片的名字从零开始依次索引。

这里着重说一下slash文件夹的下面的图片,这个图片是在息屏后开始的点亮的一瞬间使用,而且这个图片的w和h总是写0,但是实际的宽度和高度是图片的宽度和高度。
另外说明一下date文件夹,这个是用来显示日期的,显示5位是因为中间一位显示的是分隔符,分隔符显示的是12.png, 而有前俩位显示时间,后俩位显示的是日期。

itemtype

前面我说了这个是识别类型的关键字段,这个字段用来区分是显示的时间,日期,蓝牙图标等等。所以这个字段是很重要的。而我们需要知道什么数值对应什么意思图标。
这里我用的反编译dexjar包,将apk的后缀改成zip然后直接解压便可得到dex文件。然后使用d2j-dex2jar.bat反编译成jar包,然后用jd-gui打开jar包,里面有一个类就是定义itemtype类的。

public class ItemType {
public static final int ITEM_AMPM = 19;
public static final int ITEM_ANIMATION = 10;
public static final int ITEM_BACKGROUND = 254;
public static final int ITEM_BATTERY = 11;
public static final int ITEM_BLUETOOTH = 8;
public static final int ITEM_DATE = 18;
public static final int ITEM_DAY = 3;
public static final int ITEM_DISTANCE = 13;
public static final int ITEM_HEARTRATE = 9;
public static final int ITEM_HOUR = 4;
public static final int ITEM_HOUR_DIGIT = 15;
public static final int ITEM_HOUR_TEN = 14;
public static final int ITEM_KCAL = 12;
public static final int ITEM_MINUTE = 5;
public static final int ITEM_MINUTE_DIGIT = 17;
public static final int ITEM_MINUTE_TEN = 16;
public static final int ITEM_MONTH = 2;
public static final int ITEM_SHOE = 253;
public static final int ITEM_STEP = 6;
public static final int ITEM_WEEK = 7;
public static final int ITEM_YEAR = 1;
}

通过这上面的英文,可以大致理解什么数值表示什么。
这里说一下我用到的东西,例如动画ITEM_ANIMATION=10,文件夹下面的图片就是从0.png图片开始遍历,一直遍历到最后从而形成动画,是每一秒刷新一次。

表盘资源文件寻找

这里自定义表盘就是新建 txt文件,然后写入对应位置和图片路径,当然图片资源是不可能自己画的,网址。这个网站有各个手环平台的资源文件,下载下来的格式是bin, 而要解析成图片也是需要一下工具的,例如我解析的是mi-band-5的资源文件,用到的工具是MiBandWFTool_2.1.6

制作表盘工具

由于反复调节图片的位置太过费劲,我弄得头疼,所有我用opencv写了一个简单的工具,用来实时显示图片位置,更加直观。

index表示切换各个资源,在切换的时候对应的标题会改变,用来显示当前修改的是什么资源的位置,当然如果的txt中资源顺序和我的不一致可以修改78行代码:

而PosX是和横向位置,PosY纵向位置,W是单个图片的宽度,注意这里我做了转换,否者按照配置文件的w是表示总的横向宽度,H是单个图片的高度,按q退出。这里每一次调节都会实时修改txt文件。但是不会改变真正的图片大小。如果需要修改图片大小可以使用我写的convert.py的脚本。修改实际图片大小也能有效的压缩表盘文件的大小。

打包签名

添加自定义表盘资源文件后,就可以对app进行打包,同样使用 apktool,命令:

apktool b 安装包文件夹

然后会在dist文件夹下面生成一个apk,而这个apk也是不能安装的,需要签名,签名使用signapk.jar然后生成的apk才可以安装到手机上。

效果


后面俩个是我添加进去的表盘。 这里我删除了一个狗的表盘,因为我当时以为是表盘文件太多导致报错buffer size不够,后来发现是资源文件过大导致的。

其它一些细节

  1. 我写的表盘调整工具,按q退出后,会在effect,和cover文件中写入图片。这俩个图片也是重要的,会在APP自定义表盘中显示出来图片,否者图片是空白或者找不到你自定义的表盘。
  2. 资源文件不要太大,并且调节完表盘最好使用convert.py文件调节一下图片的大小,否者会导致上传表盘文件失败。
  3. 图片透明边缘过小会导致数字粘连,是因为show_num,图片拼接导致的。这种问题可以使用我写的add_border.py来填充透明边缘,这样拼接后的图片也不会显示数字太近。
  4. 更多的细节需要反复调节代码和反复修改app才能知道,毕竟我写代码也花了接近一天的时间,不可能把所有细节描述清楚。

X活手环的表盘自定义修改的更多相关文章

  1. cas sso单点登录系列4_cas-server登录页面自定义修改过程(jsp页面修改)

    转:http://blog.csdn.net/ae6623/article/details/8861065 SSO单点登录系列4:cas-server登录页面自定义修改过程,全新DIY. 目标:    ...

  2. 自定义修改Anaconda Jupyterlab Home目录

    自定义修改Anaconda Jupyterlab Home目录 最近在使用Anaconda学习数据分析和机器学习,会使用到Jupyter,但是他默认目录是用户的目录,我并没有习惯将项目和资料放在C盘, ...

  3. js实现自定义修改网页中表格信息

    项目中的打印页面,为提高用户体验,需要增自定修改表格内容的功能,以下是使用示意图(双击td标签部分的内容,可自定义修改): 以下是js插件源码,存为edit.js文件: var tbl, tbt; v ...

  4. Thinkphp框架中自定义修改success和error页面

    Thinkphp框架中自定义修改success和error页面 Thinkphp框架的默认success和error太难看,可以自定义设置,步骤如下: (注意:TP原框架中的success跳转有问题, ...

  5. SSO单点登录系列4:cas-server登录页面自定义修改过程(jsp页面修改)

    落雨 cas 单点登录 SSO单点登录系列4:cas-server登录页面自定义修改过程,全新DIY. 目标:    下面是正文: 打开cas的默认首页,映入眼帘的是满眼的中文and英文混杂体,作为一 ...

  6. PowerShell自定义修改远程桌面RDP端口

    应朋友的要求写了一个通过PowerShell修改远程桌面(Remote Desktop)端口的脚本,不复杂,启动脚本后有两个选项:1.自定义远程桌面:2.回复远程桌面的默认端口3389 发出来给有用的 ...

  7. gulp-rev-collector自定义修改rev-manifest.json后替换不成功的问题分析

    由于项目需要,我要把common.js替换成build.min.js,接着后面才用到build.min.js=>build-te234ds.min.js这样的形式替换,但是我发现怎么替换都不能把 ...

  8. iView -- TimePicker 自定义修改时间选择器选择时间面板样式

    iView官方组件展示效果: 期望的最终效果: 为什么要修改期望效果? 项目需要只选择小时,分钟跟秒的不需要,而官方并没有直接相关的小时组件或者是设置显示成小时或分钟或秒的时间选择器,因为自己直接修改 ...

  9. Confluence 6 跟踪你安装中的自定义修改

    在 Confluence 中的系统信息(System Information)部分,有一个 修改(Modification)的选项.在这个选项中列出了自你 Confluence 安装以来,你 Conf ...

  10. 如何在 Fiddler Script 中 自定义 修改 Request 、 Response

    Fiddler是一个http协议调试代理工具,方便进行http请求的拦截处理.改写请求.返回值等. 在Rules菜单下:  此次更改请求 头 ,so go to OnBeforeRequest 或者 ...

随机推荐

  1. TDengine概述以及架构模型

    TDengine TDengine是一个高效的存储.查询.分析时序大数据的平台,专为物联网.车联网.工业互联网.运维监测等优化而设计. 您可以像使用关系型数据库MySQL一样来使用它. TDengin ...

  2. Webpack与Vite热更新差异对比

    随着项目的日渐迭代,项目整体的代码量也会越来越多,从而导致项目体积越来越大:在Webpack时代,很多人会对历史项目(巨型项目)感到头疼,因为往往巨型项目在本地开发调试的时候会因为本地代码的修改触发H ...

  3. 使用pktmon抓包

    在Windows上遇到网络问题,需要抓包的时候之前我们会使用netmon和Microsoft Message Analyzer.随着时间的推移,微软已经停止了对Microsoft Message An ...

  4. 四元数Quaternion的基本运算

    技术背景 在前面一篇文章中我们介绍了欧拉角死锁问题的一些产生背景,还有基于四元数的求解方案.四元数这个概念虽然重要,但是很少会在通识教育课程中涉及到,更多的是一些图形学或者是工程学当中才会进行讲解.本 ...

  5. Kubernetes 零宕机滚动更新

    转载自:https://www.qikqiak.com/post/zero-downtime-rolling-update-k8s/ 软件世界的发展比以往任何时候都快,为了保持竞争力需要尽快推出新的软 ...

  6. 9.使用nexus3配置Python私有仓库

    搭建Python私服,我们依旧使用nexus3. 与其他私服一样的,Python私服同样有三种类型: hosted : 本地存储,便于开发者将个人的一些包上传到私服中 proxy : 提供代理其他仓库 ...

  7. switch分支

    说明: 当表达式的值等于case中的常量,则会执行其中包含的语句块 break用于跳出循环,如果不写,则直接执行下一个常量的语句块,不再去判断表达式的值是否等于下一个case的常量(case穿透) 最 ...

  8. 【Python+C#】手把手搭建基于Hugging Face模型的离线翻译系统,并通过C#代码进行访问

    前言:目前翻译都是在线的,要在C#开发的程序上做一个可以实时翻译的功能,好像不是那么好做.而且大多数处于局域网内,所以访问在线的api也显得比较尴尬.于是,就有了以下这篇文章,自己搭建一套简单的离线翻 ...

  9. TTD 专题 (第一篇):C# 那些短命线程都在干什么?

    一:背景 1.讲故事 在分析的众多dump中,经常会遇到各种奇葩的问题,仅通过dump这种快照形式还是有很多问题搞不定,而通过 perfview 这种粒度又太粗,很难找到问题之所在,真的很头疼,比如本 ...

  10. Vue3 Vite3 多环境配置 - 基于 vite 创建 vue3 全家桶项目(续篇)

    在项目或产品的迭代过程中,通常会有多套环境,常见的有: dev:开发环境 sit:集成测试环境 uat:用户接收测试环境 pre:预生产环境 prod:生产环境 环境之间配置可能存在差异,如接口地址. ...