http://www.manong.net/forum.php?mod=viewthread&tid=61
1、简介
由于部分用户对洋文
recovery
会产生头痛症状的
bug
, 决定汉化
recovery
。
2、基础知识
1
)编码
ASCII
、
GB2312
、
Unicode
、
UTF8
ASCII
ASCII
码使用指定的
7
位或
8
位二进制数组合来表示
128
或
256
种可能的字符。标准
ASCII
码也叫基础
ASCII
码,使用
7
位二进制数来表示所有的大写和小写字母,数字
0
到
9
、标点符号, 以及在美式英语中使用的特殊控制字符。其中:
0
~
31
及
127(
共
33
个
)
是控制字符或通信专用字符(其余为可显示字符),如控制符:
LF
(换行)、
CR
(
回车)、
FF
(换页)、
DEL
(删除)、
BS
(退格
)
、
BEL
(振铃)等;通信专用字符:
SOH
(文头)、
EOT
(文尾)、
ACK
(确认)等;
ASCII
值为
8
、
9
、
10
和
13
分别转换为退格、制表、换行和回车字符。它们并没有特定的图形显示,但会依不同的应用程序,而对文本显示有不同的影响。
32
~
126(
共
95
个
)
是字符
(32sp
是空格),其中
48
~
57
为
0
到
9
十个阿拉伯数字
65
~
90
为
26
个大写英文字母,
97
~
122
号为
26
个小写英文字母,其余为一些标点符号、运算符号等。
同时还要注意,在标准
ASCII
中,其最高位
(b7)
用作
奇偶校验位。所谓奇偶校验,是指在代码传送过程中用来检验是否出现错误的一种方法,一般分奇校验和偶校验两种。奇校验规定:正确的代码一个字节中
1
的个数必须是奇数,若非奇数,则在最高位
b7
添
1
;偶校验规定:正确的代码一个字节中
1
的个数必须是偶数,若非偶数,则在最高位
b7
添
1
。
后
128
个称为
扩展ASCII码,目前许多基于
x86的系统都支持使用扩展(或
“
高
”
)
ASCII
。扩展
ASCII
码允许将每个字符的第
8
位用于确定附加的
128
个特殊符号字符、外来语字母和图形符号。
file:///C:\Users\ADMINI~1\AppData\Local\Temp\ksohtml\wps_clip_image-16626.png
图
1 ASCII
表
GB2312
GB2312码是中华人民共和国国家汉字信息交换用编码,全称《信息交换用汉字编码字符集
——
基本集》,由国家标准总局发布,
1981
年
5
月
1
日实施,通行于大陆。新加坡等地也使用此编码。
它是计算机可以识别的
编码,适用于汉字处理、汉字通信等系统之间的信息交换。基本集共收入汉字
6763
个和非汉字图形字符
682
个。整个字符集分成
94
个区,每区有
94
个位。每个区位上只有一个字符,因此可用所在的区和位来对汉字进行编码,称为
区位码。
每个汉字也都有在GB2312
中的区位码,用两个字节表示。
汉字编码范围,区码:B0 ~ F7
,位码:
A1 ~ FE
汉字编码后续标准如,
GB18030
, 对
GB2312
完全兼容。
code +0 +1 +2 +3 +4 +5 +6 +7 +8 +9 +A +B +C +D +E +F
B0A0
啊 阿 埃 挨 哎 唉 哀 皑 癌 蔼 矮 艾 碍 爱 隘
B0B0
鞍 氨 安 俺 按 暗 岸 胺 案 肮 昂 盎 凹 敖 熬 翱
B0C0
袄 傲 奥 懊 澳 芭 捌 扒 叭 吧 笆 八 疤 巴 拔 跋
B0D0
靶 把 耙 坝 霸 罢 爸 白 柏 百 摆 佰 败 拜 稗 斑
B0E0
班 搬 扳 般 颁 板 版 扮 拌 伴 瓣 半 办 绊 邦 帮
B0F0
梆 榜 膀 绑 棒 磅 蚌 镑 傍 谤 苞 胞 包 褒 剥
...
...
...
code +0 +1 +2 +3 +4 +5 +6 +7 +8 +9 +A +B +C +D +E +F
F7A0
鳌 鳍 鳎 鳏 鳐 鳓 鳔 鳕 鳗 鳘 鳙 鳜 鳝 鳟 鳢
F7B0
靼 鞅 鞑 鞒 鞔 鞯 鞫 鞣 鞲 鞴 骱 骰 骷 鹘 骶 骺
F7C0
骼 髁 髀 髅 髂 髋 髌 髑 魅 魃 魇 魉 魈 魍 魑 飨
F7D0
餍 餮 饕 饔 髟 髡 髦 髯 髫 髻 髭 髹 鬈 鬏 鬓 鬟
F7E0
鬣 麽 麾 縻 麂 麇 麈 麋 麒 鏖 麝 麟 黛 黜 黝 黠
F7F0
黟 黢 黩 黧 黥 黪 黯 鼢 鼬 鼯 鼹 鼷 鼽 鼾 齄
unicode
通用字符集
UTF8
可变长编码,汉字
3
字节表示。具体可参考
RFC3629
。
D2BB 4E00 E4 B8 80
一
B6A1 4E01 E4 B8 81
丁
C6DF 4E03 E4 B8 83
七
CDF2 4E07 E4 B8 87
万
D5C9 4E08 E4 B8 88
丈
C8FD 4E09 E4 B8 89
三
C9CF 4E0A E4 B8 8A
上
CFC2 4E0B E4 B8 8B
下
D8A2 4E0C E4 B8 8C
丌
...
...
...
F6B8 9F88 E9 BE 88
龈
F6B9 9F89 E9 BE 89
龉
F6BA 9F8A E9 BE 8A
龊
C8A3 9F8B E9 BE 8B
龋
F6BB 9F8C E9 BE 8C
龌
C1FA 9F99 E9 BE 99
龙
B9A8 9F9A E9 BE 9A
龚
EDE8 9F9B E9 BE 9B
龛
B9EA 9F9F E9 BE 9F
龟
D9DF 9FA0 E9 BE A0
龠
2
)
OpenGL
OpenGL
(全写
Open Graphics Library
)是个定义了一个跨编程语言、跨平台的编程接口的规格,它用于三维图象(二维的亦可)。
OpenGL
是个专业的图形程序接口,是一个功能强大,调用方便的底层图形库。
file:///C:\Users\ADMINI~1\AppData\Local\Temp\ksohtml\wps_clip_image-23313.png
图
2 OpenGL
渲染管线
file:///C:\Users\ADMINI~1\AppData\Local\Temp\ksohtml\wps_clip_image-7388.png
图
3
像素数据处理流程简图
1
、像素操作
对数组像素进行操作
2
、纹理装配
生成纹理
3
、光栅化
截取字符纹理片段
,
生成纹理单元
4
、片段操作
对纹理单元进行操作,(着色,各种测试(
alpha..
),雾化)
3
)
Pixelflinger
Pixelflinger
是
Android
系统中为
OpenGL ES
引擎提供的一套软件渲染器(
renderer
)。
OpenGL ES
引擎提供了一系列基础绘图功能。这些功能包括定义各种颜色格式像素位置、画点画线、绘制矩形及三角形、填充纹理等等。由于
OpenGL ES
相当于一个状态机,配置
OpenGL Es
状态的函数也均由
Pixelflinger
提供。
Pixelflinger涉及到的代码路径:
1
2
3
|
system
/core/libpixelflinger
system
/core/include/libpixelflinger
system
/core/include/
private
/pixelflinger
|
Pixelflinger
有两个主要结构体
1
2
|
struct
context_t
//include/private/pixelflinger/ggl_context.h
Struct GGLContext
//include/pixelflinger/pixelflinger.h
|
其中context_t
是
pixelflinger
里最主要的结构体,
GGLContext
提供了外部操作引用接口。
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
|
typedef
struct
{
// immediate rendering
void
(*pointx)(
void
*con,
const
GGLcoord* v, GGLcoord r);
void
(*linex)(
void
*con,
const
GGLcoord* v0,
const
GGLcoord* v1, GGLcoord width);
void
(*recti)(
void
* c, GGLint l, GGLint t, GGLint r, GGLint b);
void
(*trianglex)(
void
* c,
GGLcoord
const
* v0, GGLcoord
const
* v1, GGLcoord
const
* v2);
// scissor
void
(*scissor)(
void
* c, GGLint x, GGLint y, GGLsizei width, GGLsizei height);
// Set the textures and color buffers
void
(*activeTexture)(
void
* c, GGLuint tmu);
void
(*bindTexture)(
void
* c,
const
GGLSurface* surface);
void
(*colorBuffer)(
void
* c,
const
GGLSurface* surface);
void
(*readBuffer)(
void
* c,
const
GGLSurface* surface);
void
(*depthBuffer)(
void
* c,
const
GGLSurface* surface);
void
(*bindTextureLod)(
void
* c, GGLuint tmu,
const
GGLSurface* surface);
// enable/disable features
void
(*enable)(
void
* c, GGLenum name);
void
(*disable)(
void
* c, GGLenum name);
void
(*enableDisable)(
void
* c, GGLenum name, GGLboolean en);
// specify the fragment's color
void
(*shadeModel)(
void
* c, GGLenum mode);
void
(*color4xv)(
void
* c,
const
GGLclampx* color);
// specify color iterators (16.16)
void
(*colorGrad12xv)(
void
* c,
const
GGLcolor* grad);
// specify Z coordinate iterators (0.32)
void
(*zGrad3xv)(
void
* c,
const
GGLfixed32* grad);
// specify W coordinate iterators (16.16)
void
(*wGrad3xv)(
void
* c,
const
GGLfixed* grad);
// specify fog iterator & color (16.16)
void
(*fogGrad3xv)(
void
* c,
const
GGLfixed* grad);
void
(*fogColor3xv)(
void
* c,
const
GGLclampx* color);
// specify blending parameters
void
(*blendFunc)(
void
* c, GGLenum src, GGLenum dst);
void
(*blendFuncSeparate)(
void
* c, GGLenum src, GGLenum dst,
GGLenum srcAlpha, GGLenum dstAplha);
// texture environnement (REPLACE / MODULATE / DECAL / BLEND)
void
(*texEnvi)(
void
* c, GGLenum target,
GGLenum pname,
GGLint param);
void
(*texEnvxv)(
void
* c, GGLenum target,
GGLenum pname,
const
GGLfixed* params);
// texture parameters (Wrapping, filter)
void
(*texParameteri)(
void
* c, GGLenum target,
GGLenum pname,
GGLint param);
// texture iterators (16.16)
void
(*texCoord2i)(
void
* c, GGLint s, GGLint t);
void
(*texCoord2x)(
void
* c, GGLfixed s, GGLfixed t);
// s, dsdx, dsdy, scale, t, dtdx, dtdy, tscale
// This api uses block floating-point for S and T texture coordinates.
// All values are given in 16.16, scaled by 'scale'. In other words,
// set scale to 0, for 16.16 values.
void
(*texCoordGradScale8xv)(
void
* c, GGLint tmu,
const
int32_t* grad8);
void
(*texGeni)(
void
* c, GGLenum coord, GGLenum pname, GGLint param);
// masking
void
(*colorMask)(
void
* c, GGLboolean red,
GGLboolean green,
GGLboolean blue,
GGLboolean alpha);
void
(*depthMask)(
void
* c, GGLboolean flag);
void
(*stencilMask)(
void
* c, GGLuint mask);
// alpha func
void
(*alphaFuncx)(
void
* c, GGLenum func, GGLclampx ref);
// depth func
void
(*depthFunc)(
void
* c, GGLenum func);
// logic op
void
(*logicOp)(
void
* c, GGLenum opcode);
// clear
void
(*clear)(
void
* c, GGLbitfield mask);
void
(*clearColorx)(
void
* c,
GGLclampx r, GGLclampx g, GGLclampx b, GGLclampx a);
void
(*clearDepthx)(
void
* c, GGLclampx depth);
void
(*clearStencil)(
void
* c, GGLint s);
// framebuffer operations
void
(*copyPixels)(
void
* c, GGLint x, GGLint y,
GGLsizei width, GGLsizei height, GGLenum type);
void
(*rasterPos2x)(
void
* c, GGLfixed x, GGLfixed y);
void
(*rasterPos2i)(
void
* c, GGLint x, GGLint y);
} GGLContext;
|
这些接口的真正实现在/system/core/libpixelflinger/pixelflinger.cpp里面。
在我们下面的程序里面,主要用到一些结构体。
当然在使用pixelflinger前,需要对其进行初始化gglInit(),初始化GGLContext结构体。
01
02
03
04
05
06
07
08
09
10
11
12
13
14
|
ssize_t gglInit(GGLContext** context)
{
void
*
const
base =
malloc
(
sizeof
(context_t) + 32);
if
(base) {
// always align the context on cache lines
context_t *c = (context_t *)((
ptrdiff_t
(base)+31) & ~0x1FL);
ggl_init_context(c);
//初始化context_t结构体
c->base = base;
*context = (GGLContext*)c;
}
else
{
return
-1;
}
return
0;
}
|
其实这个函数主要就是使用
ggl_init_context()
初始化
context_t
结构体,
ggl_init_context()
用于初始化
context_t
结构体中的环境、参数等。然后在
GGLContext
中引用
context_t
以对外提供接口。
GGLContext
中对外接口初始化主要在
ggl_init_context()->ggl_init_procs()
完成。
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
|
void
ggl_init_procs(context_t* c)
{
GGLContext& procs = *(GGLContext*)c;
GGL_INIT_PROC(procs, scissor);
GGL_INIT_PROC(procs, activeTexture);
GGL_INIT_PROC(procs, bindTexture);
GGL_INIT_PROC(procs, bindTextureLod);
GGL_INIT_PROC(procs, colorBuffer);
GGL_INIT_PROC(procs, readBuffer);
GGL_INIT_PROC(procs, depthBuffer);
GGL_INIT_PROC(procs, enable);
GGL_INIT_PROC(procs, disable);
GGL_INIT_PROC(procs, enableDisable);
GGL_INIT_PROC(procs, shadeModel);
GGL_INIT_PROC(procs, color4xv);
GGL_INIT_PROC(procs, colorGrad12xv);
GGL_INIT_PROC(procs, zGrad3xv);
GGL_INIT_PROC(procs, wGrad3xv);
GGL_INIT_PROC(procs, fogGrad3xv);
GGL_INIT_PROC(procs, fogColor3xv);
GGL_INIT_PROC(procs, blendFunc);
GGL_INIT_PROC(procs, blendFuncSeparate);
GGL_INIT_PROC(procs, texEnvi);
GGL_INIT_PROC(procs, texEnvxv);
GGL_INIT_PROC(procs, texParameteri);
GGL_INIT_PROC(procs, texCoord2i);
GGL_INIT_PROC(procs, texCoord2x);
GGL_INIT_PROC(procs, texCoordGradScale8xv);
GGL_INIT_PROC(procs, texGeni);
GGL_INIT_PROC(procs, colorMask);
GGL_INIT_PROC(procs, depthMask);
GGL_INIT_PROC(procs, stencilMask);
GGL_INIT_PROC(procs, alphaFuncx);
GGL_INIT_PROC(procs, depthFunc);
GGL_INIT_PROC(procs, logicOp);
ggl_init_clear(c);
}
|
Pixelflinger
中的屏幕刷新机制,
定义了两个帧缓冲区,
gr_framebuffer[2]
获取缓冲区设备,
get_framebuffer()
3、recovery基本流程
int main(int argc, char **argv)
--->ui_init()
--->ui_set_background(BACKGROUND_ICON_INSTALLING)
--->load_volume_table()
--->get_args(&argc, &argv)
在
/recovery/minui/grapics.c
内进行
字库初始化
字库索引
4、汉化流程
1
)总流程
file:///C:\Users\ADMINI~1\AppData\Local\Temp\ksohtml\wps_clip_image-28211.png
2
)字库制作
通过
GIMP_IMAGE 将字库图片转换生成字库图片源码
C
文件,
/minui/mkfont.c
将源码
C
文件压缩成字库头文件。
注意:生成的头文件,注意修改结构体名以及相应
cwidth
和
cheight
(字符长宽)
字库将在代码内初始化
file:///C:\Users\ADMINI~1\AppData\Local\Temp\ksohtml\wps_clip_image-8312.png
3
)代码修改
字库初始化
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
|
static
void
gr_init_font(
void
)
{
GGLSurface *ftex;
GGLSurface *ftex_cn;
//wkey:chinese
unsigned
char
*bits, *rle, *bits_cn;
//bits_cn
unsigned
char
*in, data;
gr_font =
calloc
(
sizeof
(*gr_font), 1);
ftex = &gr_font->texture;
bits =
malloc
(font.width * font.height);
ftex->version =
sizeof
(*ftex);
ftex->width = font.width;
ftex->height = font.height;
ftex->stride = font.width;
ftex->data = (
void
*) bits;
ftex->format = GGL_PIXEL_FORMAT_A_8;
in = font.rundata;
while
((data = *in++)) {
memset
(bits, (data & 0x80) ? 255 : 0, data & 0x7f);
bits += (data & 0x7f);
}
gr_font->cwidth = font.cwidth;
gr_font->cheight = font.cheight;
gr_font->ascent = font.cheight - 2;
/* wkey:chinese font init */
gr_font_cn =
calloc
(
sizeof
(*gr_font_cn),1);
ftex_cn = &gr_font_cn->texture;
bits_cn =
malloc
(font_cn.width * font_cn.height);
ftex_cn->version =
sizeof
(*ftex_cn);
ftex_cn->width = font_cn.width;
ftex_cn->height = font_cn.height;
ftex_cn->stride = font_cn.width;
ftex_cn->data = (
void
*) bits_cn;
ftex_cn->format = GGL_PIXEL_FORMAT_A_8;
in = font_cn.rundata;
while
((data = *in++)) {
memset
(bits_cn, (data & 0x80) ? 255 : 0, data & 0x7f);
bits_cn += (data & 0x7f);
}
gr_font_cn->cwidth = font_cn.cwidth;
gr_font_cn->cheight = font_cn.cheight;
gr_font_cn->ascent = font_cn.cheight - 2;
/* wkey: chinese font init */
}
|
字库索引
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
|
int
gr_text(
int
x,
int
y,
const
char
*s)
{
GGLContext *gl = gr_context;
GRFont *font = gr_font;
/* wkey:chinese */
GRFont *font_cn =gr_font_cn;
/* wkey:chinese */
unsigned off;
unsigned zonecode,bitcode;
//wkey:zone bit code
y -= font->ascent;
//gl->bindTexture(gl, &font->texture);
gl->texEnvi(gl, GGL_TEXTURE_ENV, GGL_TEXTURE_ENV_MODE, GGL_REPLACE);
gl->texGeni(gl, GGL_S, GGL_TEXTURE_GEN_MODE, GGL_ONE_TO_ONE);
gl->texGeni(gl, GGL_T, GGL_TEXTURE_GEN_MODE, GGL_ONE_TO_ONE);
gl->enable(gl, GGL_TEXTURE_2D);
while
((off = *s++)) {
// off -= 32;
if
(off < 128) {
off -=32;
gl->bindTexture(gl, &font->texture);
gl->texCoord2i(gl, (off * font->cwidth) - x, 0 - y);
gl->recti(gl, x, y, x + font->cwidth, y + font->cheight);
x += font->cwidth;
}
else
if
(off <= 0xf7 && off >= 0xb0)
{
/* wkey:chinese */
if
(off <= 0xf7 && off >= 0xb0)
;
else
off = 0xb1;
gl->bindTexture(gl, &font_cn->texture);
zonecode = off - 0xb0;
off = *s++;
if
(off>=0xa1)
bitcode = off - 0xa1;
else
bitcode = off < 94 ? off : 0x5d;
gl->texCoord2i(gl, (bitcode * font_cn->cwidth) - x, (zonecode * font_cn->cheight)- y);
gl->recti(gl, x, y, x + font_cn->cwidth, y + font_cn->cheight);
x += font_cn->cwidth;
/* wkey:chinese */
}
// x += font->cwidth;
}
return
x;
}
|
5、其他问题与移植性
/**
注:
1、以上是基于GB的汉化标准,所以保存文件时要注意保存为GB编码类型,保存为UTF8编码可能导致显示乱码问题
2、汉化后的recovery 只支持中文,无法进行中英文或其他语言切换。
1、以上是基于GB的汉化标准,所以保存文件时要注意保存为GB编码类型,保存为UTF8编码可能导致显示乱码问题
2、汉化后的recovery 只支持中文,无法进行中英文或其他语言切换。