github akirahayabusa/ngb-pc-native-port-release v2.2.27
Ninja Gaiden Black Hurricane PC 2.2.27

latest releases: v2.2.29, v2.2.28
one day ago

《忍者龙剑传 黑之章》(含飓风版中文汉化 vb-zh-x2.1)与《忍者龙剑传》(2004)的非官方 Windows 原生移植。2.2.27。

2.2.27:21:9 / 16:10 的 HUD 改由游戏自己判断;商店两侧不再露出游戏画面

1. HUD 两侧还是居中,改为直接问游戏

2.2.26 把“是否在游戏中”的门槛从 30 次 3D 绘制降到 1 次,解决了第一人称转视角时 HUD 来回跳的问题。但那仍然是从“这一帧画了多少 3D”去推断,不是游戏自己的判断。这一版改成直接用游戏自己的判断。

  • 为什么不按“谁画的”来区分 HUD 和菜单:先试过记录每一块 2D 是游戏里哪个函数画的。结果 HUD 和菜单的每一块 2D 都经过同一条路径:游戏先把所有 2D 放进一个统一的列表,再由同一个函数(FUN_00222730)一次画完。所以在“画”的那一刻分不出谁是 HUD。
  • 游戏自己的 HUD 函数:参考 ngbrecomp(src/hud.c),游戏画 HUD 的函数是 FUN_001FA210。我对照我们自己的反汇编确认过,地址和逻辑完全一致。它只在游戏自己的三个条件同时满足时才画 HUD:[0xD6AF00] == 1、[0xDB5A63] >= 0x28、HUD 没有被游戏隐藏([0xDB9C6E] == 0xFFFF)。而且只有“画了 HUD”这条分支,会在最后执行 mov eax, 1。
  • 做法:把这条 mov eax, 1 换成调用一个三条指令的小程序:先计数,再执行 mov eax, 1,然后返回。游戏的行为完全不变。这一帧计数变了,就说明游戏画了 HUD,算作游戏中;不管这一帧画了多少 3D。
  • 适用范围:启动时在游戏代码里按字节特征查找(数据地址部分不比对),只找到一处才打补丁。黑之章各版本(飓风版中英 / 日英、基本版、美版原版)的游戏文件里都在同一位置(0x1FA2AD);2004 光盘版(0x1DA31F)和更新版(0x1EB722)也找到了同样结构的函数。找不到时自动沿用 2.2.26 的规则。
  • 顺序验证:在黑之章和 2004 光盘版中各记录 3600 帧,每一帧都是游戏的 HUD 函数先运行、2D 后画。所以画 2D 时,这一帧算不算游戏中已经确定。
  • 实测:黑之章 21:9 下读档、第一人称左右转,HUD 始终在两侧;暂停、道具、武器、忍法菜单仍然居中。2004 光盘版读档游玩,HUD 在两侧(连续 3150 帧未跳动),开菜单居中、关掉回到两侧。

2. 商店两侧露出游戏画面和血条

  • 玩家现象:21:9 下进入村正的商店,商店界面以外的两侧露出游戏画面,连左上角的血条也看得到。
  • 对比证据(逐帧记录每一次绘制):
    • 武器菜单(2004,第 13458 帧):完全没有画 3D,先用一个全屏的纯色矩形盖住屏幕,再画菜单。屏幕上从来没有游戏画面,所以两侧是黑的。
    • 商店(黑之章,第 3137 帧):游戏在进商店时把最后一帧游戏画面存成一张图(512×512),之后每帧先把这张图铺满整个屏幕当背景,再叠一层它的模糊光晕,最后在上面画商店的美术。
  • 原因:这张存下来的图,存的是我们 21:9 的画面,两侧本来就有场景和移到两侧的 HUD。原版 16:9 下,商店的美术几乎把它整个盖住;21:9 时美术只有中间 16:9,两侧盖不住就露出来了。2.2.12 把 HUD 移到两侧后,血条也跟着露了出来。所以这不是游戏的缺陷,是游戏的画法遇上我们 21:9 扩展造成的。
  • 为什么第一次修改没有生效:第一次的修改是“不在游戏中时,全屏的拷贝画面只画中间 16:9”,但实际没有起作用。原因是这类“把画面原样贴回屏幕原位置”的绘制(贴图坐标正好对应屏幕位置),会先走水下波纹那条专门的处理分支,按原样全宽画完就直接返回了,根本没走到后面加的裁切代码。
  • 为什么第二次生效:把判断移到那条分支里面,在它返回之前裁切:不在游戏中、并且这张画面铺满全屏时,只画中间 16:9,两侧留黑,和武器菜单一样(16:10 屏幕则上下留黑)。
  • 是不是给商店做了特殊处理:不是。代码里没有任何商店专用的判断,规则是通用的:不在游戏中的帧里,凡是铺满全屏、贴回原位置的画面,都只画中间 16:9。目前确认用到这种画法的是商店;其他界面如果也用同样的画法,会得到同样的处理。游戏中的水下波纹属于游戏中的帧,不受影响。
  • 实测:21:9 下进商店,两侧变黑,不再露出血条;武器菜单、暂停菜单正常。

测试

  • 黑之章第一章基准 185 秒(集显 Iris Xe):16:9 帧时间中位数 5.38 ms(2.2.26 为 5.38 ms),2694 帧中 1 帧超时;21:9 中位数 6.02 ms(2.2.26 为 5.86 ms,几次 21:9 测量在 5.86–6.02 ms 之间波动),99% 帧 10.20 ms(2.2.26 为 10.35 ms)。新增的两处判断在游戏中每帧只多一次比较。
  • Windows Defender 扫描三个程序:无威胁。

发布包

  • ngb-hurricane-pc-2.2.27-win32.zip
  • 大小:3,058,254 字节
  • SHA-256:f7f62ab5e825edb45a4a373809119e7b064bcab8c5b2976d8bb9d1f8e42cbe85
  • 符号包 ngb-hurricane-pc-2.2.27-win32-symbols.zip:23,786,617 字节
  • SHA-256:64674776ff2d9903f4f18059beeeb30c8479bc9063bcbd259961a6d4a08fa45d

作者:b站 哈雅布撒(QQ:2682557218)


English

An unofficial native Windows port of Ninja Gaiden Black (including the Hurricane Chinese translation vb-zh-x2.1) and Ninja Gaiden (2004). 2.2.27.

2.2.27: the 21:9 / 16:10 HUD decided by the game itself; no more game picture at the shop's sides

1. HUD at the sides or in the middle: asked of the game

2.2.26 lowered the in-play test from 30 3D draws to 1, which stopped the HUD jumping while turning in first person. That was still an inference from how much 3D a frame drew, not the game's own decision. This version uses the game's own decision.

  • Why not tell HUD and menus apart by who draws them: tried first, logging which game function drew each 2D piece. Every 2D piece of the HUD and of the menus takes the same path: the game puts all its 2D in one list and one function (FUN_00222730) draws it all. At draw time the HUD cannot be told from a menu.
  • The game's own HUD routine: as ngbrecomp found (src/hud.c), FUN_001FA210 draws the HUD; checked against our own disassembly, the same addresses and logic. It draws the HUD only when three of the game's conditions hold: [0xD6AF00] == 1, [0xDB5A63] >= 0x28 and the HUD not hidden by the game ([0xDB9C6E] == 0xFFFF). Only that branch ends with mov eax, 1.
  • How: that mov eax, 1 becomes a call to a three-instruction stub: count, mov eax, 1, return. The game behaves exactly as before. A frame whose count moved drew its HUD and is in play, whatever 3D it drew.
  • Where it applies: found at startup by its bytes (data addresses not compared), patched only on exactly one match. Every Ninja Gaiden Black build (Hurricane zh/en and ja/en, basic, the US release) has it at the same place (0x1FA2AD); Ninja Gaiden 2004 disc (0x1DA31F) and title update (0x1EB722) have the same routine. Without it the 2.2.26 rule is used.
  • Order checked: over 3600 frames each in Ninja Gaiden Black and 2004 (disc), the HUD routine ran before the frame's 2D every time, so a frame's state is known when its 2D is laid out.
  • Tested: Black at 21:9, a save loaded, first person turning: the HUD stays at the sides; the pause, item, weapon and ninpo menus stay in the middle. 2004 disc, a save in play: HUD at the sides (3150 frames running without a jump), menus in the middle and back to the sides when closed.

2. The shop showing the game and the health bar at its sides

  • What players saw: at 21:9 in Muramasa's shop, the sides beyond the shop showed the game, the health bar in the top-left too.
  • Evidence (every draw of one frame logged):
    • The weapon menu (2004, frame 13458): no 3D at all; a plain full-screen quad covers the screen, then the menu. No game picture is ever on screen, so the sides are black.
    • The shop (Black, frame 3137): on entering, the game keeps the last frame of play as a picture (512x512), then each frame draws that picture over the whole screen as the backdrop, a blurred glow of it, and the shop's art over that.
  • Cause: the kept picture is our 21:9 frame, with the game and the HUD (moved to the sides) at its sides. At 16:9 the shop's art covers nearly all of it; at 21:9 the art covers only the middle 16:9, so its sides showed. Since 2.2.12 moved the HUD to the sides, the health bar showed too. Not a defect of the game: its way of drawing meeting our 21:9 extension.
  • Why the first attempt did nothing: it clipped full-screen copies to the 16:9 middle out of play, but such a "picture put back where it was" (texture coordinates following the screen) first goes down the path made for the underwater wobble, which draws it full width as it is and returns, never reaching the clip.
  • Why the second works: the test is inside that path, before it returns: out of play, such a picture covering the screen is drawn only in its 16:9 middle, black beyond, as with the weapon menu (above and below at 16:10).
  • Is the shop special-cased? No. Nothing in the code names the shop; the rule is general: in a frame out of play, any full-screen picture put back in place is drawn in its 16:9 middle. The shop is the one screen confirmed to draw so; any other drawn the same way gets the same. The underwater wobble is in play and stays as it was.
  • Tested: at 21:9 the shop's sides are black, no health bar; the weapon and pause menus as before.

Tests

  • Ninja Gaiden Black chapter-1 benchmark, 185 seconds (Iris Xe integrated graphics): 16:9 median frame time 5.38 ms (2.2.26: 5.38 ms), 1 late frame of 2694; 21:9 median 6.02 ms (2.2.26: 5.86 ms; repeated 21:9 runs vary between 5.86 and 6.02 ms), 99% 10.20 ms (2.2.26: 10.35 ms). The two new tests add one comparison per frame in play.
  • Windows Defender scan of the three programs: no threats.

Package

  • ngb-hurricane-pc-2.2.27-win32.zip
  • Size: 3,058,254 bytes
  • SHA-256: f7f62ab5e825edb45a4a373809119e7b064bcab8c5b2976d8bb9d1f8e42cbe85
  • Symbols ngb-hurricane-pc-2.2.27-win32-symbols.zip: 23,786,617 bytes
  • SHA-256: 64674776ff2d9903f4f18059beeeb30c8479bc9063bcbd259961a6d4a08fa45d

Author: 哈雅布撒 on Bilibili (QQ: 2682557218)

Don't miss a new ngb-pc-native-port-release release

NewReleases is sending notifications on new releases.