@photivra/engine 1.4.0 → 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (1074) hide show
  1. package/CHANGELOG.md +401 -6
  2. package/CITATION.cff +1 -1
  3. package/NODE_SUPPORT.md +64 -12
  4. package/README.md +301 -182
  5. package/SECURITY.md +37 -28
  6. package/THIRD_PARTY.md +148 -4
  7. package/dist/camera/equivalent-focal-length.d.ts +13 -14
  8. package/dist/camera/equivalent-focal-length.js +15 -13
  9. package/dist/camera/equivalent-focal-length.js.map +1 -1
  10. package/dist/camera/field-of-view.d.ts +30 -19
  11. package/dist/camera/field-of-view.js +67 -18
  12. package/dist/camera/field-of-view.js.map +1 -1
  13. package/dist/camera/lens-projection.d.ts +170 -0
  14. package/dist/camera/lens-projection.js +444 -0
  15. package/dist/camera/lens-projection.js.map +1 -0
  16. package/dist/camera/projected-object-size.d.ts +10 -11
  17. package/dist/camera/projected-object-size.js +12 -10
  18. package/dist/camera/projected-object-size.js.map +1 -1
  19. package/dist/capture/capture-export-metadata.d.ts +9 -10
  20. package/dist/capture/capture-export-metadata.js +8 -5
  21. package/dist/capture/capture-export-metadata.js.map +1 -1
  22. package/dist/capture/dng-import.d.ts +91 -0
  23. package/dist/capture/dng-import.js +343 -0
  24. package/dist/capture/dng-import.js.map +1 -0
  25. package/dist/capture/environment-raw-producer.d.ts +37 -17
  26. package/dist/capture/environment-raw-producer.js +43 -19
  27. package/dist/capture/environment-raw-producer.js.map +1 -1
  28. package/dist/capture/export-jpeg.d.ts +35 -4
  29. package/dist/capture/export-jpeg.js +133 -47
  30. package/dist/capture/export-jpeg.js.map +1 -1
  31. package/dist/capture/export-tiff.d.ts +48 -24
  32. package/dist/capture/export-tiff.js +91 -31
  33. package/dist/capture/export-tiff.js.map +1 -1
  34. package/dist/capture/focus-control.d.ts +42 -65
  35. package/dist/capture/focus-control.js +56 -75
  36. package/dist/capture/focus-control.js.map +1 -1
  37. package/dist/capture/host-yield-cadence.d.ts +25 -0
  38. package/dist/capture/host-yield-cadence.js +25 -0
  39. package/dist/capture/host-yield-cadence.js.map +1 -0
  40. package/dist/capture/linear-encoding.d.ts +14 -12
  41. package/dist/capture/linear-encoding.js +14 -13
  42. package/dist/capture/linear-encoding.js.map +1 -1
  43. package/dist/capture/lossless-jpeg.d.ts +27 -0
  44. package/dist/capture/lossless-jpeg.js +237 -0
  45. package/dist/capture/lossless-jpeg.js.map +1 -0
  46. package/dist/capture/native-environment-lean.d.ts +227 -0
  47. package/dist/capture/native-environment-lean.js +974 -0
  48. package/dist/capture/native-environment-lean.js.map +1 -0
  49. package/dist/capture/native-environment-optical-stage.d.ts +97 -0
  50. package/dist/capture/native-environment-optical-stage.js +340 -0
  51. package/dist/capture/native-environment-optical-stage.js.map +1 -0
  52. package/dist/capture/native-environment-raw.d.ts +140 -6
  53. package/dist/capture/native-environment-raw.js +435 -34
  54. package/dist/capture/native-environment-raw.js.map +1 -1
  55. package/dist/capture/native-raw-development.d.ts +118 -5
  56. package/dist/capture/native-raw-development.js +224 -59
  57. package/dist/capture/native-raw-development.js.map +1 -1
  58. package/dist/capture/native-raw-dng.d.ts +60 -0
  59. package/dist/capture/native-raw-dng.js +167 -0
  60. package/dist/capture/native-raw-dng.js.map +1 -0
  61. package/dist/capture/native-raw.d.ts +67 -10
  62. package/dist/capture/native-raw.js +90 -24
  63. package/dist/capture/native-raw.js.map +1 -1
  64. package/dist/capture/packed-sensor-raw.d.ts +160 -0
  65. package/dist/capture/packed-sensor-raw.js +221 -0
  66. package/dist/capture/packed-sensor-raw.js.map +1 -0
  67. package/dist/capture/photographic-export.d.ts +58 -35
  68. package/dist/capture/photographic-export.js +177 -70
  69. package/dist/capture/photographic-export.js.map +1 -1
  70. package/dist/capture/raw-development-kernel.d.ts +52 -0
  71. package/dist/capture/raw-development-kernel.js +88 -0
  72. package/dist/capture/raw-development-kernel.js.map +1 -0
  73. package/dist/capture/raw-frame-limits.d.ts +7 -7
  74. package/dist/capture/raw-frame-limits.js +7 -6
  75. package/dist/capture/raw-frame-limits.js.map +1 -1
  76. package/dist/capture/raw-frame-reconstruction.d.ts +8 -9
  77. package/dist/capture/raw-frame-reconstruction.js +9 -8
  78. package/dist/capture/raw-frame-reconstruction.js.map +1 -1
  79. package/dist/capture/raw-white-level.d.ts +55 -0
  80. package/dist/capture/raw-white-level.js +165 -0
  81. package/dist/capture/raw-white-level.js.map +1 -0
  82. package/dist/capture/release-sequence.d.ts +5 -7
  83. package/dist/capture/release-sequence.js +15 -13
  84. package/dist/capture/release-sequence.js.map +1 -1
  85. package/dist/capture/sensor-raw-frame.d.ts +5 -6
  86. package/dist/capture/sensor-raw-frame.js +26 -9
  87. package/dist/capture/sensor-raw-frame.js.map +1 -1
  88. package/dist/capture/sensor-raw-producer.d.ts +21 -13
  89. package/dist/capture/sensor-raw-producer.js +86 -25
  90. package/dist/capture/sensor-raw-producer.js.map +1 -1
  91. package/dist/capture/simulated-capture.d.ts +15 -16
  92. package/dist/capture/simulated-capture.js +22 -12
  93. package/dist/capture/simulated-capture.js.map +1 -1
  94. package/dist/color/camera-color-matrix.d.ts +69 -0
  95. package/dist/color/camera-color-matrix.js +132 -0
  96. package/dist/color/camera-color-matrix.js.map +1 -0
  97. package/dist/color/capture-color.d.ts +17 -10
  98. package/dist/color/capture-color.js +50 -17
  99. package/dist/color/capture-color.js.map +1 -1
  100. package/dist/color/chromatic-adaptation.d.ts +63 -0
  101. package/dist/color/chromatic-adaptation.js +91 -0
  102. package/dist/color/chromatic-adaptation.js.map +1 -0
  103. package/dist/color/color-difference.d.ts +104 -0
  104. package/dist/color/color-difference.js +205 -0
  105. package/dist/color/color-difference.js.map +1 -0
  106. package/dist/color/color-matching-functions.d.ts +168 -0
  107. package/dist/color/color-matching-functions.js +309 -0
  108. package/dist/color/color-matching-functions.js.map +1 -0
  109. package/dist/color/colorimetry-math.d.ts +52 -0
  110. package/dist/color/colorimetry-math.js +144 -0
  111. package/dist/color/colorimetry-math.js.map +1 -0
  112. package/dist/color/gamut-mapping.d.ts +54 -0
  113. package/dist/color/gamut-mapping.js +107 -0
  114. package/dist/color/gamut-mapping.js.map +1 -0
  115. package/dist/color/illuminants.d.ts +182 -0
  116. package/dist/color/illuminants.js +434 -0
  117. package/dist/color/illuminants.js.map +1 -0
  118. package/dist/color/rgb-color-spaces.d.ts +79 -0
  119. package/dist/color/rgb-color-spaces.js +115 -0
  120. package/dist/color/rgb-color-spaces.js.map +1 -0
  121. package/dist/color/sensor-color-development.d.ts +33 -11
  122. package/dist/color/sensor-color-development.js +104 -30
  123. package/dist/color/sensor-color-development.js.map +1 -1
  124. package/dist/color/srgb-icc.d.ts +9 -2
  125. package/dist/color/srgb-icc.js +16 -5
  126. package/dist/color/srgb-icc.js.map +1 -1
  127. package/dist/color/srgb-transfer.d.ts +1 -2
  128. package/dist/color/srgb-transfer.js +1 -1
  129. package/dist/color/srgb-transfer.js.map +1 -1
  130. package/dist/color/white-balance.d.ts +68 -19
  131. package/dist/color/white-balance.js +168 -35
  132. package/dist/color/white-balance.js.map +1 -1
  133. package/dist/composition/image-formation-plan.d.ts +152 -128
  134. package/dist/composition/image-formation-plan.js +292 -138
  135. package/dist/composition/image-formation-plan.js.map +1 -1
  136. package/dist/composition/plan-consumer.d.ts +6 -7
  137. package/dist/composition/plan-consumer.js +14 -11
  138. package/dist/composition/plan-consumer.js.map +1 -1
  139. package/dist/core/calculation-result.d.ts +21 -14
  140. package/dist/core/calculation-result.js +209 -11
  141. package/dist/core/calculation-result.js.map +1 -1
  142. package/dist/core/canonical-json.d.ts +13 -8
  143. package/dist/core/canonical-json.js +34 -15
  144. package/dist/core/canonical-json.js.map +1 -1
  145. package/dist/core/configuration-error.d.ts +5 -4
  146. package/dist/core/configuration-error.js +5 -3
  147. package/dist/core/configuration-error.js.map +1 -1
  148. package/dist/core/evidence-provenance.d.ts +12 -12
  149. package/dist/core/evidence-provenance.js +10 -9
  150. package/dist/core/evidence-provenance.js.map +1 -1
  151. package/dist/core/image-formation.d.ts +11 -10
  152. package/dist/core/image-formation.js +11 -9
  153. package/dist/core/image-formation.js.map +1 -1
  154. package/dist/core/owned-data.d.ts +9 -17
  155. package/dist/core/owned-data.js +9 -16
  156. package/dist/core/owned-data.js.map +1 -1
  157. package/dist/core/portable-math.d.ts +15 -0
  158. package/dist/core/portable-math.js +56 -0
  159. package/dist/core/portable-math.js.map +1 -0
  160. package/dist/core/record-validation.d.ts +48 -9
  161. package/dist/core/record-validation.js +93 -19
  162. package/dist/core/record-validation.js.map +1 -1
  163. package/dist/core/scientific-assurance.d.ts +16 -14
  164. package/dist/core/scientific-assurance.js +22 -18
  165. package/dist/core/scientific-assurance.js.map +1 -1
  166. package/dist/core/spectral-composition.d.ts +13 -14
  167. package/dist/core/spectral-composition.js +30 -27
  168. package/dist/core/spectral-composition.js.map +1 -1
  169. package/dist/core/spectral.d.ts +5 -6
  170. package/dist/core/spectral.js +9 -7
  171. package/dist/core/spectral.js.map +1 -1
  172. package/dist/core/validation.d.ts +3 -6
  173. package/dist/core/validation.js +3 -5
  174. package/dist/core/validation.js.map +1 -1
  175. package/dist/core/version.d.ts +6 -6
  176. package/dist/core/version.js +6 -5
  177. package/dist/core/version.js.map +1 -1
  178. package/dist/equipment/exposure-capabilities.d.ts +10 -10
  179. package/dist/equipment/exposure-capabilities.js +40 -30
  180. package/dist/equipment/exposure-capabilities.js.map +1 -1
  181. package/dist/equipment/generic-tier-assets.d.ts +13 -6
  182. package/dist/equipment/generic-tier-assets.js +34 -15
  183. package/dist/equipment/generic-tier-assets.js.map +1 -1
  184. package/dist/equipment/generic-tier-presets.d.ts +5 -6
  185. package/dist/equipment/generic-tier-presets.js +15 -13
  186. package/dist/equipment/generic-tier-presets.js.map +1 -1
  187. package/dist/equipment/iso-capabilities.d.ts +21 -22
  188. package/dist/equipment/iso-capabilities.js +49 -44
  189. package/dist/equipment/iso-capabilities.js.map +1 -1
  190. package/dist/equipment/metering-capabilities.d.ts +5 -6
  191. package/dist/equipment/metering-capabilities.js +22 -19
  192. package/dist/equipment/metering-capabilities.js.map +1 -1
  193. package/dist/equipment/release-capabilities.d.ts +3 -4
  194. package/dist/equipment/release-capabilities.js +18 -14
  195. package/dist/equipment/release-capabilities.js.map +1 -1
  196. package/dist/exposure/exposure-duration-control.d.ts +19 -17
  197. package/dist/exposure/exposure-duration-control.js +27 -23
  198. package/dist/exposure/exposure-duration-control.js.map +1 -1
  199. package/dist/exposure/exposure-mode-resolver.d.ts +42 -39
  200. package/dist/exposure/exposure-mode-resolver.js +127 -82
  201. package/dist/exposure/exposure-mode-resolver.js.map +1 -1
  202. package/dist/exposure/exposure.d.ts +17 -16
  203. package/dist/exposure/exposure.js +22 -15
  204. package/dist/exposure/exposure.js.map +1 -1
  205. package/dist/exposure/flash-ttl.d.ts +135 -0
  206. package/dist/exposure/flash-ttl.js +193 -0
  207. package/dist/exposure/flash-ttl.js.map +1 -0
  208. package/dist/exposure/flash.d.ts +144 -36
  209. package/dist/exposure/flash.js +259 -59
  210. package/dist/exposure/flash.js.map +1 -1
  211. package/dist/exposure/metering-scene-radiance.d.ts +10 -10
  212. package/dist/exposure/metering-scene-radiance.js +42 -23
  213. package/dist/exposure/metering-scene-radiance.js.map +1 -1
  214. package/dist/exposure/metering-target.d.ts +8 -8
  215. package/dist/exposure/metering-target.js +30 -20
  216. package/dist/exposure/metering-target.js.map +1 -1
  217. package/dist/exposure/metering-temporal.d.ts +16 -15
  218. package/dist/exposure/metering-temporal.js +41 -19
  219. package/dist/exposure/metering-temporal.js.map +1 -1
  220. package/dist/exposure/metering.d.ts +64 -17
  221. package/dist/exposure/metering.js +159 -30
  222. package/dist/exposure/metering.js.map +1 -1
  223. package/dist/exposure/program-line.d.ts +5 -5
  224. package/dist/exposure/program-line.js +20 -13
  225. package/dist/exposure/program-line.js.map +1 -1
  226. package/dist/facade/camera-preset.d.ts +8 -0
  227. package/dist/facade/camera-preset.js +102 -0
  228. package/dist/facade/camera-preset.js.map +1 -0
  229. package/dist/facade/chart-radiance-batch.d.ts +57 -0
  230. package/dist/facade/chart-radiance-batch.js +121 -0
  231. package/dist/facade/chart-radiance-batch.js.map +1 -0
  232. package/dist/facade/chart-scenes.d.ts +177 -0
  233. package/dist/facade/chart-scenes.js +232 -0
  234. package/dist/facade/chart-scenes.js.map +1 -0
  235. package/dist/facade/host-yield.d.ts +7 -0
  236. package/dist/facade/host-yield.js +23 -0
  237. package/dist/facade/host-yield.js.map +1 -0
  238. package/dist/facade/scene-radiance.d.ts +117 -0
  239. package/dist/facade/scene-radiance.js +205 -0
  240. package/dist/facade/scene-radiance.js.map +1 -0
  241. package/dist/facade/simulate-capture.d.ts +284 -0
  242. package/dist/facade/simulate-capture.js +1026 -0
  243. package/dist/facade/simulate-capture.js.map +1 -0
  244. package/dist/gpu/chart-radiance-gpu.d.ts +17 -0
  245. package/dist/gpu/chart-radiance-gpu.js +176 -0
  246. package/dist/gpu/chart-radiance-gpu.js.map +1 -0
  247. package/dist/gpu/image-kernel-accelerator.d.ts +132 -0
  248. package/dist/gpu/image-kernel-accelerator.js +720 -0
  249. package/dist/gpu/image-kernel-accelerator.js.map +1 -0
  250. package/dist/gpu/image-kernel-execution.d.ts +92 -0
  251. package/dist/gpu/image-kernel-execution.js +84 -0
  252. package/dist/gpu/image-kernel-execution.js.map +1 -0
  253. package/dist/gpu/sensor-stage-gpu.d.ts +44 -0
  254. package/dist/gpu/sensor-stage-gpu.js +317 -0
  255. package/dist/gpu/sensor-stage-gpu.js.map +1 -0
  256. package/dist/gpu/temporal-sum-gpu.d.ts +23 -0
  257. package/dist/gpu/temporal-sum-gpu.js +150 -0
  258. package/dist/gpu/temporal-sum-gpu.js.map +1 -0
  259. package/dist/gpu/webgpu-runtime.d.ts +63 -0
  260. package/dist/gpu/webgpu-runtime.js +215 -0
  261. package/dist/gpu/webgpu-runtime.js.map +1 -0
  262. package/dist/gpu/wgsl-chart-kernel.d.ts +30 -0
  263. package/dist/gpu/wgsl-chart-kernel.js +165 -0
  264. package/dist/gpu/wgsl-chart-kernel.js.map +1 -0
  265. package/dist/gpu/wgsl-kernels.d.ts +53 -0
  266. package/dist/gpu/wgsl-kernels.js +365 -0
  267. package/dist/gpu/wgsl-kernels.js.map +1 -0
  268. package/dist/gpu/wgsl-sensor-kernel.d.ts +64 -0
  269. package/dist/gpu/wgsl-sensor-kernel.js +409 -0
  270. package/dist/gpu/wgsl-sensor-kernel.js.map +1 -0
  271. package/dist/index.d.ts +89 -25
  272. package/dist/index.js +59 -15
  273. package/dist/index.js.map +1 -1
  274. package/dist/motion/camera-rotation.d.ts +92 -40
  275. package/dist/motion/camera-rotation.js +84 -47
  276. package/dist/motion/camera-rotation.js.map +1 -1
  277. package/dist/motion/capture-rotation-inverse-mapping.d.ts +37 -34
  278. package/dist/motion/capture-rotation-inverse-mapping.js +32 -24
  279. package/dist/motion/capture-rotation-inverse-mapping.js.map +1 -1
  280. package/dist/motion/capture-rotation-temporal-quadrature.d.ts +39 -35
  281. package/dist/motion/capture-rotation-temporal-quadrature.js +37 -28
  282. package/dist/motion/capture-rotation-temporal-quadrature.js.map +1 -1
  283. package/dist/motion/capture-rotation-trajectory.d.ts +32 -28
  284. package/dist/motion/capture-rotation-trajectory.js +36 -26
  285. package/dist/motion/capture-rotation-trajectory.js.map +1 -1
  286. package/dist/motion/capture-translation-parallax-temporal-quadrature.d.ts +23 -21
  287. package/dist/motion/capture-translation-parallax-temporal-quadrature.js +33 -14
  288. package/dist/motion/capture-translation-parallax-temporal-quadrature.js.map +1 -1
  289. package/dist/motion/extended-object-projection.d.ts +19 -16
  290. package/dist/motion/extended-object-projection.js +38 -18
  291. package/dist/motion/extended-object-projection.js.map +1 -1
  292. package/dist/motion/projected-motion.d.ts +18 -17
  293. package/dist/motion/projected-motion.js +25 -17
  294. package/dist/motion/projected-motion.js.map +1 -1
  295. package/dist/motion/temporal-exposure-sum.d.ts +55 -0
  296. package/dist/motion/temporal-exposure-sum.js +141 -0
  297. package/dist/motion/temporal-exposure-sum.js.map +1 -0
  298. package/dist/motion/video-sequence.d.ts +111 -0
  299. package/dist/motion/video-sequence.js +179 -0
  300. package/dist/motion/video-sequence.js.map +1 -0
  301. package/dist/optics/aperture.d.ts +14 -15
  302. package/dist/optics/aperture.js +13 -11
  303. package/dist/optics/aperture.js.map +1 -1
  304. package/dist/optics/atmospheric-haze.d.ts +83 -0
  305. package/dist/optics/atmospheric-haze.js +113 -0
  306. package/dist/optics/atmospheric-haze.js.map +1 -0
  307. package/dist/optics/brown-conrady-distortion.d.ts +116 -0
  308. package/dist/optics/brown-conrady-distortion.js +291 -0
  309. package/dist/optics/brown-conrady-distortion.js.map +1 -0
  310. package/dist/optics/circle-of-confusion.d.ts +10 -10
  311. package/dist/optics/circle-of-confusion.js +15 -11
  312. package/dist/optics/circle-of-confusion.js.map +1 -1
  313. package/dist/optics/complex-pupil-psf.d.ts +64 -33
  314. package/dist/optics/complex-pupil-psf.js +190 -98
  315. package/dist/optics/complex-pupil-psf.js.map +1 -1
  316. package/dist/optics/depth-of-field.d.ts +25 -15
  317. package/dist/optics/depth-of-field.js +67 -27
  318. package/dist/optics/depth-of-field.js.map +1 -1
  319. package/dist/optics/diffraction.d.ts +14 -13
  320. package/dist/optics/diffraction.js +14 -10
  321. package/dist/optics/diffraction.js.map +1 -1
  322. package/dist/optics/focus-breathing.d.ts +88 -27
  323. package/dist/optics/focus-breathing.js +114 -23
  324. package/dist/optics/focus-breathing.js.map +1 -1
  325. package/dist/optics/focus-state.d.ts +18 -18
  326. package/dist/optics/focus-state.js +21 -15
  327. package/dist/optics/focus-state.js.map +1 -1
  328. package/dist/optics/front-of-lens-filter.d.ts +45 -14
  329. package/dist/optics/front-of-lens-filter.js +259 -88
  330. package/dist/optics/front-of-lens-filter.js.map +1 -1
  331. package/dist/optics/illumination-vignetting.d.ts +16 -17
  332. package/dist/optics/illumination-vignetting.js +40 -17
  333. package/dist/optics/illumination-vignetting.js.map +1 -1
  334. package/dist/optics/irradiance-convolution.d.ts +59 -0
  335. package/dist/optics/irradiance-convolution.js +138 -0
  336. package/dist/optics/irradiance-convolution.js.map +1 -0
  337. package/dist/optics/lateral-chromatic-aberration.d.ts +33 -30
  338. package/dist/optics/lateral-chromatic-aberration.js +33 -23
  339. package/dist/optics/lateral-chromatic-aberration.js.map +1 -1
  340. package/dist/optics/lens-psf-kernels.d.ts +89 -0
  341. package/dist/optics/lens-psf-kernels.js +175 -0
  342. package/dist/optics/lens-psf-kernels.js.map +1 -0
  343. package/dist/optics/lens-psf-profile.d.ts +78 -46
  344. package/dist/optics/lens-psf-profile.js +335 -124
  345. package/dist/optics/lens-psf-profile.js.map +1 -1
  346. package/dist/optics/longitudinal-chromatic-aberration.d.ts +102 -0
  347. package/dist/optics/longitudinal-chromatic-aberration.js +210 -0
  348. package/dist/optics/longitudinal-chromatic-aberration.js.map +1 -0
  349. package/dist/optics/polygon-diffraction.d.ts +80 -23
  350. package/dist/optics/polygon-diffraction.js +130 -25
  351. package/dist/optics/polygon-diffraction.js.map +1 -1
  352. package/dist/optics/profile-contract.d.ts +5 -6
  353. package/dist/optics/profile-contract.js +14 -11
  354. package/dist/optics/profile-contract.js.map +1 -1
  355. package/dist/optics/psf-foundation.d.ts +23 -23
  356. package/dist/optics/psf-foundation.js +24 -21
  357. package/dist/optics/psf-foundation.js.map +1 -1
  358. package/dist/optics/pupil-vignetting.d.ts +118 -0
  359. package/dist/optics/pupil-vignetting.js +264 -0
  360. package/dist/optics/pupil-vignetting.js.map +1 -0
  361. package/dist/optics/radial-distortion.d.ts +34 -33
  362. package/dist/optics/radial-distortion.js +37 -30
  363. package/dist/optics/radial-distortion.js.map +1 -1
  364. package/dist/optics/scene-to-sensor-irradiance.d.ts +47 -33
  365. package/dist/optics/scene-to-sensor-irradiance.js +73 -45
  366. package/dist/optics/scene-to-sensor-irradiance.js.map +1 -1
  367. package/dist/optics/scene-to-sensor-quadrature.d.ts +23 -18
  368. package/dist/optics/scene-to-sensor-quadrature.js +16 -11
  369. package/dist/optics/scene-to-sensor-quadrature.js.map +1 -1
  370. package/dist/optics/sensor-aperture-rays.d.ts +20 -4
  371. package/dist/optics/sensor-aperture-rays.js +32 -14
  372. package/dist/optics/sensor-aperture-rays.js.map +1 -1
  373. package/dist/optics/sensor-environment-query.d.ts +81 -16
  374. package/dist/optics/sensor-environment-query.js +145 -12
  375. package/dist/optics/sensor-environment-query.js.map +1 -1
  376. package/dist/optics/sensor-psf-quadrature.d.ts +12 -10
  377. package/dist/optics/sensor-psf-quadrature.js +18 -11
  378. package/dist/optics/sensor-psf-quadrature.js.map +1 -1
  379. package/dist/optics/sensor-psf-support.d.ts +8 -6
  380. package/dist/optics/sensor-psf-support.js +8 -5
  381. package/dist/optics/sensor-psf-support.js.map +1 -1
  382. package/dist/optics/stray-light.d.ts +22 -19
  383. package/dist/optics/stray-light.js +18 -12
  384. package/dist/optics/stray-light.js.map +1 -1
  385. package/dist/optics/thin-lens.d.ts +10 -9
  386. package/dist/optics/thin-lens.js +12 -8
  387. package/dist/optics/thin-lens.js.map +1 -1
  388. package/dist/optics/zernike-wavefront.d.ts +154 -0
  389. package/dist/optics/zernike-wavefront.js +352 -0
  390. package/dist/optics/zernike-wavefront.js.map +1 -0
  391. package/dist/output/capture-corrected-sdr.d.ts +16 -8
  392. package/dist/output/capture-corrected-sdr.js +16 -8
  393. package/dist/output/capture-corrected-sdr.js.map +1 -1
  394. package/dist/output/capture-geometry.d.ts +34 -36
  395. package/dist/output/capture-geometry.js +52 -32
  396. package/dist/output/capture-geometry.js.map +1 -1
  397. package/dist/output/capture-sdr.d.ts +7 -6
  398. package/dist/output/capture-sdr.js +11 -8
  399. package/dist/output/capture-sdr.js.map +1 -1
  400. package/dist/output/crop.d.ts +22 -6
  401. package/dist/output/crop.js +40 -6
  402. package/dist/output/crop.js.map +1 -1
  403. package/dist/output/geometric-transforms.d.ts +60 -23
  404. package/dist/output/geometric-transforms.js +111 -24
  405. package/dist/output/geometric-transforms.js.map +1 -1
  406. package/dist/output/lens-corrections.d.ts +27 -19
  407. package/dist/output/lens-corrections.js +29 -13
  408. package/dist/output/lens-corrections.js.map +1 -1
  409. package/dist/output/native-capture-sdr.d.ts +71 -16
  410. package/dist/output/native-capture-sdr.js +190 -33
  411. package/dist/output/native-capture-sdr.js.map +1 -1
  412. package/dist/output/png-encoder.d.ts +65 -0
  413. package/dist/output/png-encoder.js +461 -0
  414. package/dist/output/png-encoder.js.map +1 -0
  415. package/dist/output/print-contrast-reference.d.ts +10 -9
  416. package/dist/output/print-contrast-reference.js +10 -8
  417. package/dist/output/print-contrast-reference.js.map +1 -1
  418. package/dist/output/print-detail.d.ts +18 -17
  419. package/dist/output/print-detail.js +12 -10
  420. package/dist/output/print-detail.js.map +1 -1
  421. package/dist/output/print-jpeg.d.ts +26 -5
  422. package/dist/output/print-jpeg.js +117 -50
  423. package/dist/output/print-jpeg.js.map +1 -1
  424. package/dist/output/print-plan.d.ts +19 -19
  425. package/dist/output/print-plan.js +11 -10
  426. package/dist/output/print-plan.js.map +1 -1
  427. package/dist/output/print-region-statistics.d.ts +14 -15
  428. package/dist/output/print-region-statistics.js +11 -11
  429. package/dist/output/print-region-statistics.js.map +1 -1
  430. package/dist/output/sdr-rendering.d.ts +48 -10
  431. package/dist/output/sdr-rendering.js +114 -25
  432. package/dist/output/sdr-rendering.js.map +1 -1
  433. package/dist/output/subject-framing-crop.d.ts +6 -10
  434. package/dist/output/subject-framing-crop.js +23 -13
  435. package/dist/output/subject-framing-crop.js.map +1 -1
  436. package/dist/processing/demosaic.d.ts +90 -0
  437. package/dist/processing/demosaic.js +275 -0
  438. package/dist/processing/demosaic.js.map +1 -0
  439. package/dist/processing/denoise.d.ts +68 -0
  440. package/dist/processing/denoise.js +214 -0
  441. package/dist/processing/denoise.js.map +1 -0
  442. package/dist/processing/focus-stacking.d.ts +17 -0
  443. package/dist/processing/focus-stacking.js +80 -0
  444. package/dist/processing/focus-stacking.js.map +1 -0
  445. package/dist/processing/hdr.d.ts +54 -0
  446. package/dist/processing/hdr.js +172 -0
  447. package/dist/processing/hdr.js.map +1 -0
  448. package/dist/processing/image-ops.d.ts +66 -0
  449. package/dist/processing/image-ops.js +192 -0
  450. package/dist/processing/image-ops.js.map +1 -0
  451. package/dist/processing/panorama.d.ts +51 -0
  452. package/dist/processing/panorama.js +305 -0
  453. package/dist/processing/panorama.js.map +1 -0
  454. package/dist/processing/processing-task.d.ts +85 -0
  455. package/dist/processing/processing-task.js +164 -0
  456. package/dist/processing/processing-task.js.map +1 -0
  457. package/dist/processing/tone-mapping.d.ts +69 -0
  458. package/dist/processing/tone-mapping.js +310 -0
  459. package/dist/processing/tone-mapping.js.map +1 -0
  460. package/dist/schema/camera.d.ts +5 -4
  461. package/dist/schema/illumination-spectral.d.ts +13 -19
  462. package/dist/schema/illumination-spectral.js +23 -19
  463. package/dist/schema/illumination-spectral.js.map +1 -1
  464. package/dist/schema/illumination-temporal.d.ts +12 -15
  465. package/dist/schema/illumination-temporal.js +43 -28
  466. package/dist/schema/illumination-temporal.js.map +1 -1
  467. package/dist/schema/illumination.d.ts +5 -4
  468. package/dist/schema/illumination.js +55 -20
  469. package/dist/schema/illumination.js.map +1 -1
  470. package/dist/schema/scene-radiance-temporal.d.ts +9 -11
  471. package/dist/schema/scene-radiance-temporal.js +26 -23
  472. package/dist/schema/scene-radiance-temporal.js.map +1 -1
  473. package/dist/schema/scene-radiance.d.ts +17 -17
  474. package/dist/schema/scene-radiance.js +56 -34
  475. package/dist/schema/scene-radiance.js.map +1 -1
  476. package/dist/schema/scene.d.ts +14 -13
  477. package/dist/schema/validation.d.ts +0 -1
  478. package/dist/schema/validation.js +17 -15
  479. package/dist/schema/validation.js.map +1 -1
  480. package/dist/sensor/accumulated-charge.d.ts +45 -64
  481. package/dist/sensor/accumulated-charge.js +41 -47
  482. package/dist/sensor/accumulated-charge.js.map +1 -1
  483. package/dist/sensor/architecture.d.ts +22 -25
  484. package/dist/sensor/architecture.js +17 -16
  485. package/dist/sensor/architecture.js.map +1 -1
  486. package/dist/sensor/camera-saturation-capacity.d.ts +21 -28
  487. package/dist/sensor/camera-saturation-capacity.js +36 -34
  488. package/dist/sensor/camera-saturation-capacity.js.map +1 -1
  489. package/dist/sensor/capture-color-sampling-binding.d.ts +46 -51
  490. package/dist/sensor/capture-color-sampling-binding.js +39 -41
  491. package/dist/sensor/capture-color-sampling-binding.js.map +1 -1
  492. package/dist/sensor/capture-mode-timing.d.ts +8 -9
  493. package/dist/sensor/capture-mode-timing.js +24 -21
  494. package/dist/sensor/capture-mode-timing.js.map +1 -1
  495. package/dist/sensor/capture-mode.d.ts +28 -30
  496. package/dist/sensor/capture-mode.js +33 -31
  497. package/dist/sensor/capture-mode.js.map +1 -1
  498. package/dist/sensor/color-sampling.d.ts +30 -33
  499. package/dist/sensor/color-sampling.js +32 -37
  500. package/dist/sensor/color-sampling.js.map +1 -1
  501. package/dist/sensor/constant-rate-temporal-integration.d.ts +19 -23
  502. package/dist/sensor/constant-rate-temporal-integration.js +28 -26
  503. package/dist/sensor/constant-rate-temporal-integration.js.map +1 -1
  504. package/dist/sensor/dark-current.d.ts +53 -49
  505. package/dist/sensor/dark-current.js +87 -46
  506. package/dist/sensor/dark-current.js.map +1 -1
  507. package/dist/sensor/environment-photo-signal.d.ts +71 -30
  508. package/dist/sensor/environment-photo-signal.js +127 -46
  509. package/dist/sensor/environment-photo-signal.js.map +1 -1
  510. package/dist/sensor/eqe-electron-rate.d.ts +14 -13
  511. package/dist/sensor/eqe-electron-rate.js +34 -14
  512. package/dist/sensor/eqe-electron-rate.js.map +1 -1
  513. package/dist/sensor/eqe-local-exposure.d.ts +24 -24
  514. package/dist/sensor/eqe-local-exposure.js +15 -11
  515. package/dist/sensor/eqe-local-exposure.js.map +1 -1
  516. package/dist/sensor/eqe-temporal-exposure.d.ts +11 -11
  517. package/dist/sensor/eqe-temporal-exposure.js +15 -10
  518. package/dist/sensor/eqe-temporal-exposure.js.map +1 -1
  519. package/dist/sensor/exposure-window.d.ts +48 -34
  520. package/dist/sensor/exposure-window.js +77 -36
  521. package/dist/sensor/exposure-window.js.map +1 -1
  522. package/dist/sensor/fixed-pattern-noise.d.ts +108 -0
  523. package/dist/sensor/fixed-pattern-noise.js +166 -0
  524. package/dist/sensor/fixed-pattern-noise.js.map +1 -0
  525. package/dist/sensor/iso-gain.d.ts +44 -0
  526. package/dist/sensor/iso-gain.js +119 -0
  527. package/dist/sensor/iso-gain.js.map +1 -0
  528. package/dist/sensor/iso-signal-chain.d.ts +25 -48
  529. package/dist/sensor/iso-signal-chain.js +52 -66
  530. package/dist/sensor/iso-signal-chain.js.map +1 -1
  531. package/dist/sensor/local-exposure-binding.d.ts +21 -21
  532. package/dist/sensor/local-exposure-binding.js +22 -18
  533. package/dist/sensor/local-exposure-binding.js.map +1 -1
  534. package/dist/sensor/optical-stack.d.ts +36 -40
  535. package/dist/sensor/optical-stack.js +34 -37
  536. package/dist/sensor/optical-stack.js.map +1 -1
  537. package/dist/sensor/photon-energy.d.ts +22 -28
  538. package/dist/sensor/photon-energy.js +42 -34
  539. package/dist/sensor/photon-energy.js.map +1 -1
  540. package/dist/sensor/physical-charge-capacity.d.ts +20 -30
  541. package/dist/sensor/physical-charge-capacity.js +35 -36
  542. package/dist/sensor/physical-charge-capacity.js.map +1 -1
  543. package/dist/sensor/pixel-pitch.d.ts +2 -3
  544. package/dist/sensor/pixel-pitch.js +4 -2
  545. package/dist/sensor/pixel-pitch.js.map +1 -1
  546. package/dist/sensor/radiometry-readiness.d.ts +13 -15
  547. package/dist/sensor/radiometry-readiness.js +20 -17
  548. package/dist/sensor/radiometry-readiness.js.map +1 -1
  549. package/dist/sensor/raw-readout.d.ts +173 -83
  550. package/dist/sensor/raw-readout.js +425 -160
  551. package/dist/sensor/raw-readout.js.map +1 -1
  552. package/dist/sensor/raw-reconstruction.d.ts +112 -44
  553. package/dist/sensor/raw-reconstruction.js +200 -47
  554. package/dist/sensor/raw-reconstruction.js.map +1 -1
  555. package/dist/sensor/readout-exposure-linkage.d.ts +103 -34
  556. package/dist/sensor/readout-exposure-linkage.js +125 -27
  557. package/dist/sensor/readout-exposure-linkage.js.map +1 -1
  558. package/dist/sensor/readout-timing.d.ts +43 -44
  559. package/dist/sensor/readout-timing.js +38 -30
  560. package/dist/sensor/readout-timing.js.map +1 -1
  561. package/dist/sensor/response-application-compatibility.d.ts +21 -28
  562. package/dist/sensor/response-application-compatibility.js +35 -34
  563. package/dist/sensor/response-application-compatibility.js.map +1 -1
  564. package/dist/sensor/response-operating-range.d.ts +26 -35
  565. package/dist/sensor/response-operating-range.js +40 -39
  566. package/dist/sensor/response-operating-range.js.map +1 -1
  567. package/dist/sensor/responsivity-photocurrent.d.ts +21 -29
  568. package/dist/sensor/responsivity-photocurrent.js +57 -40
  569. package/dist/sensor/responsivity-photocurrent.js.map +1 -1
  570. package/dist/sensor/sampling-aperture.d.ts +21 -25
  571. package/dist/sensor/sampling-aperture.js +29 -28
  572. package/dist/sensor/sampling-aperture.js.map +1 -1
  573. package/dist/sensor/scene-eqe-temporal-exposure.d.ts +14 -12
  574. package/dist/sensor/scene-eqe-temporal-exposure.js +13 -8
  575. package/dist/sensor/scene-eqe-temporal-exposure.js.map +1 -1
  576. package/dist/sensor/sensor-geometry.d.ts +28 -32
  577. package/dist/sensor/sensor-geometry.js +35 -20
  578. package/dist/sensor/sensor-geometry.js.map +1 -1
  579. package/dist/sensor/signal-noise.d.ts +14 -16
  580. package/dist/sensor/signal-noise.js +15 -13
  581. package/dist/sensor/signal-noise.js.map +1 -1
  582. package/dist/sensor/spatial-sample-reduction.d.ts +45 -60
  583. package/dist/sensor/spatial-sample-reduction.js +39 -48
  584. package/dist/sensor/spatial-sample-reduction.js.map +1 -1
  585. package/dist/sensor/spatial-sampling-quadrature.d.ts +46 -54
  586. package/dist/sensor/spatial-sampling-quadrature.js +31 -36
  587. package/dist/sensor/spatial-sampling-quadrature.js.map +1 -1
  588. package/dist/sensor/spatio-spectral-reduction.d.ts +32 -42
  589. package/dist/sensor/spatio-spectral-reduction.js +24 -29
  590. package/dist/sensor/spatio-spectral-reduction.js.map +1 -1
  591. package/dist/sensor/spectral-coverage.d.ts +6 -9
  592. package/dist/sensor/spectral-coverage.js +9 -6
  593. package/dist/sensor/spectral-coverage.js.map +1 -1
  594. package/dist/sensor/spectral-quadrature.d.ts +46 -60
  595. package/dist/sensor/spectral-quadrature.js +38 -48
  596. package/dist/sensor/spectral-quadrature.js.map +1 -1
  597. package/dist/sensor/spectral-response.d.ts +53 -41
  598. package/dist/sensor/spectral-response.js +80 -47
  599. package/dist/sensor/spectral-response.js.map +1 -1
  600. package/dist/sensor/stochastic-seed.d.ts +50 -0
  601. package/dist/sensor/stochastic-seed.js +123 -0
  602. package/dist/sensor/stochastic-seed.js.map +1 -0
  603. package/dist/sensor/temporal-eqe-sum.d.ts +2 -4
  604. package/dist/sensor/temporal-eqe-sum.js +5 -6
  605. package/dist/sensor/temporal-eqe-sum.js.map +1 -1
  606. package/dist/sensor/temporal-photo-signal.d.ts +5 -6
  607. package/dist/sensor/temporal-photo-signal.js +11 -10
  608. package/dist/sensor/temporal-photo-signal.js.map +1 -1
  609. package/dist/sensor/temporal-sample-binding.d.ts +1 -2
  610. package/dist/sensor/temporal-sample-binding.js +3 -3
  611. package/dist/sensor/temporal-sample-binding.js.map +1 -1
  612. package/dist/simulation/poc-simulation.d.ts +16 -16
  613. package/dist/simulation/poc-simulation.js +20 -15
  614. package/dist/simulation/poc-simulation.js.map +1 -1
  615. package/dist/stabilization/camera-shake.d.ts +42 -18
  616. package/dist/stabilization/camera-shake.js +43 -20
  617. package/dist/stabilization/camera-shake.js.map +1 -1
  618. package/dist/stabilization/system.d.ts +44 -41
  619. package/dist/stabilization/system.js +196 -108
  620. package/dist/stabilization/system.js.map +1 -1
  621. package/docs/AGENT_GUIDE.md +183 -0
  622. package/docs/API_REFERENCE.md +761 -2
  623. package/docs/QUICK_START.md +495 -0
  624. package/docs/USAGE.md +1719 -714
  625. package/docs/api/camera-equivalent-focal-length.md +6 -7
  626. package/docs/api/camera-field-of-view.md +16 -8
  627. package/docs/api/camera-lens-projection.md +246 -0
  628. package/docs/api/camera-projected-object-size.md +6 -5
  629. package/docs/api/capture-capture-export-metadata.md +10 -10
  630. package/docs/api/capture-dng-import.md +134 -0
  631. package/docs/api/capture-environment-raw-producer.md +17 -11
  632. package/docs/api/capture-export-jpeg.md +16 -0
  633. package/docs/api/capture-focus-control.md +25 -47
  634. package/docs/api/capture-linear-encoding.md +21 -12
  635. package/docs/api/capture-lossless-jpeg.md +49 -0
  636. package/docs/api/capture-native-environment-optical-stage.md +75 -0
  637. package/docs/api/capture-native-environment-raw.md +161 -4
  638. package/docs/api/capture-native-raw-development.md +69 -4
  639. package/docs/api/capture-native-raw-dng.md +84 -0
  640. package/docs/api/capture-native-raw.md +23 -8
  641. package/docs/api/capture-packed-sensor-raw.md +156 -0
  642. package/docs/api/capture-photographic-export.md +69 -31
  643. package/docs/api/capture-raw-frame-reconstruction.md +8 -8
  644. package/docs/api/capture-raw-white-level.md +37 -0
  645. package/docs/api/capture-release-sequence.md +6 -7
  646. package/docs/api/capture-sensor-raw-frame.md +6 -6
  647. package/docs/api/capture-sensor-raw-producer.md +17 -11
  648. package/docs/api/capture-simulated-capture.md +15 -15
  649. package/docs/api/color-camera-color-matrix.md +103 -0
  650. package/docs/api/color-capture-color.md +22 -11
  651. package/docs/api/color-chromatic-adaptation.md +82 -0
  652. package/docs/api/color-color-difference.md +134 -0
  653. package/docs/api/color-color-matching-functions.md +259 -0
  654. package/docs/api/color-colorimetry-math.md +54 -0
  655. package/docs/api/color-gamut-mapping.md +72 -0
  656. package/docs/api/color-illuminants.md +280 -0
  657. package/docs/api/color-rgb-color-spaces.md +151 -0
  658. package/docs/api/color-sensor-color-development.md +27 -0
  659. package/docs/api/color-srgb-icc.md +2 -4
  660. package/docs/api/color-white-balance.md +95 -19
  661. package/docs/api/composition-image-formation-plan.md +124 -95
  662. package/docs/api/composition-plan-consumer.md +7 -7
  663. package/docs/api/core-calculation-result.md +18 -14
  664. package/docs/api/core-configuration-error.md +1 -1
  665. package/docs/api/core-image-formation.md +7 -7
  666. package/docs/api/core-scientific-assurance.md +12 -10
  667. package/docs/api/core-spectral-composition.md +14 -14
  668. package/docs/api/core-spectral.md +6 -6
  669. package/docs/api/core-validation.md +3 -3
  670. package/docs/api/core-version.md +7 -6
  671. package/docs/api/equipment-exposure-capabilities.md +11 -10
  672. package/docs/api/equipment-generic-tier-assets.md +7 -2
  673. package/docs/api/equipment-generic-tier-presets.md +6 -6
  674. package/docs/api/equipment-iso-capabilities.md +18 -18
  675. package/docs/api/equipment-metering-capabilities.md +6 -6
  676. package/docs/api/equipment-release-capabilities.md +4 -4
  677. package/docs/api/exports.json +2213 -8
  678. package/docs/api/exposure-exposure-duration-control.md +9 -9
  679. package/docs/api/exposure-exposure-mode-resolver.md +35 -31
  680. package/docs/api/exposure-exposure.md +10 -10
  681. package/docs/api/exposure-flash-ttl.md +182 -0
  682. package/docs/api/exposure-flash.md +183 -28
  683. package/docs/api/exposure-metering-scene-radiance.md +11 -10
  684. package/docs/api/exposure-metering-target.md +9 -8
  685. package/docs/api/exposure-metering-temporal.md +8 -8
  686. package/docs/api/exposure-metering.md +69 -9
  687. package/docs/api/exposure-program-line.md +6 -5
  688. package/docs/api/facade-chart-radiance-batch.md +96 -0
  689. package/docs/api/facade-chart-scenes.md +240 -0
  690. package/docs/api/facade-scene-radiance.md +122 -0
  691. package/docs/api/facade-simulate-capture.md +324 -0
  692. package/docs/api/gpu-image-kernel-accelerator.md +157 -0
  693. package/docs/api/gpu-image-kernel-execution.md +152 -0
  694. package/docs/api/motion-camera-rotation.md +43 -26
  695. package/docs/api/motion-capture-rotation-inverse-mapping.md +24 -23
  696. package/docs/api/motion-capture-rotation-temporal-quadrature.md +22 -22
  697. package/docs/api/motion-capture-rotation-trajectory.md +15 -15
  698. package/docs/api/motion-capture-translation-parallax-temporal-quadrature.md +15 -14
  699. package/docs/api/motion-extended-object-projection.md +10 -8
  700. package/docs/api/motion-projected-motion.md +8 -8
  701. package/docs/api/motion-temporal-exposure-sum.md +98 -0
  702. package/docs/api/motion-video-sequence.md +159 -0
  703. package/docs/api/optics-aperture.md +8 -8
  704. package/docs/api/optics-atmospheric-haze.md +104 -0
  705. package/docs/api/optics-brown-conrady-distortion.md +123 -0
  706. package/docs/api/optics-circle-of-confusion.md +5 -4
  707. package/docs/api/optics-complex-pupil-psf.md +57 -16
  708. package/docs/api/optics-depth-of-field.md +12 -6
  709. package/docs/api/optics-diffraction.md +8 -7
  710. package/docs/api/optics-focus-breathing.md +104 -16
  711. package/docs/api/optics-focus-state.md +9 -10
  712. package/docs/api/optics-front-of-lens-filter.md +72 -14
  713. package/docs/api/optics-illumination-vignetting.md +10 -10
  714. package/docs/api/optics-irradiance-convolution.md +95 -0
  715. package/docs/api/optics-lateral-chromatic-aberration.md +22 -21
  716. package/docs/api/optics-lens-psf-kernels.md +72 -0
  717. package/docs/api/optics-lens-psf-profile.md +48 -26
  718. package/docs/api/optics-longitudinal-chromatic-aberration.md +128 -0
  719. package/docs/api/optics-polygon-diffraction.md +78 -13
  720. package/docs/api/optics-profile-contract.md +4 -4
  721. package/docs/api/optics-psf-foundation.md +12 -12
  722. package/docs/api/optics-pupil-vignetting.md +132 -0
  723. package/docs/api/optics-radial-distortion.md +12 -12
  724. package/docs/api/optics-scene-to-sensor-irradiance.md +25 -14
  725. package/docs/api/optics-scene-to-sensor-quadrature.md +15 -12
  726. package/docs/api/optics-sensor-aperture-rays.md +3 -2
  727. package/docs/api/optics-sensor-environment-query.md +52 -9
  728. package/docs/api/optics-sensor-psf-quadrature.md +13 -10
  729. package/docs/api/optics-stray-light.md +12 -11
  730. package/docs/api/optics-thin-lens.md +4 -3
  731. package/docs/api/optics-zernike-wavefront.md +229 -0
  732. package/docs/api/output-capture-corrected-sdr.md +10 -7
  733. package/docs/api/output-capture-geometry.md +35 -36
  734. package/docs/api/output-capture-sdr.md +4 -4
  735. package/docs/api/output-crop.md +7 -4
  736. package/docs/api/output-geometric-transforms.md +65 -19
  737. package/docs/api/output-lens-corrections.md +17 -15
  738. package/docs/api/output-native-capture-sdr.md +26 -13
  739. package/docs/api/output-png-encoder.md +105 -0
  740. package/docs/api/output-print-contrast-reference.md +8 -8
  741. package/docs/api/output-print-detail.md +14 -14
  742. package/docs/api/output-print-jpeg.md +22 -5
  743. package/docs/api/output-print-plan.md +18 -18
  744. package/docs/api/output-print-region-statistics.md +14 -14
  745. package/docs/api/output-sdr-rendering.md +52 -10
  746. package/docs/api/output-subject-framing-crop.md +5 -6
  747. package/docs/api/processing-demosaic.md +120 -0
  748. package/docs/api/processing-denoise.md +148 -0
  749. package/docs/api/processing-focus-stacking.md +41 -0
  750. package/docs/api/processing-hdr.md +113 -0
  751. package/docs/api/processing-panorama.md +82 -0
  752. package/docs/api/processing-processing-task.md +107 -0
  753. package/docs/api/processing-tone-mapping.md +142 -0
  754. package/docs/api/schema-camera.md +6 -4
  755. package/docs/api/schema-illumination-spectral.md +10 -11
  756. package/docs/api/schema-illumination-temporal.md +13 -15
  757. package/docs/api/schema-illumination.md +4 -4
  758. package/docs/api/schema-scene-radiance-temporal.md +10 -11
  759. package/docs/api/schema-scene-radiance.md +18 -17
  760. package/docs/api/schema-scene.md +9 -9
  761. package/docs/api/schema-validation.md +1 -1
  762. package/docs/api/sensor-accumulated-charge.md +12 -20
  763. package/docs/api/sensor-architecture.md +15 -16
  764. package/docs/api/sensor-camera-saturation-capacity.md +9 -11
  765. package/docs/api/sensor-capture-color-sampling-binding.md +47 -51
  766. package/docs/api/sensor-capture-mode-timing.md +9 -9
  767. package/docs/api/sensor-capture-mode.md +29 -30
  768. package/docs/api/sensor-color-sampling.md +31 -33
  769. package/docs/api/sensor-constant-rate-temporal-integration.md +10 -11
  770. package/docs/api/sensor-dark-current.md +30 -14
  771. package/docs/api/sensor-environment-photo-signal.md +13 -6
  772. package/docs/api/sensor-eqe-electron-rate.md +9 -8
  773. package/docs/api/sensor-eqe-local-exposure.md +18 -17
  774. package/docs/api/sensor-eqe-temporal-exposure.md +12 -11
  775. package/docs/api/sensor-exposure-window.md +24 -24
  776. package/docs/api/sensor-fixed-pattern-noise.md +104 -0
  777. package/docs/api/sensor-iso-gain.md +63 -0
  778. package/docs/api/sensor-iso-signal-chain.md +13 -22
  779. package/docs/api/sensor-local-exposure-binding.md +12 -13
  780. package/docs/api/sensor-optical-stack.md +37 -40
  781. package/docs/api/sensor-photon-energy.md +10 -11
  782. package/docs/api/sensor-physical-charge-capacity.md +8 -13
  783. package/docs/api/sensor-pixel-pitch.md +1 -1
  784. package/docs/api/sensor-radiometry-readiness.md +9 -9
  785. package/docs/api/sensor-raw-readout.md +118 -52
  786. package/docs/api/sensor-raw-reconstruction.md +97 -20
  787. package/docs/api/sensor-readout-exposure-linkage.md +120 -24
  788. package/docs/api/sensor-readout-timing.md +33 -35
  789. package/docs/api/sensor-response-application-compatibility.md +9 -11
  790. package/docs/api/sensor-response-operating-range.md +14 -18
  791. package/docs/api/sensor-responsivity-photocurrent.md +9 -12
  792. package/docs/api/sensor-sampling-aperture.md +22 -25
  793. package/docs/api/sensor-scene-eqe-temporal-exposure.md +9 -8
  794. package/docs/api/sensor-sensor-geometry.md +23 -24
  795. package/docs/api/sensor-signal-noise.md +10 -10
  796. package/docs/api/sensor-spatial-sample-reduction.md +27 -30
  797. package/docs/api/sensor-spatial-sampling-quadrature.md +37 -39
  798. package/docs/api/sensor-spatio-spectral-reduction.md +27 -29
  799. package/docs/api/sensor-spectral-coverage.md +5 -5
  800. package/docs/api/sensor-spectral-quadrature.md +33 -35
  801. package/docs/api/sensor-spectral-response.md +28 -16
  802. package/docs/api/sensor-temporal-photo-signal.md +6 -6
  803. package/docs/api/simulation-poc-simulation.md +17 -16
  804. package/docs/api/stabilization-camera-shake.md +29 -10
  805. package/docs/api/stabilization-system.md +25 -21
  806. package/docs/examples/production-request.json +3821 -2157
  807. package/docs/examples/simulate-capture.mjs +14 -0
  808. package/llms.txt +35 -0
  809. package/package.json +32 -12
  810. package/AGENTS.md +0 -674
  811. package/CONTRIBUTING.md +0 -76
  812. package/DCO +0 -33
  813. package/dist/camera/equivalent-focal-length.d.ts.map +0 -1
  814. package/dist/camera/field-of-view.d.ts.map +0 -1
  815. package/dist/camera/projected-object-size.d.ts.map +0 -1
  816. package/dist/capture/capture-export-metadata.d.ts.map +0 -1
  817. package/dist/capture/environment-raw-producer.d.ts.map +0 -1
  818. package/dist/capture/export-jpeg.d.ts.map +0 -1
  819. package/dist/capture/export-tiff.d.ts.map +0 -1
  820. package/dist/capture/focus-control.d.ts.map +0 -1
  821. package/dist/capture/linear-encoding.d.ts.map +0 -1
  822. package/dist/capture/native-environment-raw.d.ts.map +0 -1
  823. package/dist/capture/native-raw-development.d.ts.map +0 -1
  824. package/dist/capture/native-raw.d.ts.map +0 -1
  825. package/dist/capture/photographic-export.d.ts.map +0 -1
  826. package/dist/capture/raw-frame-limits.d.ts.map +0 -1
  827. package/dist/capture/raw-frame-reconstruction.d.ts.map +0 -1
  828. package/dist/capture/release-sequence.d.ts.map +0 -1
  829. package/dist/capture/sensor-raw-frame.d.ts.map +0 -1
  830. package/dist/capture/sensor-raw-producer.d.ts.map +0 -1
  831. package/dist/capture/simulated-capture.d.ts.map +0 -1
  832. package/dist/color/capture-color.d.ts.map +0 -1
  833. package/dist/color/sensor-color-development.d.ts.map +0 -1
  834. package/dist/color/srgb-icc.d.ts.map +0 -1
  835. package/dist/color/srgb-transfer.d.ts.map +0 -1
  836. package/dist/color/white-balance.d.ts.map +0 -1
  837. package/dist/composition/image-formation-plan.d.ts.map +0 -1
  838. package/dist/composition/plan-consumer.d.ts.map +0 -1
  839. package/dist/core/calculation-result.d.ts.map +0 -1
  840. package/dist/core/canonical-json.d.ts.map +0 -1
  841. package/dist/core/configuration-error.d.ts.map +0 -1
  842. package/dist/core/evidence-provenance.d.ts.map +0 -1
  843. package/dist/core/image-formation.d.ts.map +0 -1
  844. package/dist/core/owned-data.d.ts.map +0 -1
  845. package/dist/core/record-validation.d.ts.map +0 -1
  846. package/dist/core/scientific-assurance.d.ts.map +0 -1
  847. package/dist/core/spectral-composition.d.ts.map +0 -1
  848. package/dist/core/spectral.d.ts.map +0 -1
  849. package/dist/core/validation.d.ts.map +0 -1
  850. package/dist/core/version.d.ts.map +0 -1
  851. package/dist/equipment/exposure-capabilities.d.ts.map +0 -1
  852. package/dist/equipment/generic-tier-assets.d.ts.map +0 -1
  853. package/dist/equipment/generic-tier-presets.d.ts.map +0 -1
  854. package/dist/equipment/iso-capabilities.d.ts.map +0 -1
  855. package/dist/equipment/metering-capabilities.d.ts.map +0 -1
  856. package/dist/equipment/release-capabilities.d.ts.map +0 -1
  857. package/dist/exposure/exposure-duration-control.d.ts.map +0 -1
  858. package/dist/exposure/exposure-mode-resolver.d.ts.map +0 -1
  859. package/dist/exposure/exposure.d.ts.map +0 -1
  860. package/dist/exposure/flash.d.ts.map +0 -1
  861. package/dist/exposure/metering-scene-radiance.d.ts.map +0 -1
  862. package/dist/exposure/metering-target.d.ts.map +0 -1
  863. package/dist/exposure/metering-temporal.d.ts.map +0 -1
  864. package/dist/exposure/metering.d.ts.map +0 -1
  865. package/dist/exposure/program-line.d.ts.map +0 -1
  866. package/dist/index.d.ts.map +0 -1
  867. package/dist/motion/camera-rotation.d.ts.map +0 -1
  868. package/dist/motion/capture-rotation-inverse-mapping.d.ts.map +0 -1
  869. package/dist/motion/capture-rotation-temporal-quadrature.d.ts.map +0 -1
  870. package/dist/motion/capture-rotation-trajectory.d.ts.map +0 -1
  871. package/dist/motion/capture-translation-parallax-temporal-quadrature.d.ts.map +0 -1
  872. package/dist/motion/extended-object-projection.d.ts.map +0 -1
  873. package/dist/motion/projected-motion.d.ts.map +0 -1
  874. package/dist/optics/aperture.d.ts.map +0 -1
  875. package/dist/optics/circle-of-confusion.d.ts.map +0 -1
  876. package/dist/optics/complex-pupil-psf.d.ts.map +0 -1
  877. package/dist/optics/depth-of-field.d.ts.map +0 -1
  878. package/dist/optics/diffraction.d.ts.map +0 -1
  879. package/dist/optics/focus-breathing.d.ts.map +0 -1
  880. package/dist/optics/focus-state.d.ts.map +0 -1
  881. package/dist/optics/front-of-lens-filter.d.ts.map +0 -1
  882. package/dist/optics/illumination-vignetting.d.ts.map +0 -1
  883. package/dist/optics/lateral-chromatic-aberration.d.ts.map +0 -1
  884. package/dist/optics/lens-psf-profile.d.ts.map +0 -1
  885. package/dist/optics/polygon-diffraction.d.ts.map +0 -1
  886. package/dist/optics/profile-contract.d.ts.map +0 -1
  887. package/dist/optics/psf-foundation.d.ts.map +0 -1
  888. package/dist/optics/radial-distortion.d.ts.map +0 -1
  889. package/dist/optics/scene-to-sensor-irradiance.d.ts.map +0 -1
  890. package/dist/optics/scene-to-sensor-quadrature.d.ts.map +0 -1
  891. package/dist/optics/sensor-aperture-rays.d.ts.map +0 -1
  892. package/dist/optics/sensor-environment-query.d.ts.map +0 -1
  893. package/dist/optics/sensor-psf-quadrature.d.ts.map +0 -1
  894. package/dist/optics/sensor-psf-support.d.ts.map +0 -1
  895. package/dist/optics/stray-light.d.ts.map +0 -1
  896. package/dist/optics/thin-lens.d.ts.map +0 -1
  897. package/dist/output/capture-corrected-sdr.d.ts.map +0 -1
  898. package/dist/output/capture-geometry.d.ts.map +0 -1
  899. package/dist/output/capture-sdr.d.ts.map +0 -1
  900. package/dist/output/crop.d.ts.map +0 -1
  901. package/dist/output/geometric-transforms.d.ts.map +0 -1
  902. package/dist/output/lens-corrections.d.ts.map +0 -1
  903. package/dist/output/native-capture-sdr.d.ts.map +0 -1
  904. package/dist/output/print-contrast-reference.d.ts.map +0 -1
  905. package/dist/output/print-detail.d.ts.map +0 -1
  906. package/dist/output/print-jpeg.d.ts.map +0 -1
  907. package/dist/output/print-plan.d.ts.map +0 -1
  908. package/dist/output/print-region-statistics.d.ts.map +0 -1
  909. package/dist/output/sdr-rendering.d.ts.map +0 -1
  910. package/dist/output/subject-framing-crop.d.ts.map +0 -1
  911. package/dist/schema/camera.d.ts.map +0 -1
  912. package/dist/schema/camera.js +0 -3
  913. package/dist/schema/camera.js.map +0 -1
  914. package/dist/schema/illumination-spectral.d.ts.map +0 -1
  915. package/dist/schema/illumination-temporal.d.ts.map +0 -1
  916. package/dist/schema/illumination.d.ts.map +0 -1
  917. package/dist/schema/scene-radiance-temporal.d.ts.map +0 -1
  918. package/dist/schema/scene-radiance.d.ts.map +0 -1
  919. package/dist/schema/scene.d.ts.map +0 -1
  920. package/dist/schema/scene.js +0 -3
  921. package/dist/schema/scene.js.map +0 -1
  922. package/dist/schema/validation.d.ts.map +0 -1
  923. package/dist/sensor/accumulated-charge.d.ts.map +0 -1
  924. package/dist/sensor/architecture.d.ts.map +0 -1
  925. package/dist/sensor/camera-saturation-capacity.d.ts.map +0 -1
  926. package/dist/sensor/capture-color-sampling-binding.d.ts.map +0 -1
  927. package/dist/sensor/capture-mode-timing.d.ts.map +0 -1
  928. package/dist/sensor/capture-mode.d.ts.map +0 -1
  929. package/dist/sensor/color-sampling.d.ts.map +0 -1
  930. package/dist/sensor/constant-rate-temporal-integration.d.ts.map +0 -1
  931. package/dist/sensor/dark-current.d.ts.map +0 -1
  932. package/dist/sensor/environment-photo-signal.d.ts.map +0 -1
  933. package/dist/sensor/eqe-electron-rate.d.ts.map +0 -1
  934. package/dist/sensor/eqe-local-exposure.d.ts.map +0 -1
  935. package/dist/sensor/eqe-temporal-exposure.d.ts.map +0 -1
  936. package/dist/sensor/exposure-window.d.ts.map +0 -1
  937. package/dist/sensor/iso-signal-chain.d.ts.map +0 -1
  938. package/dist/sensor/local-exposure-binding.d.ts.map +0 -1
  939. package/dist/sensor/optical-stack.d.ts.map +0 -1
  940. package/dist/sensor/photon-energy.d.ts.map +0 -1
  941. package/dist/sensor/physical-charge-capacity.d.ts.map +0 -1
  942. package/dist/sensor/pixel-pitch.d.ts.map +0 -1
  943. package/dist/sensor/radiometry-readiness.d.ts.map +0 -1
  944. package/dist/sensor/raw-readout.d.ts.map +0 -1
  945. package/dist/sensor/raw-reconstruction.d.ts.map +0 -1
  946. package/dist/sensor/readout-exposure-linkage.d.ts.map +0 -1
  947. package/dist/sensor/readout-timing.d.ts.map +0 -1
  948. package/dist/sensor/response-application-compatibility.d.ts.map +0 -1
  949. package/dist/sensor/response-operating-range.d.ts.map +0 -1
  950. package/dist/sensor/responsivity-photocurrent.d.ts.map +0 -1
  951. package/dist/sensor/sampling-aperture.d.ts.map +0 -1
  952. package/dist/sensor/scene-eqe-temporal-exposure.d.ts.map +0 -1
  953. package/dist/sensor/sensor-geometry.d.ts.map +0 -1
  954. package/dist/sensor/signal-noise.d.ts.map +0 -1
  955. package/dist/sensor/spatial-sample-reduction.d.ts.map +0 -1
  956. package/dist/sensor/spatial-sampling-quadrature.d.ts.map +0 -1
  957. package/dist/sensor/spatio-spectral-reduction.d.ts.map +0 -1
  958. package/dist/sensor/spectral-coverage.d.ts.map +0 -1
  959. package/dist/sensor/spectral-quadrature.d.ts.map +0 -1
  960. package/dist/sensor/spectral-response.d.ts.map +0 -1
  961. package/dist/sensor/temporal-eqe-sum.d.ts.map +0 -1
  962. package/dist/sensor/temporal-photo-signal.d.ts.map +0 -1
  963. package/dist/sensor/temporal-sample-binding.d.ts.map +0 -1
  964. package/dist/simulation/poc-simulation.d.ts.map +0 -1
  965. package/dist/stabilization/camera-shake.d.ts.map +0 -1
  966. package/dist/stabilization/system.d.ts.map +0 -1
  967. package/docs/API_STYLE.md +0 -235
  968. package/docs/ARCHITECTURE.md +0 -356
  969. package/docs/AUTOMATION_COORDINATION.md +0 -190
  970. package/docs/CAPTURE_COLOR.md +0 -25
  971. package/docs/CAPTURE_CORRECTED_SDR.md +0 -25
  972. package/docs/CAPTURE_EXPORT_METADATA.md +0 -27
  973. package/docs/CAPTURE_SDR.md +0 -22
  974. package/docs/DEVELOPERS.md +0 -68
  975. package/docs/DIGITAL_OPTICS_FOUNDATION.md +0 -69
  976. package/docs/ENVIRONMENT_RAW_CAPTURE.md +0 -208
  977. package/docs/EXPORT_ACCEPTANCE.md +0 -133
  978. package/docs/GENERIC_TIER_PRESETS.md +0 -269
  979. package/docs/GEOMETRIC_PREPARATION_REUSE.md +0 -141
  980. package/docs/IMAGE_FORMATION.md +0 -247
  981. package/docs/LINEAR_CAPTURE_ENCODING.md +0 -25
  982. package/docs/MOTION_AND_SIGNAL.md +0 -250
  983. package/docs/NATIVE_CAPTURE_SDR.md +0 -70
  984. package/docs/NATIVE_CAPTURE_SDR_REVIEW.md +0 -37
  985. package/docs/NATIVE_CAPTURE_SDR_VALIDATION.md +0 -34
  986. package/docs/NATIVE_RAW_AND_PRINT.md +0 -47
  987. package/docs/NUMERICAL_CORRECTNESS.md +0 -191
  988. package/docs/PERFORMANCE_BASELINE.md +0 -56
  989. package/docs/PHOTOGRAPHIC_EXPORT.md +0 -206
  990. package/docs/PHYSICS_FOUNDATION.md +0 -426
  991. package/docs/POC_API.md +0 -278
  992. package/docs/POC_PROJECTION_PLATFORM_REFERENCE.md +0 -12
  993. package/docs/POC_PROJECTION_REUSE.md +0 -124
  994. package/docs/PRINT_195_196_REVIEW.md +0 -93
  995. package/docs/PRINT_196_ENGINE_ACCEPTANCE.md +0 -45
  996. package/docs/PRINT_CONTRAST_REFERENCE.md +0 -43
  997. package/docs/PRINT_DETAIL_ASSESSMENT.md +0 -81
  998. package/docs/PRINT_DETAIL_JPEG_EVIDENCE.md +0 -36
  999. package/docs/PRINT_DETAIL_SDR_EVIDENCE.md +0 -29
  1000. package/docs/PRINT_DETAIL_VALIDATION.md +0 -36
  1001. package/docs/PRINT_PLANNING.md +0 -75
  1002. package/docs/PRINT_REGION_STATISTICS.md +0 -38
  1003. package/docs/PROCESSED_OUTPUT.md +0 -157
  1004. package/docs/PRODUCTION_COMPOSITION.md +0 -373
  1005. package/docs/PRODUCTION_ENVIRONMENT_CAPTURE.md +0 -131
  1006. package/docs/PROVENANCE.md +0 -115
  1007. package/docs/PSF_FOUNDATION.md +0 -165
  1008. package/docs/RAW_FRAME_ENVELOPE.md +0 -56
  1009. package/docs/RAW_FRAME_RECONSTRUCTION.md +0 -30
  1010. package/docs/RELEASE_1_0.md +0 -66
  1011. package/docs/RELEASE_1_0_1.md +0 -61
  1012. package/docs/RELEASE_1_1_0.md +0 -25
  1013. package/docs/RELEASE_1_2_0.md +0 -51
  1014. package/docs/RELEASE_1_3_0.md +0 -15
  1015. package/docs/RELEASE_1_4_0.md +0 -23
  1016. package/docs/RELEASE_AUDIT.md +0 -39
  1017. package/docs/SCENE_RADIANCE_AND_ILLUMINATION.md +0 -298
  1018. package/docs/SCENE_SENSOR_QUADRATURE.md +0 -98
  1019. package/docs/SCENE_SENSOR_TEMPORAL_EXPOSURE.md +0 -86
  1020. package/docs/SCIENTIFIC_ASSURANCE.md +0 -280
  1021. package/docs/SCIENTIFIC_CONFORMANCE.md +0 -83
  1022. package/docs/SDR_RENDERING.md +0 -33
  1023. package/docs/SENSOR_APERTURE_RAYS.md +0 -23
  1024. package/docs/SENSOR_ENVIRONMENT_QUERY.md +0 -86
  1025. package/docs/SENSOR_EQE_LOCAL_EXPOSURE.md +0 -104
  1026. package/docs/SENSOR_EQE_TEMPORAL_EXPOSURE.md +0 -74
  1027. package/docs/SENSOR_PSF_QUADRATURE.md +0 -90
  1028. package/docs/SENSOR_RAW_FRAME.md +0 -20
  1029. package/docs/SENSOR_RAW_PRODUCER.md +0 -77
  1030. package/docs/SIGNAL_CONFORMANCE.md +0 -23
  1031. package/docs/SIMULATED_CAPTURE.md +0 -65
  1032. package/docs/STABILIZATION.md +0 -234
  1033. package/docs/TEMPORAL_PHOTO_RAW.md +0 -83
  1034. package/docs/TIER_ACCEPTANCE.md +0 -129
  1035. package/docs/TIER_PRESET_ACCEPTANCE.md +0 -59
  1036. package/docs/V1_COMPOSITION_MAP.md +0 -123
  1037. package/docs/V1_HELPER_REUSE_REVIEW.md +0 -60
  1038. package/docs/V1_PERFORMANCE_DISPOSITION.md +0 -88
  1039. package/docs/benchmarks/2026-10-01-main-baseline.json +0 -694
  1040. package/docs/benchmarks/2026-10-02-geometric-preparation-reuse.json +0 -2190
  1041. package/docs/benchmarks/2026-10-02-poc-projection-reuse.json +0 -2423
  1042. package/docs/benchmarks/2026-10-02-v1-environment-gc-profile.json +0 -210
  1043. package/docs/benchmarks/2026-10-02-v1-environment-ordinary.json +0 -187
  1044. package/docs/benchmarks/2026-10-02-v1-geometry-gc-profile.json +0 -756
  1045. package/docs/benchmarks/2026-10-02-v1-geometry-ordinary-1.json +0 -711
  1046. package/docs/benchmarks/2026-10-02-v1-geometry-ordinary-2.json +0 -711
  1047. package/docs/benchmarks/2026-10-02-v1-poc-gc-profile.json +0 -885
  1048. package/docs/benchmarks/2026-10-02-v1-poc-ordinary-1.json +0 -868
  1049. package/docs/benchmarks/2026-10-02-v1-poc-ordinary-2.json +0 -868
  1050. package/docs/licenses/castleCSF-MIT.txt +0 -21
  1051. package/docs/validation/documentation-fragments.json +0 -212
  1052. package/docs/validation/native-capture-sdr-darwin-arm64-node26-review.jsonl +0 -4
  1053. package/docs/validation/native-capture-sdr-darwin-arm64.jsonl +0 -3
  1054. package/docs/validation/native-raw-print-2026-10-04/fractional-asymmetric-crop.jpg +0 -0
  1055. package/docs/validation/native-raw-print-2026-10-04/gray-ramp.jpg +0 -0
  1056. package/docs/validation/native-raw-print-2026-10-04/linear-area-checker.jpg +0 -0
  1057. package/docs/validation/native-raw-print-2026-10-04/manifest.json +0 -218
  1058. package/docs/validation/native-raw-print-2026-10-04/megapixel-native.jpg +0 -0
  1059. package/docs/validation/native-raw-print-2026-10-04/native-color.jpg +0 -0
  1060. package/docs/validation/native-raw-print-2026-10-04/photivra-native-full-megapixel-validation.json +0 -9
  1061. package/docs/validation/native-raw-print-2026-10-04/photivra-native-full-megapixel.json +0 -29
  1062. package/docs/validation/native-raw-print-2026-10-04/photivra-native-full-megapixel.json.codes.u16le.gz +0 -0
  1063. package/docs/validation/native-raw-print-2026-10-04/photivra-native-full-megapixel.json.jpg +0 -0
  1064. package/docs/validation/native-raw-print-2026-10-04/photivra-native-full-megapixel.json.rgb.gz +0 -0
  1065. package/docs/validation/native-raw-print-2026-10-04/srgb.icc +0 -0
  1066. package/docs/validation/native-raw-print-2026-10-04/validation.json +0 -41
  1067. package/docs/validation/print-196-candidate-capabilities.json +0 -28
  1068. package/docs/validation/print-196-candidate-evidence.json +0 -356
  1069. package/docs/validation/print-196-engine-acceptance.json +0 -81
  1070. package/docs/validation/print-detail-capabilities.json +0 -103
  1071. package/docs/validation/print-detail-jpeg-evidence.json +0 -116
  1072. package/docs/validation/print-detail-sdr-evidence.json +0 -81
  1073. package/docs/validation/release-audit-inventory.json +0 -1306
  1074. package/docs/validation/tier-acceptance-report-v1.json +0 -2538
@@ -0,0 +1 @@
1
+ {"version":3,"file":"longitudinal-chromatic-aberration.js","sourceRoot":"","sources":["../../src/optics/longitudinal-chromatic-aberration.ts"],"names":[],"mappings":"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","sourcesContent":["// SPDX-License-Identifier: Apache-2.0\n\n/**\n * Longitudinal (axial) chromatic aberration: wavelength-dependent focal length and the resulting\n * per-wavelength image-plane defocus for a sensor focused at a reference wavelength.\n *\n * Two dispersion inputs:\n * - thin-singlet-abbe: an ideal thin singlet whose index follows a two-term Cauchy dispersion\n * n(lambda) = A + B / lambda^2 fitted to n_d and the Abbe number V_d = (n_d - 1) / (n_F - n_C)\n * (Cauchy 1836; Oh 2023, arXiv:2309.09375, sec. 2.3.1(b), free; Abbe number: Greivenkamp,\n * OPTI-502 course notes, University of Arizona, sec. 17, free. Also see: Born & Wolf, Principles\n * of Optics, sec. 2.3; Hecht, Optics, 5th ed., sec. 3.5 and 6.3). Lensmaker scaling gives\n * f(lambda) = f_ref (n_ref - 1) / (n(lambda) - 1), so f_C - f_F ~ f_d / V_d (Greivenkamp,\n * OPTI-502 course notes, sec. 20, free. Also see: Hecht sec. 6.3.2; Kingslake & Johnson, Lens\n * Design Fundamentals, 2nd ed., ch. 5). The Fraunhofer d, F and C wavelengths (587.5618, 486.1327, 656.2725 nm) are standard\n * spectral-line constants (SCHOTT Technical Information TIE-29, 2023, free; also specified in\n * ISO 7944). A real multi-element lens is not a singlet, so this is an educational\n * approximation.\n * - declared-focal-shift: a caller-supplied table of focal-length shift versus wavelength\n * (for example a corrected lens's secondary spectrum), interpolated linearly without extrapolation.\n *\n * How defocus is computed:\n * - The sensor sits at the Gaussian thin-lens image distance for focusDistanceM at the reference\n * wavelength.\n * - At each wavelength, the image distance of subjectDistanceM uses f(lambda).\n * - The signed image-plane defocus dz is the sensor distance minus that image distance.\n * - The geometric blur diameter is D |dz| / v(lambda), where D = f_ref / N is the entrance-pupil\n * diameter. This is the same thin-lens form as calculateDefocusCircle().\n * The defocus also feeds calculateDefocusWavefront(), so a complex-pupil PSF (point-spread function)\n * can be evaluated per wavelength.\n * @see docs/PHYSICS_FOUNDATION.md for the equations, units, coordinate conventions, known blockers\n * and support limits.\n */\n\nimport {\n approximationResult,\n type CalculationResult\n} from \"../core/calculation-result.js\";\nimport {\n InvalidScientificInputError,\n requirePositiveFinite\n} from \"../core/validation.js\";\nimport { calculateDefocusWavefront } from \"./zernike-wavefront.js\";\nimport { requireInputKeys } from \"../core/record-validation.js\";\nimport { InvalidConfigurationError } from \"../core/configuration-error.js\";\n\n/** Fraunhofer spectral-line wavelengths in nm (SCHOTT TIE-29 table; also ISO 7944 reference wavelengths). */\nexport const FRAUNHOFER_D_LINE_NM = 587.5618;\nexport const FRAUNHOFER_F_LINE_NM = 486.1327;\nexport const FRAUNHOFER_C_LINE_NM = 656.2725;\n\nconst CAUCHY_MINIMUM_WAVELENGTH_NM = 360;\nconst CAUCHY_MAXIMUM_WAVELENGTH_NM = 830;\n\nexport type LongitudinalChromaticDispersion =\n | {\n kind: \"thin-singlet-abbe\";\n /** Refractive index at the d line. */\n refractiveIndexD: number;\n /** Abbe number V_d = (n_d - 1) / (n_F - n_C). */\n abbeNumberD: number;\n }\n | {\n kind: \"declared-focal-shift\";\n /** Strictly increasing wavelengths; shift is f(lambda) - f_nominal in micrometres. */\n samples: readonly {\n wavelengthNm: number;\n focalLengthShiftMicrometers: number;\n }[];\n };\n\nexport interface CalculateLongitudinalChromaticFocusInput {\n /** Focal length at the reference wavelength, in mm. */\n focalLengthMm: number;\n /** Wavelength at which the sensor is focused, in nm. */\n referenceWavelengthNm: number;\n /** Wavelength to evaluate, in nm (same wavelength basis as the dispersion data). */\n wavelengthNm: number;\n /** Nominal f-number at the reference wavelength (entrance-pupil diameter = f / N). */\n apertureFNumber: number;\n /** Focus (object) distance at the reference wavelength, metres from the principal plane. */\n focusDistanceM: number;\n /** Subject distance in metres; defaults to focusDistanceM. */\n subjectDistanceM?: number;\n dispersion: LongitudinalChromaticDispersion;\n}\n\nexport interface LongitudinalChromaticFocus {\n wavelengthNm: number;\n referenceWavelengthNm: number;\n focalLengthAtWavelengthMm: number;\n /** f(lambda) - f(reference), micrometres. */\n focalShiftMicrometers: number;\n /** Sensor plane distance (reference-wavelength image of the focus plane), mm. */\n sensorImageDistanceMm: number;\n /** Image distance of the subject at this wavelength, mm. */\n imageDistanceAtWavelengthMm: number;\n /** Sensor minus image distance, micrometres. */\n signedDefocusImagePlaneMicrometers: number;\n /** Geometric thin-lens blur-circle diameter at the sensor, mm. */\n geometricBlurDiameterMm: number;\n /** Image-side working f-number v(lambda) / D. */\n workingFNumberAtWavelength: number;\n /** Defocus wave aberration W020 for the complex-pupil PSF, micrometres. */\n w020Micrometers: number;\n /** Equivalent Noll Z4 coefficient, micrometres. */\n zernikeZ4Micrometers: number;\n}\n\nfunction requireFinite(name: string, value: unknown): number {\n if (typeof value !== \"number\" || !Number.isFinite(value)) {\n throw new InvalidScientificInputError(`${name} must be finite.`);\n }\n return value;\n}\n\nfunction cauchyIndex(\n refractiveIndexD: number,\n abbeNumberD: number,\n wavelengthNm: number\n): number {\n const inverseSquare = (nm: number): number => 1 / (nm / 1000) ** 2;\n const b =\n (refractiveIndexD - 1) /\n abbeNumberD /\n (inverseSquare(FRAUNHOFER_F_LINE_NM) - inverseSquare(FRAUNHOFER_C_LINE_NM));\n return (\n refractiveIndexD +\n b * (inverseSquare(wavelengthNm) - inverseSquare(FRAUNHOFER_D_LINE_NM))\n );\n}\n\n/**\n * Two-term Cauchy refractive index fitted to n_d and V_d. Valid as an approximation over\n * 360-830 nm only.\n */\nexport function calculateCauchyRefractiveIndex(input: {\n refractiveIndexD: number;\n abbeNumberD: number;\n wavelengthNm: number;\n}): CalculationResult<{ refractiveIndex: number }> {\n requireInputKeys(input, \"calculateCauchyRefractiveIndex\", [\"refractiveIndexD\", \"abbeNumberD\", \"wavelengthNm\"]);\n validateAbbe(input.refractiveIndexD, input.abbeNumberD);\n validateCauchyWavelength(\"wavelengthNm\", input.wavelengthNm);\n return approximationResult(\n {\n refractiveIndex: cauchyIndex(\n input.refractiveIndexD,\n input.abbeNumberD,\n input.wavelengthNm\n )\n },\n \"two-term-cauchy-abbe-dispersion\",\n \"1.0.0\",\n [\n \"n(lambda) = A + B / lambda^2 fitted exactly to n_d and V_d = (n_d - 1) / (n_F - n_C)\",\n \"Two-term Cauchy dispersion is an approximation for normal dispersion in the visible (360-830 nm)\"\n ]\n );\n}\n\nfunction validateAbbe(refractiveIndexD: unknown, abbeNumberD: unknown): void {\n const n = requireFinite(\"dispersion.refractiveIndexD\", refractiveIndexD);\n const v = requireFinite(\"dispersion.abbeNumberD\", abbeNumberD);\n if (n <= 1 || n > 4) {\n throw new InvalidScientificInputError(\n \"dispersion.refractiveIndexD must lie in (1, 4].\"\n );\n }\n if (v < 5 || v > 200) {\n throw new InvalidScientificInputError(\n \"dispersion.abbeNumberD must lie in [5, 200].\"\n );\n }\n}\n\nfunction validateCauchyWavelength(name: string, value: unknown): void {\n const wavelength = requireFinite(name, value);\n if (\n wavelength < CAUCHY_MINIMUM_WAVELENGTH_NM ||\n wavelength > CAUCHY_MAXIMUM_WAVELENGTH_NM\n ) {\n throw new InvalidScientificInputError(\n `${name} must lie in ${CAUCHY_MINIMUM_WAVELENGTH_NM}-${CAUCHY_MAXIMUM_WAVELENGTH_NM} nm for the Cauchy dispersion approximation.`\n );\n }\n}\n\nfunction interpolateShift(\n samples: readonly { wavelengthNm: number; focalLengthShiftMicrometers: number }[],\n wavelengthNm: number,\n name: string\n): number {\n const first = samples[0]!;\n const last = samples[samples.length - 1]!;\n if (wavelengthNm < first.wavelengthNm || wavelengthNm > last.wavelengthNm) {\n throw new InvalidScientificInputError(\n `${name} lies outside the declared focal-shift wavelength range; extrapolation is not performed.`\n );\n }\n for (let index = 1; index < samples.length; index += 1) {\n const right = samples[index]!;\n if (wavelengthNm <= right.wavelengthNm) {\n const left = samples[index - 1]!;\n const t = (wavelengthNm - left.wavelengthNm) / (right.wavelengthNm - left.wavelengthNm);\n return (\n left.focalLengthShiftMicrometers +\n t * (right.focalLengthShiftMicrometers - left.focalLengthShiftMicrometers)\n );\n }\n }\n return first.focalLengthShiftMicrometers;\n}\n\nfunction parseSamples(\n value: unknown\n): readonly { wavelengthNm: number; focalLengthShiftMicrometers: number }[] {\n if (!Array.isArray(value) || value.length < 2 || value.length > 1024) {\n throw new InvalidScientificInputError(\n \"dispersion.samples must contain 2 through 1024 entries.\"\n );\n }\n let previous = 0;\n return value.map((entry: unknown, index) => {\n if (typeof entry !== \"object\" || entry === null) {\n throw new InvalidConfigurationError(`dispersion.samples[${index}] must be an object.`);\n }\n const record = entry as Record<string, unknown>;\n const wavelengthNm = requireFinite(`dispersion.samples[${index}].wavelengthNm`, record.wavelengthNm);\n if (wavelengthNm <= previous) {\n throw new InvalidScientificInputError(\n \"dispersion.samples wavelengths must be positive and strictly increasing.\"\n );\n }\n previous = wavelengthNm;\n return {\n wavelengthNm,\n focalLengthShiftMicrometers: requireFinite(\n `dispersion.samples[${index}].focalLengthShiftMicrometers`,\n record.focalLengthShiftMicrometers\n )\n };\n });\n}\n\nfunction imageDistanceMm(focalLengthMm: number, objectDistanceM: number): number {\n const objectMm = objectDistanceM * 1000;\n if (objectMm <= focalLengthMm) {\n throw new InvalidScientificInputError(\n \"Object distances must lie beyond the wavelength-dependent focal length.\"\n );\n }\n return (focalLengthMm * objectMm) / (objectMm - focalLengthMm);\n}\n\n/**\n * Wavelength-dependent focus for one wavelength: focal length, image distance, signed defocus at\n * a sensor focused at the reference wavelength, geometric blur and the defocus wavefront.\n */\nexport function calculateLongitudinalChromaticFocus(\n input: CalculateLongitudinalChromaticFocusInput\n): CalculationResult<LongitudinalChromaticFocus> {\n requireInputKeys(input, \"calculateLongitudinalChromaticFocus\", [\"focalLengthMm\", \"referenceWavelengthNm\", \"wavelengthNm\", \"apertureFNumber\", \"focusDistanceM\", \"subjectDistanceM\", \"dispersion\"]);\n requirePositiveFinite(\"focalLengthMm\", input.focalLengthMm);\n requirePositiveFinite(\"referenceWavelengthNm\", input.referenceWavelengthNm);\n requirePositiveFinite(\"wavelengthNm\", input.wavelengthNm);\n requirePositiveFinite(\"apertureFNumber\", input.apertureFNumber);\n requirePositiveFinite(\"focusDistanceM\", input.focusDistanceM);\n const subjectDistanceM = input.subjectDistanceM ?? input.focusDistanceM;\n requirePositiveFinite(\"subjectDistanceM\", subjectDistanceM);\n const dispersion = input.dispersion;\n if (typeof dispersion !== \"object\" || dispersion === null) {\n throw new InvalidConfigurationError(\"dispersion must be an object.\");\n }\n\n let focalLengthAtWavelengthMm: number;\n let model: string;\n let dispersionAssumption: string;\n if (dispersion.kind === \"thin-singlet-abbe\") {\n validateAbbe(dispersion.refractiveIndexD, dispersion.abbeNumberD);\n validateCauchyWavelength(\"referenceWavelengthNm\", input.referenceWavelengthNm);\n validateCauchyWavelength(\"wavelengthNm\", input.wavelengthNm);\n const nRef = cauchyIndex(dispersion.refractiveIndexD, dispersion.abbeNumberD, input.referenceWavelengthNm);\n const nLambda = cauchyIndex(dispersion.refractiveIndexD, dispersion.abbeNumberD, input.wavelengthNm);\n focalLengthAtWavelengthMm = (input.focalLengthMm * (nRef - 1)) / (nLambda - 1);\n model = \"thin-singlet-abbe-longitudinal-chromatic-focus\";\n dispersionAssumption =\n \"Ideal thin singlet with two-term Cauchy dispersion fitted to n_d and V_d; f(lambda) = f_ref (n_ref - 1) / (n(lambda) - 1)\";\n } else if (dispersion.kind === \"declared-focal-shift\") {\n const samples = parseSamples(dispersion.samples);\n const shiftRef = interpolateShift(samples, input.referenceWavelengthNm, \"referenceWavelengthNm\");\n const shift = interpolateShift(samples, input.wavelengthNm, \"wavelengthNm\");\n focalLengthAtWavelengthMm = input.focalLengthMm + (shift - shiftRef) / 1000;\n model = \"declared-focal-shift-longitudinal-chromatic-focus\";\n dispersionAssumption =\n \"Caller-declared focal-length shift table, linearly interpolated and re-referenced to the reference wavelength; no extrapolation\";\n } else {\n throw new InvalidConfigurationError(\"dispersion.kind is invalid.\");\n }\n if (!(focalLengthAtWavelengthMm > 0) || !Number.isFinite(focalLengthAtWavelengthMm)) {\n throw new InvalidScientificInputError(\n \"Wavelength-dependent focal length must remain finite and positive.\"\n );\n }\n\n const sensorImageDistanceMm = imageDistanceMm(input.focalLengthMm, input.focusDistanceM);\n const imageDistanceAtWavelengthMm = imageDistanceMm(focalLengthAtWavelengthMm, subjectDistanceM);\n const pupilDiameterMm = input.focalLengthMm / input.apertureFNumber;\n const defocusMm = sensorImageDistanceMm - imageDistanceAtWavelengthMm;\n const workingFNumberAtWavelength = imageDistanceAtWavelengthMm / pupilDiameterMm;\n const wavefront = calculateDefocusWavefront({\n signedDefocusImagePlaneMicrometers: defocusMm * 1000,\n workingFNumber: workingFNumberAtWavelength\n }).value;\n\n return approximationResult(\n {\n wavelengthNm: input.wavelengthNm,\n referenceWavelengthNm: input.referenceWavelengthNm,\n focalLengthAtWavelengthMm,\n focalShiftMicrometers: (focalLengthAtWavelengthMm - input.focalLengthMm) * 1000,\n sensorImageDistanceMm,\n imageDistanceAtWavelengthMm,\n signedDefocusImagePlaneMicrometers: defocusMm * 1000,\n geometricBlurDiameterMm:\n (pupilDiameterMm * Math.abs(defocusMm)) / imageDistanceAtWavelengthMm,\n workingFNumberAtWavelength,\n w020Micrometers: wavefront.w020Micrometers,\n zernikeZ4Micrometers: wavefront.zernikeZ4Micrometers\n },\n model,\n \"1.0.0\",\n [\n dispersionAssumption,\n \"Gaussian thin-lens imaging; the sensor is focused on focusDistanceM at the reference wavelength\",\n \"Entrance-pupil diameter f_ref / N is wavelength independent; distances are measured from ideal principal planes\",\n \"Longitudinal chromatic focus only: lateral chromatic magnification, spherochromatism and sensor response are separate\",\n \"Wavelength basis must match the dispersion data; no air/vacuum conversion is performed\"\n ]\n );\n}\n"]}
@@ -1,14 +1,19 @@
1
1
  /**
2
- * Module boundary and integration notes.
3
- * Calculates continuous monochromatic Fraunhofer PSF density for a uniformly illuminated, zero-phase,
4
- * on-axis ideal straight-edged regular polygon. Physical area is explicit; f/N may supply the
5
- * equal-area diameter only under a declared nominal-area convention. No phase aberration, clipping,
6
- * field dependence, curved blades, defocus or polychromatic behavior is inferred. Density = A |F/A|² /
7
- * (lambda * propagationDistance)². Parseval normalization is over the infinite plane, NOT over the
8
- * supplied point list. Downstream quadrature must preserve density × area and report
9
- * truncation/convergence.
10
- * @see docs/PHYSICS_FOUNDATION.md for equations, coordinate/unit conventions, blockers and support
11
- * limits.
2
+ * Diffraction PSF (point-spread function) of a polygon-shaped aperture.
3
+ *
4
+ * The main model gives the continuous, single-wavelength Fraunhofer (far-field) PSF density of an
5
+ * ideal regular polygon with straight edges. The pupil is uniformly lit, has zero phase and sits on
6
+ * the optical axis.
7
+ * - The physical area is explicit. f/N may supply the diameter of a circle with the same area, but
8
+ * only when the caller declares the nominal-area convention.
9
+ * - Nothing else is assumed: no phase aberration, clipping, field dependence, curved blades, defocus
10
+ * or multi-wavelength behaviour.
11
+ *
12
+ * Density = A |F/A|² / (lambda * propagationDistance)². The density integrates to 1 over the
13
+ * infinite image plane (Parseval). It is NOT normalized over the supplied list of points. Code that
14
+ * sums these samples must keep density × area and report truncation and convergence.
15
+ * @see docs/PHYSICS_FOUNDATION.md for the equations, units, coordinate conventions, known blockers
16
+ * and support limits.
12
17
  */
13
18
  import { type CalculationResult } from "../core/calculation-result.js";
14
19
  import { type CalculateIdealApertureInput } from "./aperture.js";
@@ -17,9 +22,9 @@ import type { SpectralWavelengthBasis } from "../core/spectral.js";
17
22
  export interface CalculateIdealPolygonDiffractionInput extends CalculateIdealApertureInput {
18
23
  /** Diameter of a circle with the SAME AREA as the physical polygon opening. */
19
24
  equivalentAreaPupilDiameterMm: number;
20
- /** Paraxial pupil-to-image propagation scale; not silently inferred from focus. */
25
+ /** Paraxial propagation distance from pupil to image. Never inferred from focus. */
21
26
  pupilToImageDistanceMm: number;
22
- /** Wavelength in the declared propagation medium; no air/vacuum conversion. */
27
+ /** Wavelength in the declared propagation medium. No air/vacuum conversion is applied. */
23
28
  wavelengthNm: number;
24
29
  wavelengthBasis: Exclude<SpectralWavelengthBasis, "unspecified">;
25
30
  /** Displacements from the on-axis PSF center, +X right / +Y up; at most 4096. */
@@ -28,7 +33,7 @@ export interface CalculateIdealPolygonDiffractionInput extends CalculateIdealApe
28
33
  y: number;
29
34
  }[];
30
35
  }
31
- /** Continuous unit-energy PSF samples, not a normalized finite convolution kernel. */
36
+ /** Samples of a continuous unit-energy PSF. This is not a normalized finite convolution kernel. */
32
37
  export interface IdealPolygonDiffraction {
33
38
  bladeCount: number;
34
39
  firstBladeEdgeAngleDegrees: number;
@@ -46,22 +51,74 @@ export interface IdealPolygonDiffraction {
46
51
  x: number;
47
52
  y: number;
48
53
  };
49
- /** |F/A|²; unity at the origin. Not an energy/probability weight. */
54
+ /** |F/A|². Equal to 1 at the origin. Not an energy or probability weight. */
50
55
  peakNormalizedIntensity: number;
51
56
  /** Density integrating to unity over the full image plane, in 1/µm². */
52
57
  intensityDensityPerSquareMicrometer: number;
53
58
  }[];
54
59
  }
55
60
  /**
56
- * Calculates continuous monochromatic Fraunhofer PSF density for a uniformly
57
- * illuminated, zero-phase, on-axis ideal straight-edged regular polygon.
58
- * Physical area is explicit; f/N may supply the equal-area diameter only under
59
- * a declared nominal-area convention. No phase aberration, clipping, field
60
- * dependence, curved blades, defocus or polychromatic behavior is inferred.
61
+ * Calculates the continuous, single-wavelength Fraunhofer (far-field) PSF
62
+ * density of an ideal regular polygon with straight edges. The pupil is
63
+ * uniformly lit, has zero phase and sits on the optical axis.
64
+ *
65
+ * The physical area is explicit. f/N may supply the equal-area diameter only
66
+ * when the caller declares the nominal-area convention. Nothing else is
67
+ * assumed: no phase aberration, clipping, field dependence, curved blades,
68
+ * defocus or multi-wavelength behaviour.
61
69
  *
62
- * Density = A |F/A|² / (lambda * propagationDistance)². Parseval normalization
63
- * is over the infinite plane, NOT over the supplied point list. Downstream
64
- * quadrature must preserve density × area and report truncation/convergence.
70
+ * Density = A |F/A|² / (lambda * propagationDistance)². It integrates to 1
71
+ * over the infinite plane (Parseval), NOT over the supplied points. Code that
72
+ * sums the samples must keep density × area and report truncation and
73
+ * convergence.
65
74
  */
66
75
  export declare function calculateIdealPolygonDiffractionPsf(input: CalculateIdealPolygonDiffractionInput): CalculationResult<IdealPolygonDiffraction>;
67
- //# sourceMappingURL=polygon-diffraction.d.ts.map
76
+ /** On-axis scalar Fraunhofer diffraction of one arbitrary simple polygon pupil. */
77
+ export interface CalculatePolygonPupilFraunhoferPsfInput {
78
+ /**
79
+ * Simple (non-self-intersecting) pupil polygon in pupil-plane millimetres, +X right / +Y up,
80
+ * with 3 to 4096 vertices. For example, the cat's-eye pupil from calculateMechanicalVignetting().
81
+ */
82
+ pupilVerticesMm: readonly {
83
+ x: number;
84
+ y: number;
85
+ }[];
86
+ /** Paraxial propagation distance from pupil to image. Never inferred from focus. */
87
+ pupilToImageDistanceMm: number;
88
+ /** Wavelength in the declared propagation medium. No air/vacuum conversion is applied. */
89
+ wavelengthNm: number;
90
+ wavelengthBasis: Exclude<SpectralWavelengthBasis, "unspecified">;
91
+ /** Displacements from the PSF centre (the geometric image point), +X right / +Y up; at most 4096. */
92
+ imagePointsMicrometers: readonly {
93
+ x: number;
94
+ y: number;
95
+ }[];
96
+ }
97
+ export interface PolygonPupilFraunhoferPsf {
98
+ pupilAreaSquareMm: number;
99
+ pupilToImageDistanceMm: number;
100
+ wavelengthNm: number;
101
+ wavelengthBasis: Exclude<SpectralWavelengthBasis, "unspecified">;
102
+ fieldAxes: "+X right, +Y up";
103
+ energyNormalization: "unit-integral-over-infinite-image-plane";
104
+ throughputApplied: false;
105
+ samples: readonly {
106
+ imagePointMicrometers: {
107
+ x: number;
108
+ y: number;
109
+ };
110
+ /** |F/A|²; unity at the origin. */
111
+ peakNormalizedIntensity: number;
112
+ /** Density integrating to unity over the full image plane, in 1/µm². */
113
+ intensityDensityPerSquareMicrometer: number;
114
+ }[];
115
+ }
116
+ /**
117
+ * Continuous, single-wavelength Fraunhofer PSF density for any simple polygon pupil that is uniformly
118
+ * lit and has zero phase (for example a cat's-eye pupil from mechanical vignetting).
119
+ *
120
+ * It uses the same analytic edge integral as the regular-polygon model, so there is no aliasing from
121
+ * a pupil grid. Moving the pupil off the axis only adds a linear phase; the intensity does not
122
+ * change. Density = A |F/A|² / (lambda z)², and it integrates to 1 over the infinite plane.
123
+ */
124
+ export declare function calculatePolygonPupilFraunhoferPsf(input: CalculatePolygonPupilFraunhoferPsfInput): CalculationResult<PolygonPupilFraunhoferPsf>;
@@ -1,19 +1,26 @@
1
1
  // SPDX-License-Identifier: Apache-2.0
2
2
  /**
3
- * Module boundary and integration notes.
4
- * Calculates continuous monochromatic Fraunhofer PSF density for a uniformly illuminated, zero-phase,
5
- * on-axis ideal straight-edged regular polygon. Physical area is explicit; f/N may supply the
6
- * equal-area diameter only under a declared nominal-area convention. No phase aberration, clipping,
7
- * field dependence, curved blades, defocus or polychromatic behavior is inferred. Density = A |F/A|² /
8
- * (lambda * propagationDistance)². Parseval normalization is over the infinite plane, NOT over the
9
- * supplied point list. Downstream quadrature must preserve density × area and report
10
- * truncation/convergence.
11
- * @see docs/PHYSICS_FOUNDATION.md for equations, coordinate/unit conventions, blockers and support
12
- * limits.
3
+ * Diffraction PSF (point-spread function) of a polygon-shaped aperture.
4
+ *
5
+ * The main model gives the continuous, single-wavelength Fraunhofer (far-field) PSF density of an
6
+ * ideal regular polygon with straight edges. The pupil is uniformly lit, has zero phase and sits on
7
+ * the optical axis.
8
+ * - The physical area is explicit. f/N may supply the diameter of a circle with the same area, but
9
+ * only when the caller declares the nominal-area convention.
10
+ * - Nothing else is assumed: no phase aberration, clipping, field dependence, curved blades, defocus
11
+ * or multi-wavelength behaviour.
12
+ *
13
+ * Density = A |F/A|² / (lambda * propagationDistance)². The density integrates to 1 over the
14
+ * infinite image plane (Parseval). It is NOT normalized over the supplied list of points. Code that
15
+ * sums these samples must keep density × area and report truncation and convergence.
16
+ * @see docs/PHYSICS_FOUNDATION.md for the equations, units, coordinate conventions, known blockers
17
+ * and support limits.
13
18
  */
14
19
  import { approximationResult } from "../core/calculation-result.js";
15
20
  import { InvalidScientificInputError, requirePositiveFinite } from "../core/validation.js";
16
21
  import { calculateIdealApertureGeometry } from "./aperture.js";
22
+ import { requireInputKeys } from "../core/record-validation.js";
23
+ import { InvalidConfigurationError } from "../core/configuration-error.js";
17
24
  /** sin(x)/x - 1, evaluated without cancellation near zero. */
18
25
  function sincMinusOne(x) {
19
26
  if (Math.abs(x) < 0.01) {
@@ -23,10 +30,11 @@ function sincMinusOne(x) {
23
30
  return Math.sin(x) / x - 1;
24
31
  }
25
32
  /**
26
- * Independently derived polygon Fourier boundary integral via the divergence
27
- * theorem. Coordinates use unit circumradius so pupil size cannot change the
28
- * numerical conditioning. Subtracting the zero-frequency edge term (whose
29
- * closed-contour sum is zero) removes cancellation at/near the origin.
33
+ * Fourier transform of the polygon, written as an integral around its edges
34
+ * using the divergence theorem (independently derived). Coordinates use a
35
+ * circumradius of 1, so pupil size cannot affect numerical conditioning.
36
+ * Subtracting the zero-frequency edge term (which sums to zero around the
37
+ * closed polygon) avoids cancellation at and near the origin.
30
38
  */
31
39
  function peakIntensity(vertices, area, qx, qy) {
32
40
  const q = Math.hypot(qx, qy);
@@ -53,15 +61,19 @@ function peakIntensity(vertices, area, qx, qy) {
53
61
  return real * real + imaginary * imaginary;
54
62
  }
55
63
  /**
56
- * Calculates continuous monochromatic Fraunhofer PSF density for a uniformly
57
- * illuminated, zero-phase, on-axis ideal straight-edged regular polygon.
58
- * Physical area is explicit; f/N may supply the equal-area diameter only under
59
- * a declared nominal-area convention. No phase aberration, clipping, field
60
- * dependence, curved blades, defocus or polychromatic behavior is inferred.
64
+ * Calculates the continuous, single-wavelength Fraunhofer (far-field) PSF
65
+ * density of an ideal regular polygon with straight edges. The pupil is
66
+ * uniformly lit, has zero phase and sits on the optical axis.
67
+ *
68
+ * The physical area is explicit. f/N may supply the equal-area diameter only
69
+ * when the caller declares the nominal-area convention. Nothing else is
70
+ * assumed: no phase aberration, clipping, field dependence, curved blades,
71
+ * defocus or multi-wavelength behaviour.
61
72
  *
62
- * Density = A |F/A|² / (lambda * propagationDistance)². Parseval normalization
63
- * is over the infinite plane, NOT over the supplied point list. Downstream
64
- * quadrature must preserve density × area and report truncation/convergence.
73
+ * Density = A |F/A|² / (lambda * propagationDistance)². It integrates to 1
74
+ * over the infinite plane (Parseval), NOT over the supplied points. Code that
75
+ * sums the samples must keep density × area and report truncation and
76
+ * convergence.
65
77
  */
66
78
  export function calculateIdealPolygonDiffractionPsf(input) {
67
79
  // Reject unmodeled effects rather than silently accepting and ignoring them.
@@ -71,13 +83,13 @@ export function calculateIdealPolygonDiffractionPsf(input) {
71
83
  ]);
72
84
  if (typeof input !== "object" || input === null || Array.isArray(input) ||
73
85
  Object.keys(input).some((key) => !allowed.has(key))) {
74
- throw new InvalidScientificInputError("Polygon diffraction input contains unsupported fields or is not an object.");
86
+ throw new InvalidConfigurationError("Polygon diffraction input contains unsupported fields or is not an object.");
75
87
  }
76
88
  requirePositiveFinite("equivalentAreaPupilDiameterMm", input.equivalentAreaPupilDiameterMm);
77
89
  requirePositiveFinite("pupilToImageDistanceMm", input.pupilToImageDistanceMm);
78
90
  requirePositiveFinite("wavelengthNm", input.wavelengthNm);
79
91
  if (input.wavelengthBasis !== "air" && input.wavelengthBasis !== "vacuum") {
80
- throw new InvalidScientificInputError("wavelengthBasis must be air or vacuum.");
92
+ throw new InvalidConfigurationError("wavelengthBasis must be air or vacuum.");
81
93
  }
82
94
  if (input.firstBladeEdgeAngleDegrees !== undefined && !Number.isFinite(input.firstBladeEdgeAngleDegrees)) {
83
95
  throw new InvalidScientificInputError("firstBladeEdgeAngleDegrees must be finite when supplied.");
@@ -91,7 +103,7 @@ export function calculateIdealPolygonDiffractionPsf(input) {
91
103
  throw new InvalidScientificInputError("imagePointsMicrometers must not contain sparse entries.");
92
104
  }
93
105
  }
94
- const geometry = calculateIdealApertureGeometry(input).value;
106
+ const geometry = calculateIdealApertureGeometry({ bladeCount: input.bladeCount, ...(input.firstBladeEdgeAngleDegrees === undefined ? {} : { firstBladeEdgeAngleDegrees: input.firstBladeEdgeAngleDegrees }) }).value;
95
107
  const unitArea = input.bladeCount * Math.sin(2 * Math.PI / input.bladeCount) / 2;
96
108
  const pupilAreaSquareMm = Math.PI * (input.equivalentAreaPupilDiameterMm / 2) ** 2;
97
109
  const radius = Math.sqrt(pupilAreaSquareMm / unitArea);
@@ -142,4 +154,97 @@ export function calculateIdealPolygonDiffractionPsf(input) {
142
154
  "Circular Airy remains a separate named diagnostic; do not stack this diffraction PSF over an already diffracted complex-pupil result."
143
155
  ], { notes: ["No quantified physical-model uncertainty is asserted. Numerical tolerances in tests are validation evidence, not real-lens accuracy bounds."] });
144
156
  }
157
+ function requirePlanarPoint(value, path) {
158
+ if (typeof value !== "object" || value === null || Array.isArray(value)) {
159
+ throw new InvalidScientificInputError(`${path} must contain finite x/y coordinates only.`);
160
+ }
161
+ const record = value;
162
+ if (Object.keys(record).some((key) => key !== "x" && key !== "y") ||
163
+ typeof record.x !== "number" || typeof record.y !== "number" ||
164
+ !Number.isFinite(record.x) || !Number.isFinite(record.y)) {
165
+ throw new InvalidScientificInputError(`${path} must contain finite x/y coordinates only.`);
166
+ }
167
+ return { x: record.x, y: record.y };
168
+ }
169
+ /**
170
+ * Continuous, single-wavelength Fraunhofer PSF density for any simple polygon pupil that is uniformly
171
+ * lit and has zero phase (for example a cat's-eye pupil from mechanical vignetting).
172
+ *
173
+ * It uses the same analytic edge integral as the regular-polygon model, so there is no aliasing from
174
+ * a pupil grid. Moving the pupil off the axis only adds a linear phase; the intensity does not
175
+ * change. Density = A |F/A|² / (lambda z)², and it integrates to 1 over the infinite plane.
176
+ */
177
+ export function calculatePolygonPupilFraunhoferPsf(input) {
178
+ requireInputKeys(input, "calculatePolygonPupilFraunhoferPsf", ["pupilVerticesMm", "pupilToImageDistanceMm", "wavelengthNm", "wavelengthBasis", "imagePointsMicrometers"]);
179
+ requirePositiveFinite("pupilToImageDistanceMm", input.pupilToImageDistanceMm);
180
+ requirePositiveFinite("wavelengthNm", input.wavelengthNm);
181
+ if (input.wavelengthBasis !== "air" && input.wavelengthBasis !== "vacuum") {
182
+ throw new InvalidConfigurationError("wavelengthBasis must be air or vacuum.");
183
+ }
184
+ if (!Array.isArray(input.pupilVerticesMm) || input.pupilVerticesMm.length < 3 ||
185
+ input.pupilVerticesMm.length > 4096) {
186
+ throw new InvalidScientificInputError("pupilVerticesMm must contain 3 through 4096 vertices.");
187
+ }
188
+ if (!Array.isArray(input.imagePointsMicrometers) ||
189
+ input.imagePointsMicrometers.length === 0 || input.imagePointsMicrometers.length > 4096) {
190
+ throw new InvalidScientificInputError("imagePointsMicrometers must contain 1 through 4096 points.");
191
+ }
192
+ const vertices = input.pupilVerticesMm.map((vertex, index) => requirePlanarPoint(vertex, `pupilVerticesMm[${index}]`));
193
+ // Centre and scale the polygon for conditioning; translation changes only the phase of F.
194
+ const cx = vertices.reduce((sum, v) => sum + v.x, 0) / vertices.length;
195
+ const cy = vertices.reduce((sum, v) => sum + v.y, 0) / vertices.length;
196
+ const scale = Math.max(...vertices.map((v) => Math.hypot(v.x - cx, v.y - cy)));
197
+ if (!(scale > 0) || !Number.isFinite(scale)) {
198
+ throw new InvalidScientificInputError("pupilVerticesMm must span a finite non-zero region.");
199
+ }
200
+ let normalized = vertices.map((v) => ({ x: (v.x - cx) / scale, y: (v.y - cy) / scale }));
201
+ let twiceArea = 0;
202
+ for (let index = 0; index < normalized.length; index += 1) {
203
+ const a = normalized[index];
204
+ const b = normalized[(index + 1) % normalized.length];
205
+ twiceArea += a.x * b.y - b.x * a.y;
206
+ }
207
+ if (twiceArea < 0) {
208
+ normalized = [...normalized].reverse();
209
+ twiceArea = -twiceArea;
210
+ }
211
+ const unitArea = twiceArea / 2;
212
+ const pupilAreaSquareMm = unitArea * scale * scale;
213
+ const propagationScale = input.wavelengthNm / 1_000_000 * input.pupilToImageDistanceMm;
214
+ const densityScale = pupilAreaSquareMm / propagationScale ** 2 / 1_000_000;
215
+ if (!(unitArea > 1e-12) ||
216
+ ![pupilAreaSquareMm, propagationScale, densityScale].every((x) => Number.isFinite(x) && x > 0)) {
217
+ throw new InvalidScientificInputError("Polygon pupil area and derived scales must remain finite and positive.");
218
+ }
219
+ const samples = input.imagePointsMicrometers.map((value, index) => {
220
+ const point = requirePlanarPoint(value, `imagePointsMicrometers[${index}]`);
221
+ const qx = 2 * Math.PI * (point.x / 1000) * scale / propagationScale;
222
+ const qy = 2 * Math.PI * (point.y / 1000) * scale / propagationScale;
223
+ if (!Number.isFinite(Math.hypot(qx, qy)) || Math.hypot(qx, qy) > 1_000_000) {
224
+ throw new InvalidScientificInputError("Dimensionless pupil phase radius must not exceed 1000000.");
225
+ }
226
+ const intensity = peakIntensity(normalized, unitArea, qx, qy);
227
+ return {
228
+ imagePointMicrometers: { x: point.x === 0 ? 0 : point.x, y: point.y === 0 ? 0 : point.y },
229
+ peakNormalizedIntensity: intensity,
230
+ intensityDensityPerSquareMicrometer: intensity * densityScale
231
+ };
232
+ });
233
+ return approximationResult({
234
+ pupilAreaSquareMm,
235
+ pupilToImageDistanceMm: input.pupilToImageDistanceMm,
236
+ wavelengthNm: input.wavelengthNm,
237
+ wavelengthBasis: input.wavelengthBasis,
238
+ fieldAxes: "+X right, +Y up",
239
+ energyNormalization: "unit-integral-over-infinite-image-plane",
240
+ throughputApplied: false,
241
+ samples
242
+ }, "polygon-pupil-fraunhofer-diffraction", "1.0.0", [
243
+ "Uniform unit pupil amplitude and zero phase over a caller-declared simple polygon; scalar paraxial Fraunhofer propagation.",
244
+ "The PSF is centred on the geometric image point; a pupil offset from the optical axis adds only a linear phase.",
245
+ "Continuous PSF density has unit integral over the infinite image plane. Point samples are not a finite energy-normalized kernel.",
246
+ "Pupil-area throughput (for example mechanical vignetting) is reported separately and not applied to the density.",
247
+ "No aberration, defocus, polarization, sensor response or stray light is modeled."
248
+ ], { notes: ["No quantified physical-model uncertainty is asserted. Numerical tolerances in tests are validation evidence, not real-lens accuracy bounds."] });
249
+ }
145
250
  //# sourceMappingURL=polygon-diffraction.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"polygon-diffraction.js","sourceRoot":"","sources":["../../src/optics/polygon-diffraction.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"polygon-diffraction.js","sourceRoot":"","sources":["../../src/optics/polygon-diffraction.ts"],"names":[],"mappings":"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","sourcesContent":["// SPDX-License-Identifier: Apache-2.0\n\n/**\n * Diffraction PSF (point-spread function) of a polygon-shaped aperture.\n *\n * The main model gives the continuous, single-wavelength Fraunhofer (far-field) PSF density of an\n * ideal regular polygon with straight edges. The pupil is uniformly lit, has zero phase and sits on\n * the optical axis.\n * - The physical area is explicit. f/N may supply the diameter of a circle with the same area, but\n * only when the caller declares the nominal-area convention.\n * - Nothing else is assumed: no phase aberration, clipping, field dependence, curved blades, defocus\n * or multi-wavelength behaviour.\n *\n * Density = A |F/A|² / (lambda * propagationDistance)². The density integrates to 1 over the\n * infinite image plane (Parseval). It is NOT normalized over the supplied list of points. Code that\n * sums these samples must keep density × area and report truncation and convergence.\n * @see docs/PHYSICS_FOUNDATION.md for the equations, units, coordinate conventions, known blockers\n * and support limits.\n */\n\nimport { approximationResult, type CalculationResult } from \"../core/calculation-result.js\";\nimport { InvalidScientificInputError, requirePositiveFinite } from \"../core/validation.js\";\nimport { calculateIdealApertureGeometry, type CalculateIdealApertureInput } from \"./aperture.js\";\nimport type { SpectralWavelengthBasis } from \"../core/spectral.js\";\nimport { requireInputKeys } from \"../core/record-validation.js\";\nimport { InvalidConfigurationError } from \"../core/configuration-error.js\";\n\n/** On-axis, in-focus scalar diffraction of one ideal regular polygon pupil. */\nexport interface CalculateIdealPolygonDiffractionInput extends CalculateIdealApertureInput {\n /** Diameter of a circle with the SAME AREA as the physical polygon opening. */\n equivalentAreaPupilDiameterMm: number;\n /** Paraxial propagation distance from pupil to image. Never inferred from focus. */\n pupilToImageDistanceMm: number;\n /** Wavelength in the declared propagation medium. No air/vacuum conversion is applied. */\n wavelengthNm: number;\n wavelengthBasis: Exclude<SpectralWavelengthBasis, \"unspecified\">;\n /** Displacements from the on-axis PSF center, +X right / +Y up; at most 4096. */\n imagePointsMicrometers: readonly { x: number; y: number }[];\n}\n\n/** Samples of a continuous unit-energy PSF. This is not a normalized finite convolution kernel. */\nexport interface IdealPolygonDiffraction {\n bladeCount: number;\n firstBladeEdgeAngleDegrees: number;\n pupilToImageDistanceMm: number;\n wavelengthNm: number;\n wavelengthBasis: Exclude<SpectralWavelengthBasis, \"unspecified\">;\n pupilAreaSquareMm: number;\n pupilCircumradiusMm: number;\n pupilNormalization: \"equal-area-circle\";\n fieldAxes: \"+X right, +Y up\";\n energyNormalization: \"unit-integral-over-infinite-image-plane\";\n throughputApplied: false;\n samples: readonly {\n imagePointMicrometers: { x: number; y: number };\n /** |F/A|². Equal to 1 at the origin. Not an energy or probability weight. */\n peakNormalizedIntensity: number;\n /** Density integrating to unity over the full image plane, in 1/µm². */\n intensityDensityPerSquareMicrometer: number;\n }[];\n}\n\n/** sin(x)/x - 1, evaluated without cancellation near zero. */\nfunction sincMinusOne(x: number): number {\n if (Math.abs(x) < 0.01) {\n const x2 = x * x;\n return x2 * (-1 / 6 + x2 * (1 / 120 - x2 / 5040));\n }\n return Math.sin(x) / x - 1;\n}\n\n/**\n * Fourier transform of the polygon, written as an integral around its edges\n * using the divergence theorem (independently derived). Coordinates use a\n * circumradius of 1, so pupil size cannot affect numerical conditioning.\n * Subtracting the zero-frequency edge term (which sums to zero around the\n * closed polygon) avoids cancellation at and near the origin.\n */\nfunction peakIntensity(\n vertices: readonly { x: number; y: number }[],\n area: number,\n qx: number,\n qy: number\n): number {\n const q = Math.hypot(qx, qy);\n if (q === 0) return 1;\n const ux = qx / q;\n const uy = qy / q;\n let real = 0;\n let imaginary = 0;\n for (let index = 0; index < vertices.length; index += 1) {\n const a = vertices[index]!;\n const b = vertices[(index + 1) % vertices.length]!;\n const dx = b.x - a.x;\n const dy = b.y - a.y;\n const midpointPhase = qx * (a.x + b.x) / 2 + qy * (a.y + b.y) / 2;\n const edgePhase = (qx * dx + qy * dy) / 2;\n const sm1 = sincMinusOne(edgePhase);\n const sinc = 1 + sm1;\n const coefficient = (ux * dy - uy * dx) / area;\n // i times the edge integral: real = -Im(edge), imaginary = Re(edge).\n real += coefficient * sinc * (Math.sin(midpointPhase) / q);\n imaginary += coefficient * (sm1 - sinc * 2 * Math.sin(midpointPhase / 2) ** 2) / q;\n }\n return real * real + imaginary * imaginary;\n}\n\n/**\n * Calculates the continuous, single-wavelength Fraunhofer (far-field) PSF\n * density of an ideal regular polygon with straight edges. The pupil is\n * uniformly lit, has zero phase and sits on the optical axis.\n *\n * The physical area is explicit. f/N may supply the equal-area diameter only\n * when the caller declares the nominal-area convention. Nothing else is\n * assumed: no phase aberration, clipping, field dependence, curved blades,\n * defocus or multi-wavelength behaviour.\n *\n * Density = A |F/A|² / (lambda * propagationDistance)². It integrates to 1\n * over the infinite plane (Parseval), NOT over the supplied points. Code that\n * sums the samples must keep density × area and report truncation and\n * convergence.\n */\nexport function calculateIdealPolygonDiffractionPsf(\n input: CalculateIdealPolygonDiffractionInput\n): CalculationResult<IdealPolygonDiffraction> {\n // Reject unmodeled effects rather than silently accepting and ignoring them.\n const allowed = new Set([\n \"bladeCount\", \"firstBladeEdgeAngleDegrees\", \"equivalentAreaPupilDiameterMm\",\n \"pupilToImageDistanceMm\", \"wavelengthNm\", \"wavelengthBasis\", \"imagePointsMicrometers\"\n ]);\n if (typeof input !== \"object\" || input === null || Array.isArray(input) ||\n Object.keys(input).some((key) => !allowed.has(key))) {\n throw new InvalidConfigurationError(\"Polygon diffraction input contains unsupported fields or is not an object.\");\n }\n requirePositiveFinite(\"equivalentAreaPupilDiameterMm\", input.equivalentAreaPupilDiameterMm);\n requirePositiveFinite(\"pupilToImageDistanceMm\", input.pupilToImageDistanceMm);\n requirePositiveFinite(\"wavelengthNm\", input.wavelengthNm);\n if (input.wavelengthBasis !== \"air\" && input.wavelengthBasis !== \"vacuum\") {\n throw new InvalidConfigurationError(\"wavelengthBasis must be air or vacuum.\");\n }\n if (input.firstBladeEdgeAngleDegrees !== undefined && !Number.isFinite(input.firstBladeEdgeAngleDegrees)) {\n throw new InvalidScientificInputError(\"firstBladeEdgeAngleDegrees must be finite when supplied.\");\n }\n if (!Array.isArray(input.imagePointsMicrometers) ||\n input.imagePointsMicrometers.length === 0 || input.imagePointsMicrometers.length > 4096) {\n throw new InvalidScientificInputError(\"imagePointsMicrometers must contain 1 through 4096 points.\");\n }\n for (let index = 0; index < input.imagePointsMicrometers.length; index += 1) {\n if (!Object.hasOwn(input.imagePointsMicrometers, index)) {\n throw new InvalidScientificInputError(\"imagePointsMicrometers must not contain sparse entries.\");\n }\n }\n const geometry = calculateIdealApertureGeometry({ bladeCount: input.bladeCount, ...(input.firstBladeEdgeAngleDegrees === undefined ? {} : { firstBladeEdgeAngleDegrees: input.firstBladeEdgeAngleDegrees }) }).value;\n const unitArea = input.bladeCount * Math.sin(2 * Math.PI / input.bladeCount) / 2;\n const pupilAreaSquareMm = Math.PI * (input.equivalentAreaPupilDiameterMm / 2) ** 2;\n const radius = Math.sqrt(pupilAreaSquareMm / unitArea);\n const propagationScale = input.wavelengthNm / 1_000_000 * input.pupilToImageDistanceMm;\n const densityScale = pupilAreaSquareMm / propagationScale ** 2 / 1_000_000;\n if (![pupilAreaSquareMm, radius, propagationScale, densityScale].every((x) => Number.isFinite(x) && x > 0)) {\n throw new InvalidScientificInputError(\"Derived polygon diffraction scales must remain finite and positive.\");\n }\n const samples = input.imagePointsMicrometers.map((point) => {\n if (typeof point !== \"object\" || point === null || Array.isArray(point) ||\n !Number.isFinite(point.x) || !Number.isFinite(point.y) ||\n Object.keys(point).some((key) => key !== \"x\" && key !== \"y\")) {\n throw new InvalidScientificInputError(\"Each image point must contain finite x/y coordinates only.\");\n }\n const qx = 2 * Math.PI * (point.x / 1000) * radius / propagationScale;\n const qy = 2 * Math.PI * (point.y / 1000) * radius / propagationScale;\n // A numerical envelope, not a real-lens calibration or physical accuracy bound.\n if (!Number.isFinite(Math.hypot(qx, qy)) || Math.hypot(qx, qy) > 1_000_000) {\n throw new InvalidScientificInputError(\"Dimensionless pupil phase radius must not exceed 1000000.\");\n }\n const intensity = peakIntensity(geometry.normalizedVertices, unitArea, qx, qy);\n return {\n imagePointMicrometers: { x: point.x === 0 ? 0 : point.x, y: point.y === 0 ? 0 : point.y },\n peakNormalizedIntensity: intensity,\n intensityDensityPerSquareMicrometer: intensity * densityScale\n };\n });\n return approximationResult({\n bladeCount: geometry.bladeCount,\n firstBladeEdgeAngleDegrees: input.firstBladeEdgeAngleDegrees ?? 0,\n pupilToImageDistanceMm: input.pupilToImageDistanceMm,\n wavelengthNm: input.wavelengthNm,\n wavelengthBasis: input.wavelengthBasis,\n pupilAreaSquareMm,\n pupilCircumradiusMm: radius,\n pupilNormalization: \"equal-area-circle\",\n fieldAxes: \"+X right, +Y up\",\n energyNormalization: \"unit-integral-over-infinite-image-plane\",\n throughputApplied: false,\n samples\n }, \"ideal-regular-polygon-fraunhofer-diffraction\", \"1.0.0\", [\n \"Uniform unit pupil amplitude, zero phase, ideal regular straight-edged polygon; on-axis in-focus scalar paraxial Fraunhofer propagation only.\",\n \"Wavelength is supplied in its declared propagation medium; no wavelength-basis conversion is performed.\",\n \"Equal-area diameter fixes physical pupil area, not circumradius or inradius; no optical throughput loss is applied.\",\n \"Continuous PSF density has unit integral over the infinite image plane. Point samples are not a finite energy-normalized kernel.\",\n \"The analytical polygon boundary integral has no FFT/pupil-grid aliasing; downstream image-plane sampling and finite-support truncation still require convergence checks.\",\n \"No real-lens calibration, aberration, defocus, mechanical clipping, curved blades, field dependence, polarization, sensor response or stray light is modeled.\",\n \"Circular Airy remains a separate named diagnostic; do not stack this diffraction PSF over an already diffracted complex-pupil result.\"\n ], { notes: [\"No quantified physical-model uncertainty is asserted. Numerical tolerances in tests are validation evidence, not real-lens accuracy bounds.\"] });\n}\n\n/** On-axis scalar Fraunhofer diffraction of one arbitrary simple polygon pupil. */\nexport interface CalculatePolygonPupilFraunhoferPsfInput {\n /**\n * Simple (non-self-intersecting) pupil polygon in pupil-plane millimetres, +X right / +Y up,\n * with 3 to 4096 vertices. For example, the cat's-eye pupil from calculateMechanicalVignetting().\n */\n pupilVerticesMm: readonly { x: number; y: number }[];\n /** Paraxial propagation distance from pupil to image. Never inferred from focus. */\n pupilToImageDistanceMm: number;\n /** Wavelength in the declared propagation medium. No air/vacuum conversion is applied. */\n wavelengthNm: number;\n wavelengthBasis: Exclude<SpectralWavelengthBasis, \"unspecified\">;\n /** Displacements from the PSF centre (the geometric image point), +X right / +Y up; at most 4096. */\n imagePointsMicrometers: readonly { x: number; y: number }[];\n}\n\nexport interface PolygonPupilFraunhoferPsf {\n pupilAreaSquareMm: number;\n pupilToImageDistanceMm: number;\n wavelengthNm: number;\n wavelengthBasis: Exclude<SpectralWavelengthBasis, \"unspecified\">;\n fieldAxes: \"+X right, +Y up\";\n energyNormalization: \"unit-integral-over-infinite-image-plane\";\n throughputApplied: false;\n samples: readonly {\n imagePointMicrometers: { x: number; y: number };\n /** |F/A|²; unity at the origin. */\n peakNormalizedIntensity: number;\n /** Density integrating to unity over the full image plane, in 1/µm². */\n intensityDensityPerSquareMicrometer: number;\n }[];\n}\n\nfunction requirePlanarPoint(value: unknown, path: string): { x: number; y: number } {\n if (typeof value !== \"object\" || value === null || Array.isArray(value)) {\n throw new InvalidScientificInputError(`${path} must contain finite x/y coordinates only.`);\n }\n const record = value as Record<string, unknown>;\n if (\n Object.keys(record).some((key) => key !== \"x\" && key !== \"y\") ||\n typeof record.x !== \"number\" || typeof record.y !== \"number\" ||\n !Number.isFinite(record.x) || !Number.isFinite(record.y)\n ) {\n throw new InvalidScientificInputError(`${path} must contain finite x/y coordinates only.`);\n }\n return { x: record.x, y: record.y };\n}\n\n/**\n * Continuous, single-wavelength Fraunhofer PSF density for any simple polygon pupil that is uniformly\n * lit and has zero phase (for example a cat's-eye pupil from mechanical vignetting).\n *\n * It uses the same analytic edge integral as the regular-polygon model, so there is no aliasing from\n * a pupil grid. Moving the pupil off the axis only adds a linear phase; the intensity does not\n * change. Density = A |F/A|² / (lambda z)², and it integrates to 1 over the infinite plane.\n */\nexport function calculatePolygonPupilFraunhoferPsf(\n input: CalculatePolygonPupilFraunhoferPsfInput\n): CalculationResult<PolygonPupilFraunhoferPsf> {\n requireInputKeys(input, \"calculatePolygonPupilFraunhoferPsf\", [\"pupilVerticesMm\", \"pupilToImageDistanceMm\", \"wavelengthNm\", \"wavelengthBasis\", \"imagePointsMicrometers\"]);\n requirePositiveFinite(\"pupilToImageDistanceMm\", input.pupilToImageDistanceMm);\n requirePositiveFinite(\"wavelengthNm\", input.wavelengthNm);\n if (input.wavelengthBasis !== \"air\" && input.wavelengthBasis !== \"vacuum\") {\n throw new InvalidConfigurationError(\"wavelengthBasis must be air or vacuum.\");\n }\n if (!Array.isArray(input.pupilVerticesMm) || input.pupilVerticesMm.length < 3 ||\n input.pupilVerticesMm.length > 4096) {\n throw new InvalidScientificInputError(\"pupilVerticesMm must contain 3 through 4096 vertices.\");\n }\n if (!Array.isArray(input.imagePointsMicrometers) ||\n input.imagePointsMicrometers.length === 0 || input.imagePointsMicrometers.length > 4096) {\n throw new InvalidScientificInputError(\"imagePointsMicrometers must contain 1 through 4096 points.\");\n }\n const vertices = input.pupilVerticesMm.map((vertex, index) =>\n requirePlanarPoint(vertex, `pupilVerticesMm[${index}]`));\n // Centre and scale the polygon for conditioning; translation changes only the phase of F.\n const cx = vertices.reduce((sum, v) => sum + v.x, 0) / vertices.length;\n const cy = vertices.reduce((sum, v) => sum + v.y, 0) / vertices.length;\n const scale = Math.max(...vertices.map((v) => Math.hypot(v.x - cx, v.y - cy)));\n if (!(scale > 0) || !Number.isFinite(scale)) {\n throw new InvalidScientificInputError(\"pupilVerticesMm must span a finite non-zero region.\");\n }\n let normalized = vertices.map((v) => ({ x: (v.x - cx) / scale, y: (v.y - cy) / scale }));\n let twiceArea = 0;\n for (let index = 0; index < normalized.length; index += 1) {\n const a = normalized[index]!;\n const b = normalized[(index + 1) % normalized.length]!;\n twiceArea += a.x * b.y - b.x * a.y;\n }\n if (twiceArea < 0) {\n normalized = [...normalized].reverse();\n twiceArea = -twiceArea;\n }\n const unitArea = twiceArea / 2;\n const pupilAreaSquareMm = unitArea * scale * scale;\n const propagationScale = input.wavelengthNm / 1_000_000 * input.pupilToImageDistanceMm;\n const densityScale = pupilAreaSquareMm / propagationScale ** 2 / 1_000_000;\n if (!(unitArea > 1e-12) ||\n ![pupilAreaSquareMm, propagationScale, densityScale].every((x) => Number.isFinite(x) && x > 0)) {\n throw new InvalidScientificInputError(\"Polygon pupil area and derived scales must remain finite and positive.\");\n }\n const samples = input.imagePointsMicrometers.map((value, index) => {\n const point = requirePlanarPoint(value, `imagePointsMicrometers[${index}]`);\n const qx = 2 * Math.PI * (point.x / 1000) * scale / propagationScale;\n const qy = 2 * Math.PI * (point.y / 1000) * scale / propagationScale;\n if (!Number.isFinite(Math.hypot(qx, qy)) || Math.hypot(qx, qy) > 1_000_000) {\n throw new InvalidScientificInputError(\"Dimensionless pupil phase radius must not exceed 1000000.\");\n }\n const intensity = peakIntensity(normalized, unitArea, qx, qy);\n return {\n imagePointMicrometers: { x: point.x === 0 ? 0 : point.x, y: point.y === 0 ? 0 : point.y },\n peakNormalizedIntensity: intensity,\n intensityDensityPerSquareMicrometer: intensity * densityScale\n };\n });\n return approximationResult({\n pupilAreaSquareMm,\n pupilToImageDistanceMm: input.pupilToImageDistanceMm,\n wavelengthNm: input.wavelengthNm,\n wavelengthBasis: input.wavelengthBasis,\n fieldAxes: \"+X right, +Y up\",\n energyNormalization: \"unit-integral-over-infinite-image-plane\",\n throughputApplied: false,\n samples\n }, \"polygon-pupil-fraunhofer-diffraction\", \"1.0.0\", [\n \"Uniform unit pupil amplitude and zero phase over a caller-declared simple polygon; scalar paraxial Fraunhofer propagation.\",\n \"The PSF is centred on the geometric image point; a pupil offset from the optical axis adds only a linear phase.\",\n \"Continuous PSF density has unit integral over the infinite image plane. Point samples are not a finite energy-normalized kernel.\",\n \"Pupil-area throughput (for example mechanical vignetting) is reported separately and not applied to the density.\",\n \"No aberration, defocus, polarization, sensor response or stray light is modeled.\"\n ], { notes: [\"No quantified physical-model uncertainty is asserted. Numerical tolerances in tests are validation evidence, not real-lens accuracy bounds.\"] });\n}\n"]}
@@ -1,5 +1,5 @@
1
1
  import { type EvidenceProvenance } from "../core/evidence-provenance.js";
2
- /** Exact, generic camera/lens and acquisition state; no implicit interpolation. */
2
+ /** Exact, generic camera, lens and acquisition state. Nothing is interpolated implicitly. */
3
3
  export interface OpticalProfileState {
4
4
  bodyId: string;
5
5
  bodyVersion: string;
@@ -14,7 +14,7 @@ export interface OpticalProfileState {
14
14
  frameRateHz: number;
15
15
  stabilizationMode: string;
16
16
  }
17
- /** Generic approximation evidence; never implies measured calibration. */
17
+ /** Evidence for a generic approximation. It never implies a measured calibration. */
18
18
  export interface GenericOpticalEvidence {
19
19
  kind: "generic-parametric";
20
20
  basis: string;
@@ -31,12 +31,11 @@ export declare function positive(value: unknown, name: string): number;
31
31
  export declare function textValue(value: unknown): string;
32
32
  /** @internal */
33
33
  export declare function choice<T extends string>(value: unknown, choices: readonly T[]): T;
34
- /** @internal Reject holes, duplicates (by consumers), and unbounded work. */
34
+ /** @internal Rejects gaps and unbounded work. Consumers reject duplicates. */
35
35
  export declare function list(value: unknown, maximum?: number): unknown[];
36
- /** Parses a complete exact-state binding, including still/video/output settings. */
36
+ /** Parses a complete exact-state binding, including still, video and output settings. */
37
37
  export declare function parseOpticalProfileState(value: unknown): OpticalProfileState;
38
- /** @internal Exact binding; mismatches fail rather than extrapolate. */
38
+ /** @internal Exact binding. A mismatch fails; it is never extrapolated. */
39
39
  export declare function requireSameState(expected: OpticalProfileState, actual: OpticalProfileState): void;
40
40
  /** @internal */
41
41
  export declare function parseEvidence(value: unknown): GenericOpticalEvidence;
42
- //# sourceMappingURL=profile-contract.d.ts.map
@@ -1,21 +1,24 @@
1
1
  // SPDX-License-Identifier: Apache-2.0
2
2
  /**
3
- * Generic optical state binds one body/lens/version/acquisition/output configuration to explicit
4
- * approximation evidence. These identities do not certify manufacturer calibration.
5
- * Correction/stray-light consumers validate exact state equality before applying declared
6
- * coefficients.
3
+ * Generic optical state. It ties one camera body, lens, version, acquisition setting and output
4
+ * configuration to explicit evidence for the approximation used.
5
+ *
6
+ * These identities do not certify manufacturer calibration. Correction and stray-light code checks
7
+ * that the state matches exactly before it applies any declared coefficients.
7
8
  * @see docs/RELEASE_1_0.md and the corresponding domain guide.
8
9
  */
9
10
  import { InvalidScientificInputError } from "../core/validation.js";
10
11
  import { parseEvidenceList } from "../core/evidence-provenance.js";
12
+ import { InvalidConfigurationError } from "../core/configuration-error.js";
11
13
  /** @internal Strict shared profile parser helpers. */
12
14
  export function record(value, keys) {
13
15
  if (typeof value !== "object" || value === null || Array.isArray(value)) {
14
- throw new InvalidScientificInputError("Expected a profile object.");
16
+ throw new InvalidConfigurationError("Expected a profile object.");
15
17
  }
16
18
  const result = value;
17
- if (Object.keys(result).some((key) => !keys.includes(key))) {
18
- throw new InvalidScientificInputError("Unknown profile field.");
19
+ const unknown = Object.keys(result).find((key) => !keys.includes(key));
20
+ if (unknown !== undefined) {
21
+ throw new InvalidConfigurationError(`Unknown profile field. Unknown field ${JSON.stringify(unknown)}.`);
19
22
  }
20
23
  return result;
21
24
  }
@@ -43,10 +46,10 @@ export function textValue(value) {
43
46
  /** @internal */
44
47
  export function choice(value, choices) {
45
48
  if (!choices.includes(value))
46
- throw new InvalidScientificInputError("Unknown profile enum.");
49
+ throw new InvalidConfigurationError("Unknown profile enum.");
47
50
  return value;
48
51
  }
49
- /** @internal Reject holes, duplicates (by consumers), and unbounded work. */
52
+ /** @internal Rejects gaps and unbounded work. Consumers reject duplicates. */
50
53
  export function list(value, maximum = 4096) {
51
54
  if (!Array.isArray(value) || value.length > maximum ||
52
55
  Array.from({ length: value.length }, (_, index) => index in value).includes(false)) {
@@ -54,7 +57,7 @@ export function list(value, maximum = 4096) {
54
57
  }
55
58
  return value;
56
59
  }
57
- /** Parses a complete exact-state binding, including still/video/output settings. */
60
+ /** Parses a complete exact-state binding, including still, video and output settings. */
58
61
  export function parseOpticalProfileState(value) {
59
62
  const r = record(value, ["bodyId", "bodyVersion", "lensId", "lensVersion", "focalLengthMm",
60
63
  "aperture", "focusDistanceM", "captureMode", "outputWidth", "outputHeight", "frameRateHz", "stabilizationMode"]);
@@ -77,7 +80,7 @@ export function parseOpticalProfileState(value) {
77
80
  stabilizationMode: textValue(r.stabilizationMode)
78
81
  };
79
82
  }
80
- /** @internal Exact binding; mismatches fail rather than extrapolate. */
83
+ /** @internal Exact binding. A mismatch fails; it is never extrapolated. */
81
84
  export function requireSameState(expected, actual) {
82
85
  if (JSON.stringify(parseOpticalProfileState(expected)) !== JSON.stringify(parseOpticalProfileState(actual))) {
83
86
  throw new InvalidScientificInputError("Profile is not applicable to this exact camera/lens state.");