From 4033159b1f2a5b6fed77d2aabb5024363694ebcf Mon Sep 17 00:00:00 2001 From: ud18010 Date: Fri, 17 Jul 2026 17:18:56 +0800 Subject: [PATCH] =?UTF-8?q?ModelTranslator:=20RizomUV=20=E9=97=B4=E6=AD=87?= =?UTF-8?q?=20IPC=20=E5=A4=B1=E8=B4=A5=E6=8D=A2=E6=96=B0=E5=AE=9E=E4=BE=8B?= =?UTF-8?q?=E9=87=8D=E8=AF=95=E4=B8=80=E6=AC=A1=EF=BC=88=E5=AE=9E=E6=B5=8B?= =?UTF-8?q?=20Cut=20=E5=81=B6=E5=8F=91=202000ms=20not=20responding?= =?UTF-8?q?=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- Tools/ModelTranslator/rizom_unwrap.py | 22 ++++++++++++++++--- .../tests/test_rizom_unwrap.py | 22 +++++++++++++++++++ 2 files changed, 41 insertions(+), 3 deletions(-) diff --git a/Tools/ModelTranslator/rizom_unwrap.py b/Tools/ModelTranslator/rizom_unwrap.py index 09e8d44a..5326851e 100644 --- a/Tools/ModelTranslator/rizom_unwrap.py +++ b/Tools/ModelTranslator/rizom_unwrap.py @@ -91,16 +91,32 @@ def _call(label, fn, params, timeout=TIMEOUT_S): return res +RETRY = 1 # 实例级重试次数:RizomUV IPC 有 2000ms 内部响应窗,偶发 not responding + + def rizom_unwrap(fbx_path, exe, map_res=MAP_RES, padding_px=PADDING_PX): - """AutoSeam 全自动切缝 -> Unfold -> Pack -> 覆盖保存 fbx_path。失败抛 RizomError。""" + """AutoSeam 全自动切缝 -> Unfold -> Pack -> 覆盖保存 fbx_path。失败抛 RizomError。 + 间歇性 IPC 失败自动换新实例重试一次。""" mod = _import_link(exe) + fbx_abs = os.path.abspath(fbx_path) + pad_uv = float(padding_px) / map_res + last = None + for attempt in range(1 + RETRY): + if attempt: + print("[警告] RizomUV 第 %d 次失败(%s),换新实例重试" % (attempt, last)) + try: + return _unwrap_once(mod, exe, fbx_abs, map_res, pad_uv) + except RizomError as e: + last = e + raise RizomError("重试后仍失败:%s" % last) + + +def _unwrap_once(mod, exe, fbx_abs, map_res, pad_uv): link = mod.CRizomUVLink() try: _call("RunRizomUV", lambda _p: link.RunRizomUV(exePath=exe), None, timeout=60) except RizomError as e: raise RizomError("RizomUV 启动失败(license/环境):%s" % e) - fbx_abs = os.path.abspath(fbx_path) - pad_uv = float(padding_px) / map_res try: _call("Load", link.Load, {"File.Path": fbx_abs, "File.XYZ": True}) # AutoSeam:MOSAIC(QuasiDevelopable) + 切柄/连洞 + 防重叠后处理 diff --git a/Tools/ModelTranslator/tests/test_rizom_unwrap.py b/Tools/ModelTranslator/tests/test_rizom_unwrap.py index 59908c5b..a8443965 100644 --- a/Tools/ModelTranslator/tests/test_rizom_unwrap.py +++ b/Tools/ModelTranslator/tests/test_rizom_unwrap.py @@ -50,5 +50,27 @@ class TestCall(unittest.TestCase): self.assertEqual(ru._call("Ok", lambda p: {"Data": 1}, {}), {"Data": 1}) +class TestRetry(unittest.TestCase): + def test_second_attempt_succeeds(self): + calls = [] + + def fake_once(*a, **kw): + calls.append(1) + if len(calls) == 1: + raise ru.RizomError("IPC 抖动") + + with mock.patch.object(ru, "_import_link"), \ + mock.patch.object(ru, "_unwrap_once", side_effect=fake_once): + ru.rizom_unwrap("x.fbx", "rizomuv.exe") + self.assertEqual(len(calls), 2) + + def test_both_attempts_fail_raises(self): + with mock.patch.object(ru, "_import_link"), \ + mock.patch.object(ru, "_unwrap_once", + side_effect=ru.RizomError("持续失败")), \ + self.assertRaises(ru.RizomError): + ru.rizom_unwrap("x.fbx", "rizomuv.exe") + + if __name__ == "__main__": unittest.main()