{ "schema": "multispec_module_params_v3", "saved_at": "2026-05-07 14:41:12", "frame_type": "RAW_BRUTO", "capture_mode_requested": "AUTO", "capture_mode_effective": "AUTO", "raw_policy": "allow_single", "sensor_width": 1280, "sensor_height": 800, "bayer_pattern": "RGGB", "camera_settings": { "rgb": { "ae_enable": false, "awb_enable": false, "exposure_time_us": 2000, "analogue_gain": 1.0, "colour_gains": [ 1.0, 1.0 ] }, "re": { "ae_enable": false, "awb_enable": false, "exposure_time_us": 5000, "analogue_gain": 1.0, "colour_gains": null }, "nir": { "ae_enable": false, "awb_enable": false, "exposure_time_us": 5000, "analogue_gain": 1.0, "colour_gains": null } }, "fusion_config": { "alignment_mode": "homography", "baseline_mm": 75.0, "reference_camera": "rgb", "manual_offsets": { "re": { "dx": 0, "dy": 0, "theta_deg": 0.0 }, "nir": { "dx": 0, "dy": 0, "theta_deg": 0.0 } }, "homographies": { "re_to_rgb": [ [ 0.9836077983170345, -0.00414576215755023, -7.995670153079967 ], [ -0.009155951570825544, 0.9872093474367271, 65.61737450021248 ], [ -8.515127189657688e-06, -3.4530877754475106e-06, 1.0 ] ], "nir_to_rgb": [ [ 0.9950840771095427, -0.01203311522937068, -0.37678489564225515 ], [ 0.005818513521498549, 0.9844634830519817, 40.58679770900771 ], [ 1.1689856045746963e-05, -1.643688958474221e-05, 1.0 ] ] }, "crop_valid_common": true, "resize_after_crop": true, "target_size": null }, "radiometric_config": { "enabled": true, "interval_s": 0.5, "verbose": true, "metering_mode": "reference_patches", "spectral_control_mode": "shared", "control_metric": "p50", "target_value": 0.5, "deadband": 0.035, "p95_limit": 0.94, "saturation_limit_pct": 0.5, "alpha": 0.18, "exp_step_gain": 0.55, "prefer_exposure": true, "exp_min_us": 100, "exp_max_us": 80000, "gain_min": 1.0, "gain_max": 4.0, "reference_patches": [ { "name": "black_reference", "type": "black", "roles": [ "rgb", "re", "nir" ], "roi_pct": { "x0": 0.376563, "y0": 0.81, "x1": 0.440625, "y1": 0.985 }, "target_value": 0.08, "weight": 0.7, "roi_pct_by_role": { "rgb": { "x0": 0.376563, "y0": 0.81, "x1": 0.440625, "y1": 0.985 }, "re": { "x0": 0.403125, "y0": 0.745, "x1": 0.459375, "y1": 0.92 }, "nir": { "x0": 0.364063, "y0": 0.775, "x1": 0.428125, "y1": 0.9425 } }, "roi_list_by_role": { "rgb": [ { "name": "rgb_legacy_01", "enabled": true, "roi_pct": { "x0": 0.376563, "y0": 0.81, "x1": 0.440625, "y1": 0.985 }, "created_at": "2026-05-07 14:36:25", "updated_at": "2026-05-07 14:39:47" } ], "re": [ { "name": "re_legacy_01", "enabled": true, "roi_pct": { "x0": 0.403125, "y0": 0.745, "x1": 0.459375, "y1": 0.92 }, "created_at": "2026-05-07 14:36:25", "updated_at": "2026-05-07 14:40:05" } ], "nir": [ { "name": "nir_legacy_01", "enabled": true, "roi_pct": { "x0": 0.364063, "y0": 0.775, "x1": 0.428125, "y1": 0.9425 }, "created_at": "2026-05-07 14:36:25", "updated_at": "2026-05-07 14:40:37" } ] } }, { "name": "gray_reference", "type": "gray", "roles": [ "rgb", "re", "nir" ], "roi_pct": { "x0": 0.30625, "y0": 0.8225, "x1": 0.370312, "y1": 0.985 }, "target_value": 0.5, "target_value_by_role": { "rgb": 0.34, "re": 0.24, "nir": 0.30 }, "weight": 1.0, "roi_pct_by_role": { "rgb": { "x0": 0.30625, "y0": 0.8225, "x1": 0.370312, "y1": 0.985 }, "re": { "x0": 0.332813, "y0": 0.745, "x1": 0.395313, "y1": 0.915 }, "nir": { "x0": 0.29375, "y0": 0.775, "x1": 0.35625, "y1": 0.94 } }, "roi_list_by_role": { "rgb": [ { "name": "rgb_legacy_01", "enabled": true, "roi_pct": { "x0": 0.30625, "y0": 0.8225, "x1": 0.370312, "y1": 0.985 }, "created_at": "2026-05-07 14:36:25", "updated_at": "2026-05-07 14:39:15" } ], "re": [ { "name": "re_legacy_01", "enabled": true, "roi_pct": { "x0": 0.332813, "y0": 0.745, "x1": 0.395313, "y1": 0.915 }, "created_at": "2026-05-07 14:36:25", "updated_at": "2026-05-07 14:40:15" } ], "nir": [ { "name": "nir_legacy_01", "enabled": true, "roi_pct": { "x0": 0.29375, "y0": 0.775, "x1": 0.35625, "y1": 0.94 }, "created_at": "2026-05-07 14:36:25", "updated_at": "2026-05-07 14:40:46" } ] } }, { "name": "white_reference", "type": "white", "roles": [ "rgb", "re", "nir" ], "roi_pct": { "x0": 0.232813, "y0": 0.8225, "x1": 0.3, "y1": 0.99 }, "target_value": 0.82, "weight": 0.8, "roi_pct_by_role": { "rgb": { "x0": 0.232813, "y0": 0.8225, "x1": 0.3, "y1": 0.99 }, "re": { "x0": 0.2625, "y0": 0.7525, "x1": 0.321875, "y1": 0.9225 }, "nir": { "x0": 0.220312, "y0": 0.775, "x1": 0.284375, "y1": 0.9425 } }, "roi_list_by_role": { "rgb": [ { "name": "rgb_legacy_01", "enabled": true, "roi_pct": { "x0": 0.232813, "y0": 0.8225, "x1": 0.3, "y1": 0.99 }, "created_at": "2026-05-07 14:36:25", "updated_at": "2026-05-07 14:39:38" } ], "re": [ { "name": "re_legacy_01", "enabled": true, "roi_pct": { "x0": 0.2625, "y0": 0.7525, "x1": 0.321875, "y1": 0.9225 }, "created_at": "2026-05-07 14:36:25", "updated_at": "2026-05-07 14:40:24" } ], "nir": [ { "name": "nir_legacy_01", "enabled": true, "roi_pct": { "x0": 0.220312, "y0": 0.775, "x1": 0.284375, "y1": 0.9425 }, "created_at": "2026-05-07 14:36:25", "updated_at": "2026-05-07 14:40:55" } ] } } ], "exp_apply_threshold_us": 80, "gain_apply_threshold": 0.05, "apply_same_spectral_to_both": true, "spectral_roles": [ "re", "nir" ], "dark_limit_pct": 35.0, "control_strategy": "ratio", "ratio_alpha": 0.35, "ratio_min": 0.65, "ratio_max": 1.35, "reduce_fast_factor": 0.80, "factor_min": 0.55, "factor_max": 1.28, "gain_return_enabled": true, "gain_reduce_on_saturation": true, "gain_increase_required_cycles": 5, "gain_decrease_required_cycles": 2, "gain_step_up": 0.2, "gain_step_down": 0.5, "gain_hard_reset_on_saturation": false, "exp_high_ratio_for_gain": 0.95, "exp_low_ratio_for_gain_return": 0.75, "role_limits": { "rgb": { "exp_min_us": 100, "exp_max_us": 80000, "gain_min": 1.0, "gain_max": 2.0 }, "re": { "exp_min_us": 100, "exp_max_us": 2500, "gain_min": 1.0, "gain_max": 2.0 }, "nir": { "exp_min_us": 100, "exp_max_us": 3000, "gain_min": 1.0, "gain_max": 2.0 } }, "ready_required_cycles": 3, "patch_control_mode": "gray_primary", "patch_require_order": true, "patch_min_separation": 0.08, "patch_white_sat_limit_pct": 0.5, "patch_white_p95_limit": 0.94, "patch_black_dark_limit_pct": 80.0, "patch_black_max_p50": 0.2, "patch_gray_min_p50": 0.08, "patch_gray_max_p50": 0.85, "patch_roi_contract": "multi_roi_by_role_v1", "patch_roi_reduce_method": "median_valid_rois", "patch_roi_outlier_reject": true, "patch_roi_max_p50_delta": 0.12 }, "radiometric_normalization": { "enabled": true, "method": "exposure_gain_reference", "apply_stage": "after_dark_before_flat_gain", "reference_controls": { "rgb": { "exposure_time_us": 3000, "analogue_gain": 1.0 }, "re": { "exposure_time_us": 7000, "analogue_gain": 1.0 }, "nir": { "exposure_time_us": 7000, "analogue_gain": 1.0 } }, "clip_output": true }, "patch_normalization": { "enabled": true, "apply_when_metering_mode": "reference_patches", "apply_stage": "after_fusion", "method": "gray_scale_with_white_guard", "space": "multispec_tensor", "targets": { "black": 0.06, "gray": 0.4, "white": 0.78 }, "white_guard_max": 0.92, "scale_min": 0.35, "scale_max": 2.5, "clip_output": true, "require_valid_gray": true, "use_black_for_offset": false, "save_patch_stats": true }, "rgb_calibration": { "enabled": true, "gains": { "R": 1.2500000000000002, "G": 1.0, "B": 1.5500000000000005 } }, "flatfield_config": { "enabled": true, "subtract_dark": true, "schema": "multispec_flatfield_v1", "created_at": "2026-05-06 13:37:25", "json_file": "calibration/flatfield_maps_v1.json", "npz_file": "calibration/flatfield_maps_v1.npz", "apply_before_fusion": true, "apply_after_decode": true, "apply_space": "native_camera_space", "map_type": "gain", "formula": "channel_corrected = max(channel_linear - dark, 0) * gain_map", "channels": [ "R", "G", "B", "RE", "NIR" ], "channel_maps": { "R": { "gain_key": "gain_R", "flat_norm_key": "flat_norm_R", "white_median_key": "white_median_R", "dark_median_key": "dark_median_R", "shape": [ 400, 640 ], "gain_min": 0.5639018416404724, "gain_max": 1.8886771202087402, "gain_mean": 1.0681155920028687, "gain_std": 0.3506295084953308 }, "G": { "gain_key": "gain_G", "flat_norm_key": "flat_norm_G", "white_median_key": "white_median_G", "dark_median_key": "dark_median_G", "shape": [ 400, 640 ], "gain_min": 0.5427238941192627, "gain_max": 2.177884101867676, "gain_mean": 1.0985527038574219, "gain_std": 0.4235461354255676 }, "B": { "gain_key": "gain_B", "flat_norm_key": "flat_norm_B", "white_median_key": "white_median_B", "dark_median_key": "dark_median_B", "shape": [ 400, 640 ], "gain_min": 0.57332444190979, "gain_max": 1.991808533668518, "gain_mean": 1.0765669345855713, "gain_std": 0.36871764063835144 }, "RE": { "gain_key": "gain_RE", "flat_norm_key": "flat_norm_RE", "white_median_key": "white_median_RE", "dark_median_key": "dark_median_RE", "shape": [ 800, 1280 ], "gain_min": 0.7719405889511108, "gain_max": 1.6437114477157593, "gain_mean": 1.0222759246826172, "gain_std": 0.19225353002548218 }, "NIR": { "gain_key": "gain_NIR", "flat_norm_key": "flat_norm_NIR", "white_median_key": "white_median_NIR", "dark_median_key": "dark_median_NIR", "shape": [ 800, 1280 ], "gain_min": 0.808167576789856, "gain_max": 1.5716955661773682, "gain_mean": 1.021193265914917, "gain_std": 0.1498267650604248 } }, "exp_gain_correct_during_flat_capture": true, "smooth_ksize": 31, "min_gain": 0.25, "max_gain": 4.0, "notes": "" } }