设为首页收藏本站官方微博

建议 【Directx9游戏汉化 #6】 静物2 (Still Life 2) 字幕显示函数

[复制链接]
查看: 368|回复: 1
打印 上一主题 下一主题

[建议] 【Directx9游戏汉化 #6】 静物2 (Still Life 2) 字幕显示函数

跳转到指定楼层
楼主
发表于 2023-8-26 12:30 | 只看该作者 回帖奖励 |正序浏览 |阅读模式

【Directx9游戏汉化 #6】 静物2 (Still Life 2) 字幕显示函数

本帖最后由 shane007 于 2023-8-26 14:47 编辑 2 W% ?* ?. X* {+ k. _1 ]

5 G3 g! R8 W6 z. d. T# _这个有的在上一波(第4波)中进行了比较深入的分析。* S! `. e# C1 U+ m0 U  O  T* F
本次在以前分析的基础上,排除无关内容,只抓和汉化有关的要点。
1 W  B+ p6 B+ A. ~' _( }" H; s+ @+ G
$ c0 q: M$ |" g, H《1》这个游戏的初始化Directx9共有2处,一处是xcDxShader.dll,还有一处是xcDxOldschool.dll0 F7 j! X  I, A0 `1 E" g
     具体要抓取哪个CreateDevice用于往屏幕上写字,需要写代码测试一下。
) y4 |/ W7 \; l, b& p6 u2 V+ X2 v4 O& i' K( v! s
《2》这个函数,以ida pro的静态分析为主,暂时认为字幕显示函数是xcEngine.dll中的SetTextString方法。
& Z* b' A1 h  e  c# f/ T, _- C) i5 c- [/ X
关键是这2句,Str是完整的字幕,char_unicode是其中一个字符。
7 z6 u5 k/ e2 |0 X2 _* g从代码上看,这个游戏是支持双字节的。但是由于采用的是图片字库,搞清楚结构不容易,因此暂定用hook方法自己写一个显示函数。
. G7 {+ R# P( U, T3 r* e$ J8 H; p6 ]这函数传入一个text_object,里边也许会有颜色和坐标。
, @: ~3 W1 d0 R5 c6 j" v+ Q3 C
  1. char_unicode = (unsigned __int16 *)(*str + 2 * counter);
    % L  ^8 k/ G7 I% g
  2. *char_unicode = xccTextureFont::GetCharacterIndex((xccTextureFont *)text_object[20], *char_unicode);
复制代码

% U1 G% i6 H/ h$ W此外,该游戏在字体文件Sl2fnt.dat不存在的时候调用系统字库,
5 e/ R/ ?) M1 w0 X* m7 `) l1 l因此,也许在调用createfont的时候,能用修改参数的方法让该游戏支持中文。0 ]0 I1 @) Q( z2 K9 z
7 k! E( i! w- B: h% ]
# B" s7 v7 U2 }4 @4 u" U
以下是修改过变量名的代码。& \: l/ S) G" ?) W) b& A
  1. int __thiscall xccFrameText::SetTextString(_DWORD *this, int length, _DWORD *a3, int show_subtitle_flag)# ?9 A5 k+ Z9 y$ l, \/ [2 H4 y, w; N
  2. {" U' X, \& o+ b3 C# g) ^, W: o
  3.   _DWORD *text_object; // esi
    0 R0 |3 T8 P, [, T  L
  4.   int offset; // ebx
      p' C( X. t! }" z
  5.   int counter; // edi9 F: V" B4 W# L$ D& w1 o
  6.   _DWORD *str; // eax
    7 n6 H. G& W: m5 N; v
  7.   unsigned __int16 *char_unicode; // ebp# S' z9 T& l4 h" p  X2 x' N
  8.   int v9; // edx
    5 x) `" A  {( T  I+ _/ i' t

  9. ) m" P5 F4 _2 E
  10.   text_object = this;/ z! c/ F0 {# A- G9 X
  11.   offset = 32 * length;% o: R& T3 a0 p+ m
  12.   counter = 0;8 A9 [( n4 X/ i7 t/ o7 [
  13.   *(_DWORD *)(32 * length + this[21] + 8) = 0;
    : S. G  C9 v1 z3 Q# x) z( |( y+ Q
  14.   xctArray<unsigned short>::add(*a3, a3[2]);
    1 G( b+ l# e5 i' L+ h
  15.   if ( !show_subtitle_flag ); V5 _$ c4 M0 s  y- _3 N
  16.   {0 p& n9 S8 }2 p+ R; A! Y& o
  17.     str = (_DWORD *)(offset + text_object[21]);+ P# e+ T4 U3 N5 A. ~+ T* F  A
  18.     if ( str[2] > 0 )& w$ _+ `9 d4 U
  19.     {. w/ p6 ~" t: L
  20.       do& n* o3 ^  W/ q8 ~/ e: A$ J' Z
  21.       {. f# P3 K8 V; {" F4 [% }& f
  22.         char_unicode = (unsigned __int16 *)(*str + 2 * counter);
    ) ~' x6 y5 p: w* z
  23.         *char_unicode = xccTextureFont::GetCharacterIndex((xccTextureFont *)text_object[20], *char_unicode);
    1 W4 X' u! u8 j7 \; N& u: M5 h
  24.         ++counter;
    * Y7 W/ I7 c- t# B
  25.         str = (_DWORD *)(offset + text_object[21]);
    % d5 M3 s5 ^& [3 W6 C5 d7 T0 o
  26.       }
    4 ]# m: [- J8 y0 J5 j$ q
  27.       while ( counter < str[2] );# `) l, v, M0 i* }' o+ c0 i. m* c
  28.     }
    / W! @6 |* H+ D  A/ }0 N+ [' W
  29.   }
    . ^3 b1 b; T1 V% w; S2 `
  30.   v9 = text_object[21];/ F4 F7 L- V2 w/ h/ h
  31.   *(_DWORD *)(offset + v9 + 28) |= 4u;. q- ~( Y7 Y8 i. n# w# C  @  q1 c
  32.   return offset + v9 + 28;+ e/ z3 \: \6 [. i
  33. }
复制代码
1 s" }& J4 U+ F* i
xcEngine.dll 中的CreateFontA代码,可以尝试修改字符集和字符名称,看看是否能显示出中文。
, ?% w+ b; ^/ |' M0 l
  1. h = CreateFontA(9 p5 f% R% s* y3 K9 H& o
  2.         -*((_DWORD *)a1 + 1),      // 字体高度(负值用于可变尺寸字体)* y: K0 ^& N# s
  3.         0,                         // 字体宽度(0 表示由系统选择合适的宽度)3 ?* P7 E$ B/ i) i! m; }; a
  4.         0,                         // 文本输出方向角度
    1 a- b* L' Q' Q9 A  B: v0 u- c
  5.         0,                         // 字体基线方向角度
    % _/ H7 ]9 y8 S8 z
  6.         *((_DWORD *)a1 + 3),       // 字体重量(例如:FW_NORMAL、FW_BOLD)
    8 T. }( {% S1 @6 x0 X& K& D, w1 n3 b
  7.         *((_DWORD *)a1 + 4),       // 是否斜体3 t" y( Q5 F' i
  8.         *((_DWORD *)a1 + 5),       // 是否下划线3 i7 D. y* `) L) T8 G6 a8 ]6 u
  9.         *((_DWORD *)a1 + 6),       // 是否删除线6 @# F+ [* ]7 G
  10.         *((_DWORD *)a1 + 7),       // 字符集(例如:ANSI_CHARSET、DEFAULT_CHARSET)7 K/ }* q4 |  L
  11.         6u,                        // 输出精度(OUT_DEFAULT_PRECIS)
    / h! [3 l7 [* Z7 N) e
  12.         0,                         // 剪裁精度(默认剪裁精度:CLIP_DEFAULT_PRECIS)' e* t# d5 R" |+ o, w2 D
  13.         4u,                        // 字体质量(DEFAULT_QUALITY)
    6 \$ @2 m/ L7 k
  14.         2u,                        // 字体族和固定/可变宽标志(字符剪裁精度:CLIP_CHARACTER_PRECIS)$ }9 E6 F6 s/ q
  15.         *(LPCSTR *)a1);            // 字体名称
复制代码
$ d# M. P6 g! i6 ?! H9 r0 K1 x
用API monitor 跟踪了一下GetDrawnCharCount ,发现和画面都能对应上,比如一下2行的24和8,就是对应画面上2行字幕的字符数。
& \; @) q  R( s# G! P
* W+ K0 u) {. Q3 X6 [9 w
  1. #        Time of Day        Thread        Module        API        Return Value        Error        Duration9 E* L  }9 K" r# S. q) w
  2. 6353        2:44:57.277 PM        1        SL2.exe        xccFrameText::GetDrawnCharCount ( ... )        24                0.0000002" n6 X! L2 u4 e1 T2 B
  3. 6354        2:44:57.277 PM        1        SL2.exe        xccFrameText::GetDrawnCharCount ( ... )        8                0.0000001* O& k1 a. H1 V" v9 C
复制代码
' a0 U! d% t' u/ o
$ T* s, [! D- X. D9 L

( C; s. x4 y4 T* i: V9 q
0 |% h  z" S( j$ o6 @- P3 @7 |/ Z$ d3 Y3 J6 q  j: p

! @1 e' w, N+ k& C' A. l. c8 v
3 G, a. ~* E" w" B' k0 T; U4 H
分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏 分享分享 很美好很美好 很差劲很差劲
回复

使用道具 举报

沙发
未注册网友  发表于 2023-10-22 04:09
等了十年了这游戏的汉化,还有望吗?
回复 支持 反对

使用道具

高级模式
B Color Image Link Quote Code Smilies

本版积分规则

冒险解谜游戏中文网 ChinaAVG

官方微博官方微信号小黑屋 微信玩家群  

(C) ChinaAVG 2004 - 2019 All Right Reserved. Powered by Discuz! X3.2
辽ICP备11008827号 | 桂公网安备 45010702000051号

冒险,与你同在。 冒险解谜游戏中文网ChinaAVG诞生于2004年9月9日,是全球华人共同的冒险解谜类游戏家园。我们致力于提供各类冒险游戏资讯供大家学习交流。本站所有资源均不用于商业用途。

快速回复 返回顶部 返回列表