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

其他 【Scummvm汉化 #3】The 7th Guest 第七访客 #1 字幕篇

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

[其他] 【Scummvm汉化 #3】The 7th Guest 第七访客 #1 字幕篇

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

【Scummvm汉化 #3】The 7th Guest 第七访客 #1 字幕篇

本帖最后由 shane007 于 2023-8-12 13:57 编辑
- q7 T2 z. y# z
: j( F3 \" y) ]" m这个游戏原本是没有字幕的,但是在Scummvm论坛上发现了一个帖子,
5 A' {# A1 w' z% Z讨论的内容是关于在原本没有字幕的游戏上加上字幕。(最初的缘由,是为了帮助一位失聪的朋友)/ t" b/ S4 M  m+ W( Y- O' ^
https://forums.scummvm.org/viewtopic.php?t=7168
7 q/ j1 G) z9 \$ T[Scummvm-devel] Displaying subtitles in voice-only games (narkive.com)
4 j+ l" \5 l2 _6 R/ I. H! I- e( t% C! q9 v5 z( r8 ~9 F7 |
前段时间第七访客出了25周年纪念版(The 7th Guest 25th Anniversary Edition。
2 l# U9 Y" s1 O3 @2 c* q' E在这个版本中,游戏的视频是有字幕的,因此把这个视频的字幕用到Scummvm中就成为了可能。
3 w. l+ F. r: @2 A4 B5 O" A9 ^( z# n
8 e* m, O5 K7 Q+ o. z5 q/ v7 d我查看了一下最新版本的Scummvm的代码,发现老外已经加入了一部分代码。' @0 v' S! [: P3 b" V8 A1 o# H$ \
在此基础上,汉化是大有希望的。此种汉化方法,也是前所未有的,如果真的实现了将会有重要意义。4 d) m9 A  T: ]( j3 U  K
8 ^0 y$ F" q0 @& y3 `# F* D
类似游戏还有
  1. · Groovie  b8 X- h2 |  g- J
  2. - The 7th Guest, ]: i+ f  }) e
  3. - The 11th Hour* W, ^3 }8 u( P) M2 o0 B: _8 O

  4. - f1 f/ e( c0 A6 n) w/ p
  5. · MADE: C& y4 f7 I. P$ @
  6. - Return to Zork (descriptions are text only, while spoken dialogs lack
    ' o+ U, {/ X) }: h
  7. any text)
      P2 U! N% d! l

  8. ' _3 b) N5 A- w/ F  K6 ^
  9. · SCI 1
    5 _* O4 f( D. o. C0 c
  10. - King's Quest V (CD Version). In this case, just enabling voice and text
    ( Q! {) t( V1 o/ _
  11. simultanously would allow a 3rd party to create a set of MSG files: O! Q9 d" a  z) _) R( j5 K
  12. containing the voice transcription/translation, as it happened with Gabriel
    % B' h3 G# v) C! Z5 {4 b; u
  13. Knight II.
    0 R% ?. \2 K) U! p% R3 y# ]* s

  14. ; c* r3 }* j5 b9 J! P

  15. & t6 Z9 R/ A- c+ ]
  16. Future engines:
    5 a6 g# Q2 u  [+ _

  17. 9 K% q& }' o4 x3 c
  18. · SCI 21" _! z% o2 W' s( n& @: ~0 y
  19. - Gabriel Knight II: The Beast Within (Already a fan patch available in* N  K5 \2 `, z. I0 Z/ D
  20. order to enable the text display feature)" [9 d% [+ w/ L: t! t
  21. - Phantasmagoria
    : s: N- n7 s+ G# _9 R& c9 R
  22. - Rama# G" ^3 l: q/ @  L& k' }+ v
  23. - Shivers* m+ I' E5 A' f  \
  24. - Phantasmagoria II: A Puzzle Of Flesh% r  |; Z2 i5 o+ G0 q0 s
  25. 3 E5 M) `0 s9 n
  26. · SCI 3
    . T6 O4 ^- b  ~0 J  U; u1 K
  27. - Lighthouse: The Dark Being
    ' ~4 x+ Q6 q* o1 N
  28. - [5 M* K( _9 w# w: Y& \0 d
  29. · M4/MADS
    5 H) ?% X! v# c
  30. - Orion Burger( Q) c) d" r0 [
  31. ; [" j( n# f8 a9 g& ~0 K
  32. · Mohawk& }) s6 C0 P3 s  }
  33. - Myst: j, Y. w* m, u
  34. - Riven: The Sequel to Myst
复制代码
1 `8 _$ P, ?! H1 {" C, w8 `- N( ~

! W% [6 a0 {* o9 F& {( Y* C7 s$ n% ?" v' A5 C9 w
, H0 e6 z) {4 D0 @) o+ ]
相关代码如下9 i# m/ }2 O% t0 H7 r
  1. bool VideoPlayer::playFrame() {
    / K  y6 a+ v# ~& k/ f
  2.         bool end = true;' v2 O0 t7 F6 ]+ ?, z

  3. ( F% _. t$ s  n0 V8 I. t
  4.         // Process the next frame while the file is open
    2 K# H* M6 l( W. ?- K/ Q  V6 c& V
  5.         if (_file) {+ c7 X; @( M$ g: ?& E
  6.                 end = playFrameInternal();
    " }" ?0 T3 A2 D: f: W/ A( T

  7. 2 S) P/ G5 Z+ |; r, {
  8.                 _subtitles.drawSubtitle(_lastFrameTime - _startTime);: M, G% Q4 B! k/ q: v. J' x' q
  9.         }
复制代码
  1. bool Subtitles::drawSubtitle(uint32 timestamp, bool force) {
    % f& Y" y9 A  y  [) M
  2.         Common::String subtitle;; M8 }) X, P$ S
  3.         if (_loaded) {
    * m: G! H9 ?. A/ h: X# ]
  4.                 subtitle = _srtParser.getSubtitle(timestamp);2 b$ C. P+ C% O
  5.         } else if (_subtitleDev) {
    4 B3 F8 O: o8 T" s6 o0 ?
  6.                 subtitle = _fname;4 g5 E: W" Q3 h1 C! f( y$ ?! L+ M
  7.                 uint32 hours, mins, secs, msecs;
    7 i3 N& b1 M) s: z+ I
  8.                 secs = timestamp / 1000;
    3 O8 C5 n) Y& l
  9.                 hours = secs / 3600;
    " c( y; x, S5 [1 T( k2 e
  10.                 mins = (secs / 60) % 60;) S" r5 {8 ?7 |5 K
  11.                 secs %= 60;9 e: y2 [2 W$ q! a, c) M4 t& m
  12.                 msecs = timestamp % 1000;
    + `' z+ e0 A# v
  13.                 subtitle += " " + Common::String::format("%02u:%02u:%02u,%03u", hours, mins, secs, msecs);8 {$ y2 f4 F3 A
  14.         } else {
    & f/ _' t8 p% l4 Y% Q4 `: l1 [
  15.                 return false;
    ! u9 J* y# \8 F6 ?1 ]6 W; A
  16.         }
    ) Q: o$ J! @. H; y% U, S& W

  17. . t1 e/ Z% b4 p0 M- Z7 ^
  18.         int16 width = g_system->getOverlayWidth(),
    2 F! A9 v( `# s" {, J% V
  19.                   height = g_system->getOverlayHeight();( b& D* c! I* Q4 N3 f

  20. 2 X7 d* c; |/ v, _* G, Z: p
  21.         if (width != _lastOverlayWidth ||: P2 l' B2 {% b- ~8 E
  22.                 height != _lastOverlayHeight) {' i% B0 o# I7 Z
  23.                 _lastOverlayWidth = width;
    - ^9 n" b/ D  h/ S) x8 d
  24.                 _lastOverlayHeight = height;2 J5 X% R2 ~2 K, ^/ M

  25. ' c$ _: B2 U( o3 u0 [
  26.                 // Recalculate the real bounding box to use
    : y2 T$ T9 T5 Z5 b" }
  27.                 _realBBox = _requestedBBox;* f& U9 j# G3 j; [5 j0 A1 A  {
  28. # T  y8 A8 v. i3 n
  29.                 if (_realBBox.bottom > height) {1 o: z% }. v3 X; w
  30.                         // First try to move the bounding box: f( o7 j  z% }2 F' S( u
  31.                         _realBBox.top -= _realBBox.bottom - height;
    $ f! T8 Z. f) X7 D3 l) B6 c) [. r
  32.                         _realBBox.bottom = height;
    6 ^- L5 C( ]- \. [' y: n
  33.                 }
    . w" l& U! W, W9 n0 k; Q! i
  34.                 if (_realBBox.top < 0) {
    ! ]0 a1 h3 @* X: q2 j' h
  35.                         // Not enough space
    & r" x" B2 Q  Z4 B; N$ C
  36.                         _realBBox.top = 0;9 H6 u7 g0 \& C. ]! o8 d& |
  37.                 }
      K% Q6 M( Q! T- Y* P
  38. ) `1 e: F- b+ W% N! I
  39.                 if (_realBBox.right > width) {
    # X2 P, x# J- H: i! }( }
  40.                         // First try to move the bounding box$ T& i" ^+ T0 N" \
  41.                         _realBBox.left -= _realBBox.right - width;
    ! c3 i9 h5 Z+ t; B* N& p
  42.                         _realBBox.right = width;, K3 H5 f* V+ s  M! R
  43.                 }
    / g) y, }1 ^3 ~$ e
  44.                 if (_realBBox.left < 0) {
    2 C# ~& z4 L: h7 m3 J5 K/ l
  45.                         // Not enough space
    3 m; D. _* G( [% l: ~3 z
  46.                         _realBBox.left = 0;
    1 |) _% a/ y% q
  47.                 }3 ^7 _# |9 N% _- K  c& b
  48. % I* O' Z9 W0 M8 C$ U
  49.                 force = true;! }; Q, ^5 I0 d) }1 r0 f4 a' O
  50.         }/ c4 M' i7 ^" z! a! L4 w2 t
  51. : f( Z; H( d! r$ F+ W
  52.         if (!force && _overlayHasAlpha && subtitle == _subtitle)! x, o2 U. d# ], d8 P. D0 N
  53.                 return false;
    + F% Z! C5 J7 }. C/ k/ f
  54. 4 o7 A( z' b9 j$ b
  55.         if (force || subtitle != _subtitle) {; W, @' _8 D/ P% v5 y
  56.                 debug(1, "%d: %s", timestamp, subtitle.c_str());
    ( t3 g8 K+ x' L1 d& f" @* n
  57. , P, w0 }' D4 p* t7 U  i& `
  58.                 _subtitle = subtitle;
    # ~$ F; Z1 K$ v: S5 t
  59.                 renderSubtitle();9 \; m- O. X  z. t9 t2 t
  60.         }
    , ?- B1 L1 x! o7 G' [' K) y
  61. ' [3 B2 W- }2 u! h: ?, \  w5 Q, {; x
  62.         if (_overlayHasAlpha) {) u7 `8 Z$ ]$ E+ k, C
  63.                 // When we have alpha, draw the whole surface without thinking it more* b: E2 M$ X+ c% P% Y, j, ?+ _- u
  64.                 g_system->copyRectToOverlay(_surface->getPixels(), _surface->pitch, _realBBox.left, _realBBox.top, _realBBox.width(), _realBBox.height());( D, h$ ]& G) n
  65.         } else {9 S9 H# A; L7 I2 ?
  66.                 // When overlay doesn't have alpha, showing it hides the underlying game screen
    ! V# A: e! c; \/ H
  67.                 // We force a copy of the game screen to the overlay by clearing it
    . s, a  u% W5 a) y! Y
  68.                 // We then draw the smallest possible surface to minimize black rectangle behind text
    ! ]! g% r; H) C- ^
  69.                 g_system->clearOverlay();: l0 X; c: G) T; S2 t% w
  70.                 g_system->copyRectToOverlay((byte *)_surface->getPixels() + _drawRect.top * _surface->pitch + _drawRect.left * _surface->format.bytesPerPixel, _surface->pitch,
    + o; {4 V0 I/ j+ ~9 c
  71.                                 _realBBox.left + _drawRect.left, _realBBox.top + _drawRect.top, _drawRect.width(), _drawRect.height());
    ( Z0 c6 d7 [, j% n+ c9 i$ ~
  72.         }, Q, P" v. L. `4 g0 H
  73. 9 ?$ F' G( m! f9 i( p, D
  74.         return true;
    0 G* Y6 K0 W  G
  75. }
    ; E& U/ W& @1 s0 H
复制代码
7 x. g: s" Y. S! T

; Y* p- _) t. W" |: I9 U! _  w) k" p# j' K

" D# @% S- [. t' r0 a1 n& m: v5 D7 O) Y0 O% {4 o4 e% @5 o' ]
( a4 P5 b5 j  K1 d1 z, z" Y
9 B! r' R6 A$ n& h9 q
分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏 分享分享 很美好很美好 很差劲很差劲
回复

使用道具 举报

高级模式
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日,是全球华人共同的冒险解谜类游戏家园。我们致力于提供各类冒险游戏资讯供大家学习交流。本站所有资源均不用于商业用途。

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