本帖最后由 shane007 于 2023-9-4 18:28 编辑
3 C. x6 k# H) T7 Y0 |$ Q' x8 y* U, C: @
这是一个opengl的游戏,当初发售的时候只有德文版,因为被人遗忘了,
8 P% J. p: ? F d& @9 I8 Z但目前已经有了英文补丁,因此汉化又被提上日程。
& t* e( ~1 q2 f4 i# ]
5 p0 ^' ^5 ^, |8 L对opengl的调用主要是在toh.exe完成的,
$ K) Z# C8 U3 u. j对于opengl的游戏我们主要关注glGenLists和glCallList这2个函数
0 ]6 Y7 d% E' z6 s/ Q( l
3 p- Q4 \4 R% @9 ~glGenLists的调用处共有6处,每处都类似,
/ R4 s* X$ Y' c1 \可见游戏初始化了6种字体,每种有256个字符。# i8 h% P8 c5 V- L0 t) s- w5 w) m
其中一处代码如下。可以看见游戏创建了256个显示列表,并调用CreateFontA生成字符的材质。
! `& _ ?* M; {修改的时候,应该还要修改到上层调用的其他函数。
6 y% R% \+ O1 G# B1 c! h) F( d9 x- BOOL __cdecl sub_4518C0(HDC hdc)! e+ e1 n+ _0 V; |3 \2 J0 X
- {
7 ]: |7 T; R" P; m+ W7 p9 [4 s - HFONT h; // [esp+4h] [ebp-8h]
% V5 j: m" F3 I5 n6 M$ u4 k. v - DWORD iCharSet; // [esp+8h] [ebp-4h]0 C2 K( F, J6 |
- % w0 y( R8 W, h6 m/ P
- if ( dword_4A4490 <= 1252 ), }- m& D' b7 }" G2 v$ B
- {
- m* v& k: k- v! y" b - if ( dword_4A4490 == 1252 )4 L, U) `, e8 n& I
- {8 f I0 g3 ]0 ]& y/ p3 N1 I3 Y# U
- iCharSet = 1;
6 F" g! M b0 i$ G4 I( R: I - goto LABEL_11;" Z" K2 w7 i, @" R6 n' X
- }3 {+ x7 r; A; X4 i# i
- if ( dword_4A4490 != 1250 ); n* G! X3 \& s- J+ [2 a9 Z
- {
5 i; }4 Z' ~7 | S+ w0 A/ W - if ( dword_4A4490 == 1251 )" b$ K8 j, {% G+ V
- {
8 g, R0 ]/ C- W7 R - iCharSet = 204;4 X: H6 s i% e2 o
- goto LABEL_11;
+ V: u9 a( q$ ?' ^: [+ @ - }; v: q, j3 C# i/ Z- p
- goto LABEL_10;
9 N6 m( B9 g1 G, w" {% X1 A - }
- P; m3 k4 x& k! K/ e9 I. T - LABEL_7:4 E r+ R" A, _+ y3 A0 ]
- iCharSet = 238;
# L g4 w1 @, L0 Y, G1 S, r - goto LABEL_11;8 \# h7 R" \, M5 N2 I1 _5 \
- }4 }9 N& o( h% g# }2 I
- if ( dword_4A4490 == 11250 )
+ [! `; `2 \- B3 f+ M - goto LABEL_7;
( i3 S* D u; o/ h ?% m - LABEL_10:/ [5 x# T' F; h: N) {6 ^- f
- iCharSet = 1;
1 \- \/ I7 @7 Y# X: \/ ~ - LABEL_11:2 z) x5 c! C; n: y2 m6 L' I
- base = glGenLists(256);4 u: p- ]; N" k0 u) ~* i# a* i
- h = CreateFontA(-14, 8, 0, 0, 700, 0, 0, 0, iCharSet, 4u, 0, 4u, 0, pszFaceName);0 O1 E6 ]# J0 k" Y9 Y% [; E3 G+ ^, w
- if ( !h )# }- D! z+ e8 D0 P3 y s4 V: ]
- MessageBoxA(0, aCannotCreateFo, aBuildfont, 0);
8 q% S( q/ N) x \5 s2 ~7 z0 ~0 o - SelectObject(hdc, h);
z* a% d7 s# W# N. W7 @ - return wglUseFontBitmapsA(hdc, 0, 0x100u, base);
% G4 K- T1 @% G/ U8 Z" X6 ~% Y0 n - }
复制代码 ! z( ~- x7 `% d6 | m. a
9 O4 j* v: U* u
glCallLists调用的地方共有3处,- K( T: l4 q' I
这个函数就是游戏的显示函数,共有3个参数,$ K# ?9 s. w- R8 p( l
- void WINAPI glCallLists(: S# C0 s0 L& e0 y- H* E+ l
- GLsizei n,* h9 l( ^, R5 G% b( T
- GLenum type,
" F' Y0 D6 Y/ ]8 t$ ?' R: M - const GLvoid *lists
8 }1 j8 @) U7 j - );
复制代码 ! k% u7 @0 h: f4 b' V: M. \
/ [+ I" C0 M& a
其中n为字符串长度,type为字符串类型,*lists为字符串指针,
: H& R; g4 c/ c4 x& h8 q! {) a' @ 如果游戏在调用glCallLists时第二个参数使用了0x1400,即GL_BYTE,则表示单字节:
0 f$ `1 j! y2 E' {* \) ` 需要修改为GL_UNSIGNED_SHORT,即0x1403。
' Q m. D( J& {* {- \+ R9 V
9 Y. K3 k2 M: t* o/ h2 g定义
+ R3 N3 A. t* W* Y- |; X- #define GL_BYTE 0x1400
, `6 s0 {8 s5 C# d' `3 ^- D# `+ B - #define GL_UNSIGNED_BYTE 0x1401 k3 F4 x5 k: x) n, k" M1 k8 y* d1 f
- #define GL_SHORT 0x1402 i6 ]3 C. [" l2 M8 b
- #define GL_UNSIGNED_SHORT 0x1403
; \$ E R5 c6 E; E9 h" } - #define GL_INT 0x14049 S# c0 G/ ]) A
- #define GL_UNSIGNED_INT 0x1405
; _% `& P7 D. k+ P) h - #define GL_FLOAT 0x1406
5 X1 C& } N5 x4 N5 R2 r" a5 x - #define GL_2_BYTES 0x1407
: L! ?) b7 x) `' V9 S - #define GL_3_BYTES 0x1408
$ P. C/ d; C, d, ], ?* o/ o3 u - #define GL_4_BYTES 0x1409, L T% f5 C7 j, e p. l& V) J7 ] Q3 }
- #define GL_DOUBLE 0x140A
复制代码
# e: h" S" E# t" B% h
; H5 B: |4 W5 R+ h' e! Z |