diff --git a/docs/sensor-bundles.md b/docs/sensor-bundles.md index 3b7eba3..c51e8de 100644 --- a/docs/sensor-bundles.md +++ b/docs/sensor-bundles.md @@ -49,6 +49,15 @@ bundle with no manifest still resolves through the compatibility adapter. ## Compatibility for existing bundles +The shipped Finger compute assets under `sensors/finger/assets/30fps-0703/` mirror the +[Studio calibration baseline](../../orisys-app/apps/studio/config/sensors/finger/assets/30fps-0703/). +Synchronize the complete mesh, camera intrinsics, camera pose and UV cache together; the current +profile uses `source_scale=0.42`. The SDK retains its own copy and has no runtime dependency on a +Studio checkout. The obsolete `0.4` cache from the previous geometry is not shipped. +`tests/test_finger_asset_identity.py` pins the verified calibration geometry and domain identity. +Changing SHA fields alone does not migrate a calibration; regenerate and validate its coordinate +artifact against the selected bundle before using its gain map. + `resolve_bundle` reads a new-shape descriptor when `schema_version` is present. Otherwise - no manifest, or the older `name`/`sensor_json`/`assets_dir`/`viz_pose` shape - the adapter describes it. That is the only place a folder name is consulted, and only for the built-in set: diff --git a/sensors/finger/assets/30fps-0703/housing.npz b/sensors/finger/assets/30fps-0703/housing.npz new file mode 100644 index 0000000..f036a8f Binary files /dev/null and b/sensors/finger/assets/30fps-0703/housing.npz differ diff --git a/sensors/finger/assets/30fps-0703/mesh.npz b/sensors/finger/assets/30fps-0703/mesh.npz index 4da6bb1..b00110c 100644 Binary files a/sensors/finger/assets/30fps-0703/mesh.npz and b/sensors/finger/assets/30fps-0703/mesh.npz differ diff --git a/sensors/finger/assets/30fps-0703/unroll_map_uv_s0.4.npz b/sensors/finger/assets/30fps-0703/unroll_map_uv_s0.4.npz deleted file mode 100644 index 995cee0..0000000 Binary files a/sensors/finger/assets/30fps-0703/unroll_map_uv_s0.4.npz and /dev/null differ diff --git a/sensors/finger/assets/30fps-0703/unroll_map_uv_s0.42.npz b/sensors/finger/assets/30fps-0703/unroll_map_uv_s0.42.npz index f4884a1..b88abf6 100644 Binary files a/sensors/finger/assets/30fps-0703/unroll_map_uv_s0.42.npz and b/sensors/finger/assets/30fps-0703/unroll_map_uv_s0.42.npz differ diff --git a/sensors/finger/assets/30fps-0703/world_to_cam.npy b/sensors/finger/assets/30fps-0703/world_to_cam.npy index 3d6f897..a4b39d3 100644 Binary files a/sensors/finger/assets/30fps-0703/world_to_cam.npy and b/sensors/finger/assets/30fps-0703/world_to_cam.npy differ diff --git a/tests/test_finger_asset_identity.py b/tests/test_finger_asset_identity.py new file mode 100644 index 0000000..a7bca2c --- /dev/null +++ b/tests/test_finger_asset_identity.py @@ -0,0 +1,29 @@ +"""Keep the shipped Finger compute assets aligned with the verified Studio calibration.""" + +import hashlib +from pathlib import Path + +import numpy as np + +from orisys.calibration_context import domain_fingerprint +from orisys.finger.runtime import resolve_finger_geometry + + +def test_shipped_finger_assets_match_the_verified_calibration_geometry(): + root = Path(__file__).resolve().parents[1] / "sensors" / "finger" + assets = root / "assets" / "30fps-0703" + # Recorded by the 2026-10-17 calibration run; changing this bundle requires revalidation. + expected = { + "mesh.npz": "fc47c438c745ada2c27775a0437fcbe8bfe8fbab354abdae390a07f7a26b78ac", + "camera_intrinsics.npz": "c8e2b1fbd89c1cf514186dd69b10f38ee73d0de1d41f0d1b40018e2650f939e3", + "world_to_cam.npy": "f8cb4109b5a1585833da0845c3644a9554eea55cc38854bf2e6b196e011a5506", + "unroll_map_uv_s0.42.npz": "397fada8a584b03327ec62eebc179f7b6406b7f9cc35248e8f3d0a068873f0c8", + } + for name, digest in expected.items(): + assert hashlib.sha256((assets / name).read_bytes()).hexdigest() == digest, name + with np.load(assets / "unroll_map_uv_s0.42.npz", allow_pickle=False) as archive: + domain = {key: archive[key] for key in archive.files} + assert domain_fingerprint(domain) == "2a76d8e797c7400f734d141b21fec5d9e65a02db418e0acacc36faf7c5ac8dbc" + geometry = resolve_finger_geometry(export_dir=assets, config=str(root / "sensor.json")) + assert geometry.source_scale == .42 + assert (geometry.out_width, geometry.out_height) == (280, 300)