@photivra/engine 2.10.0 → 2.11.1

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 (115) hide show
  1. package/CHANGELOG.md +139 -1
  2. package/CITATION.cff +1 -1
  3. package/NODE_SUPPORT.md +21 -3
  4. package/README.md +6 -6
  5. package/SECURITY.md +1 -1
  6. package/dist/core/portable-math.d.ts +6 -0
  7. package/dist/core/portable-math.js +39 -0
  8. package/dist/core/portable-math.js.map +1 -1
  9. package/dist/core/version.d.ts +1 -1
  10. package/dist/core/version.js +1 -1
  11. package/dist/core/version.js.map +1 -1
  12. package/dist/facade/chart-material-layers.d.ts +115 -0
  13. package/dist/facade/chart-material-layers.js +224 -0
  14. package/dist/facade/chart-material-layers.js.map +1 -0
  15. package/dist/facade/chart-radiance-batch.d.ts +8 -2
  16. package/dist/facade/chart-radiance-batch.js +11 -4
  17. package/dist/facade/chart-radiance-batch.js.map +1 -1
  18. package/dist/facade/chart-scenes.d.ts +134 -0
  19. package/dist/facade/chart-scenes.js +32 -22
  20. package/dist/facade/chart-scenes.js.map +1 -1
  21. package/dist/facade/diffraction-provider.d.ts +8 -2
  22. package/dist/facade/diffraction-provider.js +71 -2
  23. package/dist/facade/diffraction-provider.js.map +1 -1
  24. package/dist/facade/display-view-gpu-session.d.ts +18 -0
  25. package/dist/facade/display-view-gpu-session.js +280 -0
  26. package/dist/facade/display-view-gpu-session.js.map +1 -0
  27. package/dist/facade/display-view-gpu.d.ts +146 -0
  28. package/dist/facade/display-view-gpu.js +59 -0
  29. package/dist/facade/display-view-gpu.js.map +1 -0
  30. package/dist/facade/display-view.d.ts +48 -1
  31. package/dist/facade/display-view.js +7 -7
  32. package/dist/facade/display-view.js.map +1 -1
  33. package/dist/facade/expected-signal-setup.d.ts +5 -0
  34. package/dist/facade/expected-signal-setup.js +16 -0
  35. package/dist/facade/expected-signal-setup.js.map +1 -1
  36. package/dist/facade/expected-signal.d.ts +48 -3
  37. package/dist/facade/expected-signal.js +8 -0
  38. package/dist/facade/expected-signal.js.map +1 -1
  39. package/dist/facade/scene-radiance.d.ts +4 -2
  40. package/dist/facade/scene-radiance.js +7 -4
  41. package/dist/facade/scene-radiance.js.map +1 -1
  42. package/dist/facade/simulate-capture.d.ts +32 -5
  43. package/dist/facade/simulate-capture.js +148 -24
  44. package/dist/facade/simulate-capture.js.map +1 -1
  45. package/dist/facade/simulate-display-view.d.ts +31 -3
  46. package/dist/facade/simulate-display-view.js +72 -12
  47. package/dist/facade/simulate-display-view.js.map +1 -1
  48. package/dist/gpu/chart-composite-gpu.d.ts +119 -0
  49. package/dist/gpu/chart-composite-gpu.js +572 -0
  50. package/dist/gpu/chart-composite-gpu.js.map +1 -0
  51. package/dist/gpu/chart-radiance-gpu.d.ts +6 -6
  52. package/dist/gpu/chart-radiance-gpu.js +9 -11
  53. package/dist/gpu/chart-radiance-gpu.js.map +1 -1
  54. package/dist/gpu/display-view-chart-material-module.d.ts +10 -0
  55. package/dist/gpu/display-view-chart-material-module.js +58 -0
  56. package/dist/gpu/display-view-chart-material-module.js.map +1 -0
  57. package/dist/gpu/display-view-composite-material-module.d.ts +68 -0
  58. package/dist/gpu/display-view-composite-material-module.js +248 -0
  59. package/dist/gpu/display-view-composite-material-module.js.map +1 -0
  60. package/dist/gpu/display-view-quality-gpu.d.ts +185 -0
  61. package/dist/gpu/display-view-quality-gpu.js +1000 -0
  62. package/dist/gpu/display-view-quality-gpu.js.map +1 -0
  63. package/dist/gpu/display-view-speed-gpu.d.ts +156 -0
  64. package/dist/gpu/display-view-speed-gpu.js +524 -0
  65. package/dist/gpu/display-view-speed-gpu.js.map +1 -0
  66. package/dist/gpu/image-kernel-accelerator.d.ts +23 -4
  67. package/dist/gpu/image-kernel-accelerator.js +58 -10
  68. package/dist/gpu/image-kernel-accelerator.js.map +1 -1
  69. package/dist/gpu/image-kernel-execution.d.ts +55 -3
  70. package/dist/gpu/image-kernel-execution.js.map +1 -1
  71. package/dist/gpu/sensor-stage-gpu.d.ts +11 -0
  72. package/dist/gpu/sensor-stage-gpu.js +42 -13
  73. package/dist/gpu/sensor-stage-gpu.js.map +1 -1
  74. package/dist/gpu/webgpu-runtime.d.ts +4 -2
  75. package/dist/gpu/webgpu-runtime.js +13 -4
  76. package/dist/gpu/webgpu-runtime.js.map +1 -1
  77. package/dist/gpu/webgpu-switch.d.ts +4 -0
  78. package/dist/gpu/webgpu-switch.js +29 -0
  79. package/dist/gpu/webgpu-switch.js.map +1 -0
  80. package/dist/gpu/wgsl-chart-composite-kernel.d.ts +52 -0
  81. package/dist/gpu/wgsl-chart-composite-kernel.js +515 -0
  82. package/dist/gpu/wgsl-chart-composite-kernel.js.map +1 -0
  83. package/dist/gpu/wgsl-chart-kernel.d.ts +11 -9
  84. package/dist/gpu/wgsl-chart-kernel.js +33 -27
  85. package/dist/gpu/wgsl-chart-kernel.js.map +1 -1
  86. package/dist/gpu/wgsl-display-view-quality-kernel.d.ts +95 -0
  87. package/dist/gpu/wgsl-display-view-quality-kernel.js +769 -0
  88. package/dist/gpu/wgsl-display-view-quality-kernel.js.map +1 -0
  89. package/dist/gpu/wgsl-display-view-speed-kernel.d.ts +75 -0
  90. package/dist/gpu/wgsl-display-view-speed-kernel.js +386 -0
  91. package/dist/gpu/wgsl-display-view-speed-kernel.js.map +1 -0
  92. package/dist/gpu/wgsl-sensor-kernel.d.ts +28 -9
  93. package/dist/gpu/wgsl-sensor-kernel.js +94 -50
  94. package/dist/gpu/wgsl-sensor-kernel.js.map +1 -1
  95. package/dist/index.d.ts +4 -1
  96. package/dist/index.js +2 -0
  97. package/dist/index.js.map +1 -1
  98. package/dist/optics/defocus-disc-kernel.d.ts +61 -0
  99. package/dist/optics/defocus-disc-kernel.js +191 -0
  100. package/dist/optics/defocus-disc-kernel.js.map +1 -0
  101. package/docs/API_REFERENCE.md +45 -1
  102. package/docs/QUICK_START.md +102 -3
  103. package/docs/USAGE.md +52 -2
  104. package/docs/api/core-version.md +1 -1
  105. package/docs/api/exports.json +117 -2
  106. package/docs/api/facade-chart-material-layers.md +137 -0
  107. package/docs/api/facade-chart-radiance-batch.md +7 -2
  108. package/docs/api/facade-display-view-gpu.md +94 -0
  109. package/docs/api/facade-scene-radiance.md +3 -2
  110. package/docs/api/facade-simulate-capture.md +23 -6
  111. package/docs/api/facade-simulate-display-view.md +17 -2
  112. package/docs/api/gpu-image-kernel-accelerator.md +10 -3
  113. package/docs/api/gpu-image-kernel-execution.md +71 -4
  114. package/docs/api/gpu-webgpu-switch.md +23 -0
  115. package/package.json +3 -1
@@ -1 +1 @@
1
- {"version":3,"file":"scene-radiance.js","sourceRoot":"","sources":["../../src/facade/scene-radiance.ts"],"names":[],"mappings":"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","sourcesContent":["// SPDX-License-Identifier: Apache-2.0\n\n/**\n * Turns a facade scene and an illuminant into a scene radiance provider for the existing native\n * environment RAW contract (`NativeEnvironmentRawProvider.evaluateRadiance` and, for pupil sampling,\n * `evaluateApertureRadiance`). The scene is an engine chart, a caller reflectance function or a caller\n * radiance function.\n *\n * Geometry: one plane perpendicular to the optical axis at `distanceM` in front of the camera. A query's\n * outgoing direction o (scene toward camera, see docs/SENSOR_ENVIRONMENT_QUERY.md) gives the look\n * direction l = -o; the plane point is l·distanceM/l.z. With a pupil ray, the plane point is the ray from\n * its lens origin to z = distanceM.\n *\n * Radiometry: a Lambertian reflector of reflectance ρ(λ) under irradiance E(λ) has radiance\n * L(λ) = ρ(λ)·E(λ)/π (W·m⁻²·sr⁻¹·nm⁻¹). The illuminant spectral shape S(λ) is scaled so that the\n * plane illuminance is E_v = K_m ∫ E(λ) V(λ) dλ with K_m = 683 lm/W (CIE photometric definition) and\n * V(λ) = ȳ(λ) from the engine's analytic CIE 1931 fit. The light is uniform\n * over the plane, with no shadows. Inter-reflection, gloss and fluorescence are not modelled.\n * @see docs/QUICK_START.md\n */\n\nimport { InvalidConfigurationError } from \"../core/configuration-error.js\";\nimport { requireInputObject } from \"../core/record-validation.js\";\nimport { estimateCie1931ColorMatchingFunctions, prepareColorimetricSpectrum, type ColorimetricSpectrum,\n type PreparedColorimetricSpectrum } from \"../color/color-matching-functions.js\";\nimport { createCieIlluminantASpectrum, createCieDaylightSpectrum, createPlanckianSpectrum, createPortableCieDaylightSpectrum, createPortableCieIlluminantASpectrum,\n createPortablePlanckianSpectrum, type CieDaylightBasis } from \"../color/illuminants.js\";\nimport type { SceneRadianceEvaluationRequest, SceneRadianceEvaluationResult } from \"../schema/scene-radiance.js\";\nimport type { EvidenceProvenance } from \"../core/evidence-provenance.js\";\nimport type { SensorApertureRay } from \"../optics/sensor-aperture-rays.js\";\nimport { resolveChartMaterial, resolveChartScene, type ChartReflectance, type ChartScene, type ResolvedChartScene } from \"./chart-scenes.js\";\n\n/** CIE maximum luminous efficacy for photopic vision, lm/W. */\nexport const PHOTOPIC_MAXIMUM_LUMINOUS_EFFICACY_LM_PER_W = 683;\n/** Wavelength range of every facade spectrum and of the facade sensor quadrature, nm. */\nexport const FACADE_SPECTRAL_RANGE_NANOMETERS = Object.freeze({ minimum: 380, maximum: 780 });\n\n/**\n * Illuminant choices. CIE D65 is not bundled: its S0/S1/S2 basis tables must come from the caller\n * (`daylight`). `planckian` is Planck's law; `cie-a` is CIE illuminant A from its defining formula.\n */\nexport type CaptureIlluminant =\n | \"cie-a\"\n | { kind: \"planckian\"; temperatureKelvin: number }\n | { kind: \"cie-a\" }\n | { kind: \"daylight\"; correlatedColorTemperatureKelvin: number; basis: CieDaylightBasis }\n | { kind: \"spectrum\"; spectrum: ColorimetricSpectrum; label?: string };\n\nexport interface ResolvedCaptureIlluminant {\n /** Short public description, for example \"planckian-6500K\". */\n id: string;\n description: string;\n /** Relative spectral shape (arbitrary scale) over at least 380-780 nm. */\n shape: PreparedColorimetricSpectrum;\n /** Original spectrum, for colorimetric white-balance calculations. */\n spectrum: ColorimetricSpectrum;\n}\n\nexport function resolveCaptureIlluminant(value: CaptureIlluminant): ResolvedCaptureIlluminant {\n return resolveIlluminant(value, CAPTURE_SPECTRA);\n}\n/**\n * The spectrum constructors of the engine's own illuminant formulas: the capture's, or the portable ones (the display view).\n * They are passed in rather than chosen inside {@link resolveIlluminant}, so a bundle that only captures does not contain the\n * portable ones.\n */\ninterface IlluminantSpectra { planckian: typeof createPlanckianSpectrum; cieA: typeof createCieIlluminantASpectrum; daylight: typeof createCieDaylightSpectrum }\nconst CAPTURE_SPECTRA: IlluminantSpectra = { planckian: createPlanckianSpectrum, cieA: createCieIlluminantASpectrum, daylight: createCieDaylightSpectrum };\n/**\n * Internal (not exported from the package): {@link resolveCaptureIlluminant} with the engine's own formulas (Planckian,\n * CIE A, daylight locus) evaluated with the portable power and e^x − 1 (`portablePow`, `portableExpm1`), so the spectrum\n * has the same bits in every JavaScript engine. The display view uses it; captures keep {@link resolveCaptureIlluminant}.\n * A caller spectrum is the caller's own.\n */\nexport function resolvePortableCaptureIlluminant(value: CaptureIlluminant): ResolvedCaptureIlluminant {\n return resolveIlluminant(value, { planckian: createPortablePlanckianSpectrum, cieA: createPortableCieIlluminantASpectrum, daylight: createPortableCieDaylightSpectrum });\n}\nfunction resolveIlluminant(value: CaptureIlluminant, spectra: IlluminantSpectra): ResolvedCaptureIlluminant {\n if (value === \"cie-a\") return resolveIlluminant({ kind: \"cie-a\" }, spectra);\n requireInputObject(value, \"illuminant\");\n const record = value as unknown as Record<string, unknown>;\n const allowed: Record<string, readonly string[]> = { planckian: [\"kind\", \"temperatureKelvin\"], \"cie-a\": [\"kind\"],\n daylight: [\"kind\", \"correlatedColorTemperatureKelvin\", \"basis\"], spectrum: [\"kind\", \"spectrum\", \"label\"] };\n const keys = typeof record.kind === \"string\" ? allowed[record.kind] : undefined;\n if (!keys) throw new InvalidConfigurationError(\"Unknown illuminant kind.\");\n for (const key of Object.keys(record)) if (!keys.includes(key)) throw new InvalidConfigurationError(\"Unknown illuminant field: \" + key + \".\");\n let spectrum: ColorimetricSpectrum, id: string, description: string;\n try {\n switch (value.kind) {\n case \"planckian\": {\n const t = value.temperatureKelvin;\n if (typeof t !== \"number\" || !Number.isFinite(t) || t < 1000 || t > 25000) throw new InvalidConfigurationError(\"Planckian temperature must be 1000-25000 K.\");\n spectrum = spectra.planckian({ temperatureKelvin: t, wavelengthRangeNanometers: { ...FACADE_SPECTRAL_RANGE_NANOMETERS } });\n id = \"planckian-\" + t + \"K\"; description = \"Planck blackbody spectrum at \" + t + \" K (Planck's law).\";\n break;\n }\n case \"cie-a\":\n spectrum = spectra.cieA(); id = \"cie-a\"; description = \"CIE standard illuminant A from its defining formula: Planck's law with c2 = 1.435e-2 m·K and T = 2848 K, 100 at 560 nm.\";\n break;\n case \"daylight\":\n spectrum = spectra.daylight({ correlatedColorTemperatureKelvin: value.correlatedColorTemperatureKelvin, coefficientRounding: \"cie-three-decimals\", basis: value.basis });\n id = \"cie-daylight-\" + value.correlatedColorTemperatureKelvin + \"K\"; description = \"CIE daylight from the caller's S0/S1/S2 basis (\" + value.basis.datasetId + \").\";\n break;\n case \"spectrum\":\n spectrum = value.spectrum; id = \"caller-spectrum\";\n description = \"Caller illuminant spectrum\" + (typeof value.label === \"string\" ? \" (\" + value.label + \")\" : \"\") + \".\";\n break;\n }\n } catch (error) {\n if (error instanceof InvalidConfigurationError) throw error;\n throw new InvalidConfigurationError(\"Invalid illuminant: \" + (error instanceof Error ? error.message : \"invalid\"));\n }\n let shape: PreparedColorimetricSpectrum;\n try { shape = prepareColorimetricSpectrum(spectrum, \"illuminant\"); } catch (error) {\n throw new InvalidConfigurationError(\"Invalid illuminant spectrum: \" + (error instanceof Error ? error.message : \"invalid\"));\n }\n const range = shape.wavelengthRangeNanometers;\n if (range.minimum > FACADE_SPECTRAL_RANGE_NANOMETERS.minimum || range.maximum < FACADE_SPECTRAL_RANGE_NANOMETERS.maximum)\n throw new InvalidConfigurationError(\"The illuminant spectrum must cover 380-780 nm.\");\n for (let nm = FACADE_SPECTRAL_RANGE_NANOMETERS.minimum; nm <= FACADE_SPECTRAL_RANGE_NANOMETERS.maximum; nm += 1) {\n const s = shape.evaluate(nm);\n if (!(s >= 0)) throw new InvalidConfigurationError(\"The illuminant spectrum must be non-negative over 380-780 nm.\");\n }\n return Object.freeze({ id, description, shape, spectrum });\n}\n\n/**\n * Factor k such that k·S(λ) (W·m⁻²·nm⁻¹) gives `illuminanceLux` on the plane: E_v = 683 ∫ k S ȳ dλ,\n * integrated with the 1 nm trapezoid rule over 380-780 nm (ȳ outside this range is below 4e-5 of its peak).\n */\nexport function calculateIlluminantIrradianceScale(shape: PreparedColorimetricSpectrum, illuminanceLux: number): number {\n if (typeof shape !== \"object\" || shape === null || typeof shape.evaluate !== \"function\") throw new InvalidConfigurationError(\"A prepared illuminant spectrum is required.\");\n if (typeof illuminanceLux !== \"number\" || !Number.isFinite(illuminanceLux) || illuminanceLux <= 0 || illuminanceLux > 1e7)\n throw new InvalidConfigurationError(\"Illuminance must be a positive number of lux up to 1e7.\");\n let sum = 0;\n for (let nm = FACADE_SPECTRAL_RANGE_NANOMETERS.minimum; nm <= FACADE_SPECTRAL_RANGE_NANOMETERS.maximum; nm++) {\n const w = nm === FACADE_SPECTRAL_RANGE_NANOMETERS.minimum || nm === FACADE_SPECTRAL_RANGE_NANOMETERS.maximum ? 0.5 : 1;\n sum += w * shape.evaluate(nm) * estimateCie1931ColorMatchingFunctions(nm).y;\n }\n if (!(sum > 0)) throw new InvalidConfigurationError(\"The illuminant has no luminous power.\");\n return illuminanceLux / (PHOTOPIC_MAXIMUM_LUMINOUS_EFFICACY_LM_PER_W * sum);\n}\n\n/**\n * A point of the scene plane passed to caller scene functions: a new object for every call, which the engine does not read\n * after the call (not frozen: freezing cost about 40 % of a chart lookup).\n */\nexport interface ScenePlanePoint {\n /** Metres on the plane, from the optical axis: +x right, +y up (as seen from the camera). */\n xM: number;\n yM: number;\n /** The same point in frame units (u = ±1 at the left/right frame edges, v up on the same scale). */\n u: number;\n v: number;\n wavelengthNanometers: number;\n /**\n * 2.3, only with a fixed-size chart (`chartSize`): the point in chart-local frame units (±1 at the chart's\n * left/right edges, v up on the same scale, ±chart height/width at its top/bottom). The function is then\n * called only for points on the chart; the surround is the placement's surround reflectance.\n */\n chartU?: number;\n chartV?: number;\n}\n/** Caller Lambertian reflectance (in [0, 1]) lit by the facade illuminant. */\nexport interface CallerReflectanceScene { kind: \"reflectance-function\"; sceneId: string; evaluate(point: Readonly<ScenePlanePoint>): number }\n/** Caller absolute spectral radiance in W·m⁻²·sr⁻¹·nm⁻¹; the facade illuminant is not used. */\nexport interface CallerRadianceScene { kind: \"radiance-function\"; sceneId: string; evaluate(point: Readonly<ScenePlanePoint>): number }\n/** 2.7: a scene-plane point without a wavelength, passed to a material scene's `materialAt`. */\nexport type SceneMaterialPoint = Omit<ScenePlanePoint, \"wavelengthNanometers\">;\n/**\n * 2.7 (#386): a piecewise-constant caller scene, lit by the facade illuminant like a reflectance function. `materials` are\n * reflectances as a chart's patches take them (a neutral number in [0, 1] or a reflectance spectrum covering 380–780 nm, at\n * most {@link CALLER_MATERIAL_SCENE_MAX_MATERIALS}); `materialAt` returns the index of the material at a plane point (an\n * integer from 0 to materials.length − 1). The radiance at a point is that material's, exactly as for a reflectance function\n * returning its reflectance, but renderers can tabulate each material once: the display view then takes the chart path.\n */\nexport interface CallerMaterialScene {\n kind: \"material-function\";\n sceneId: string;\n materials: readonly ChartReflectance[];\n materialAt(point: Readonly<SceneMaterialPoint>): number;\n}\n/** Most materials a {@link CallerMaterialScene} may list. */\nexport const CALLER_MATERIAL_SCENE_MAX_MATERIALS = 65_536;\n/** Internal: a validated material scene with its materials prepared (and the caller inputs, for the scene digest). */\nexport interface ResolvedCallerMaterialScene {\n kind: \"material-function\";\n sceneId: string;\n materials: ResolvedChartScene[\"materials\"];\n materialInputs: readonly unknown[];\n materialAt(point: Readonly<SceneMaterialPoint>): number;\n}\n/** Internal: a validated caller scene. */\nexport type ResolvedCallerScene = CallerReflectanceScene | CallerRadianceScene | ResolvedCallerMaterialScene;\n\nexport interface PlanarSceneGeometry {\n distanceM: number;\n /** Metres per frame unit on the plane (half the framed width). */\n metresPerFrameUnit: number;\n /**\n * 2.3, opt-in fixed-size chart: the chart is `widthM` × `heightM` on the plane, centred on the optical axis;\n * outside it the plane is a neutral Lambertian surround of `surroundReflectance`, lit by the same illuminant.\n * A chart preset is then resolved in its own frame (aspect heightM / widthM). Without it the chart fills the frame.\n */\n chart?: { widthM: number; heightM: number; surroundReflectance: number };\n}\n\nexport interface PlanarSceneRadianceProvider {\n sceneId: string;\n providerProfileId: string;\n evaluateRadiance(request: Readonly<SceneRadianceEvaluationRequest>): SceneRadianceEvaluationResult;\n evaluateApertureRadiance(request: Readonly<SceneRadianceEvaluationRequest>, ray: Readonly<SensorApertureRay>): SceneRadianceEvaluationResult;\n /** Spectral radiance at a plane point (frame units), the same value the callbacks return. */\n radianceAt(u: number, v: number, wavelengthNanometers: number): number;\n /**\n * 2.3, chart scenes only: the chart material at a plane point (frame units), or `materials.length` for the\n * surround of a fixed-size chart; `materialRadiance` gives that material's spectral radiance, the same value\n * `radianceAt` returns at its points.\n */\n chartMaterialAt?(u: number, v: number): number;\n materialRadiance?(material: number, wavelengthNanometers: number): number;\n}\n\n/**\n * Internal (#394, not exported from the package): per provider of a chart preset or caller material scene, the material its\n * `evaluateRadiance` reads for an environment-direction query with a given outgoing direction (the same plane-point\n * arithmetic), or undefined where `evaluateRadiance` would throw. Its radiance is `materialRadiance(material, wavelength)`.\n */\nconst MATERIAL_OF_DIRECTION = new WeakMap<PlanarSceneRadianceProvider, (direction: Readonly<{ x: number; y: number; z: number }>) => number | undefined>();\n\n/** Internal (#394): the material lookup of a provider built by {@link buildPlanarSceneRadianceProvider}, if it has one. */\nexport function planarProviderMaterialOfDirection(provider: PlanarSceneRadianceProvider):\n ((direction: Readonly<{ x: number; y: number; z: number }>) => number | undefined) | undefined {\n return MATERIAL_OF_DIRECTION.get(provider);\n}\n\nconst UNCERTAINTY = Object.freeze({ kind: \"not-quantified\" as const, limitation: \"Analytic planar Lambertian scene; no measured scene, BRDF or illumination.\" });\n\n/** Most distinct wavelengths {@link tabulatedSpectrum} keeps; later ones are evaluated on every call. */\nconst TABULATED_SPECTRUM_MAX_ENTRIES = 4096;\n\n/**\n * Internal (#385): `spectrum.evaluate` remembered per distinct wavelength. A prepared spectrum is a pure function of the\n * wavelength, so the table returns the same double the call would; renderers ask for the same few spectral nodes millions\n * of times, and the illuminant's formula (two transcendental evaluations) was about 30 % of a caller-scene display view.\n */\nexport function tabulatedSpectrum(spectrum: Readonly<PreparedColorimetricSpectrum>): (wavelengthNanometers: number) => number {\n const table = new Map<number, number>();\n return (nm) => {\n let value = table.get(nm);\n if (value === undefined) {\n value = spectrum.evaluate(nm);\n if (table.size < TABULATED_SPECTRUM_MAX_ENTRIES) table.set(nm, value);\n }\n return value;\n };\n}\n\n/**\n * Wraps a chart or caller scene as a provider for the native environment RAW task. `irradianceScale` is\n * from {@link calculateIlluminantIrradianceScale}; caller radiance scenes ignore the illuminant.\n */\nexport function buildPlanarSceneRadianceProvider(input: {\n scene: ResolvedChartScene | ResolvedCallerScene;\n sceneId: string;\n providerProfileId: string;\n illuminant: ResolvedCaptureIlluminant;\n irradianceScale: number;\n geometry: PlanarSceneGeometry;\n evidence: readonly EvidenceProvenance[];\n limitations: readonly string[];\n}): PlanarSceneRadianceProvider {\n const { scene, illuminant, irradianceScale, geometry } = input;\n const scale = geometry.metresPerFrameUnit, distance = geometry.distanceM, sceneId = input.sceneId, providerProfileId = input.providerProfileId;\n const evidence = input.evidence, limitations = input.limitations;\n const caller = \"kind\" in scene ? scene : undefined, chart = caller ? undefined : scene as ResolvedChartScene;\n const materialScene = caller?.kind === \"material-function\" ? caller : undefined, materials = chart ? chart.materials : materialScene?.materials;\n const placed = geometry.chart, half = placed ? placed.widthM / 2 : 0, chartAspect = placed ? placed.heightM / placed.widthM : 0;\n const shapeAt = tabulatedSpectrum(illuminant.shape);\n /** A material scene's material at a frame point: the caller's index, or `materials.length` for a fixed-size chart's surround. */\n function callerMaterialAt(u: number, v: number): number {\n const xM = u * scale, yM = v * scale;\n let point: SceneMaterialPoint;\n if (placed) {\n const cu = xM / half, cv = yM / half;\n if (!(Math.abs(cu) <= 1 && Math.abs(cv) <= chartAspect)) return materialScene!.materials.length;\n point = { xM, yM, u, v, chartU: cu, chartV: cv };\n } else point = { xM, yM, u, v };\n const index = materialScene!.materialAt(point);\n if (!Number.isInteger(index) || index < 0 || index >= materialScene!.materials.length) throw new InvalidConfigurationError(\"Scene materialAt must return an index into its materials.\");\n return index;\n }\n function radianceAt(u: number, v: number, nm: number): number {\n if (materialScene) return materialRadianceOf(callerMaterialAt(u, v), nm);\n if (placed) {\n // Fixed-size chart (2.3): chart-local frame units from the plane point in metres.\n const xM = u * scale, yM = v * scale, cu = xM / half, cv = yM / half;\n if (!(Math.abs(cu) <= 1 && Math.abs(cv) <= chartAspect)) return placed.surroundReflectance * irradianceScale * shapeAt(nm) / Math.PI;\n if (chart) return chart.reflectanceAt(cu, cv, nm) * irradianceScale * shapeAt(nm) / Math.PI;\n return callerValue({ xM, yM, u, v, wavelengthNanometers: nm, chartU: cu, chartV: cv }, nm);\n }\n if (chart) return chart.reflectanceAt(u, v, nm) * irradianceScale * shapeAt(nm) / Math.PI;\n return callerValue({ xM: u * scale, yM: v * scale, u, v, wavelengthNanometers: nm }, nm);\n }\n function callerValue(point: Readonly<ScenePlanePoint>, nm: number): number {\n const value = (caller as CallerReflectanceScene | CallerRadianceScene).evaluate(point);\n if (caller!.kind === \"reflectance-function\") {\n if (typeof value !== \"number\" || !Number.isFinite(value) || value < 0 || value > 1) throw new InvalidConfigurationError(\"Scene reflectance function must return a value in [0, 1].\");\n return value * irradianceScale * shapeAt(nm) / Math.PI;\n }\n if (typeof value !== \"number\" || !Number.isFinite(value) || value < 0) throw new InvalidConfigurationError(\"Scene radiance function must return a finite non-negative radiance.\");\n return value;\n }\n function result(request: Readonly<SceneRadianceEvaluationRequest>, radiance: number): SceneRadianceEvaluationResult {\n return { schemaVersion: \"0.1.0\", sampleId: request.sampleId, sceneId, providerProfileId, wavelengthNanometers: request.wavelengthNanometers,\n wavelengthBasis: request.wavelengthBasis as SceneRadianceEvaluationResult[\"wavelengthBasis\"], quantity: \"outgoing-spectral-radiance\", unit: \"W/m^2/sr/nm\",\n spectralRadianceWattsPerSquareMeterSteradianNanometer: radiance, scientificStatus: \"approximation\", uncertainty: UNCERTAINTY, evidence, limitations };\n }\n /** Spectral radiance of material `material` (`materials.length`: a fixed-size chart's surround), in the chart's expression order. */\n function materialRadianceOf(material: number, nm: number): number {\n const m = materials![material];\n let value: number;\n if (m === undefined) value = placed ? placed.surroundReflectance : NaN;\n else if (m.kind === \"neutral\") value = m.reflectance;\n else {\n value = m.spectrum.evaluate(nm);\n if (!(value >= 0 && value <= 1)) throw new InvalidConfigurationError(\"Chart reflectance spectrum left [0, 1].\");\n }\n if (!(value >= 0)) throw new InvalidConfigurationError(\"Unknown chart material.\");\n return value * irradianceScale * shapeAt(nm) / Math.PI;\n }\n function chartMaterialAt(u: number, v: number): number {\n if (!placed) return chart!.materialAt(u, v);\n const cu = u * scale / half, cv = v * scale / half;\n return Math.abs(cu) <= 1 && Math.abs(cv) <= chartAspect ? chart!.materialAt(cu, cv) : chart!.materials.length;\n }\n const chartAccess = chart ? { chartMaterialAt, materialRadiance: materialRadianceOf } :\n materialScene ? { chartMaterialAt: callerMaterialAt, materialRadiance: materialRadianceOf } : {};\n // #394: evaluateRadiance's own plane-point arithmetic; radianceAt is then materialRadianceOf(material, nm) for both scene forms.\n const materialAtPoint = chart ? chartMaterialAt : materialScene ? callerMaterialAt : undefined;\n const materialOfDirection = materialAtPoint === undefined ? undefined : (o: Readonly<{ x: number; y: number; z: number }>): number | undefined => {\n const lz = -o.z;\n if (!(lz > 0)) return undefined;\n const t = distance / lz;\n return materialAtPoint(-o.x * t / scale, -o.y * t / scale);\n };\n const provider: PlanarSceneRadianceProvider = {\n sceneId, providerProfileId, radianceAt, ...chartAccess,\n evaluateRadiance(request): SceneRadianceEvaluationResult {\n const target = request.target;\n if (target.kind !== \"environment-direction\") throw new InvalidConfigurationError(\"Planar scene provider needs environment-direction queries.\");\n const o = target.outgoingDirectionUnitVector, lz = -o.z;\n if (!(lz > 0)) throw new InvalidConfigurationError(\"Planar scene query does not point toward the scene plane.\");\n const t = distance / lz;\n return result(request, radianceAt(-o.x * t / scale, -o.y * t / scale, request.wavelengthNanometers));\n },\n evaluateApertureRadiance(request, ray): SceneRadianceEvaluationResult {\n const d = ray.directionUnitVector, origin = ray.originM;\n if (!(d.z > 0)) throw new InvalidConfigurationError(\"Planar scene pupil ray does not point toward the scene plane.\");\n const t = (distance - origin.z) / d.z;\n return result(request, radianceAt((origin.x + d.x * t) / scale, (origin.y + d.y * t) / scale, request.wavelengthNanometers));\n }\n };\n if (materialOfDirection) MATERIAL_OF_DIRECTION.set(provider, materialOfDirection);\n return provider;\n}\n\n/** 2.3: a chart's physical size on the scene plane (`simulateCapture` `chartSize`, `createPlanarSceneRadianceProvider` `chartSize`). */\nexport interface ChartSizeOption {\n /** Chart width in metres, (0, 10 000]. */\n widthM: number;\n /** Chart height in metres. Default: widthM × the frame aspect (height / width), so the chart has the frame's shape. */\n heightM?: number;\n /** Neutral reflectance of the plane around the chart, lit by the same illuminant. Default 0.18. */\n surroundReflectance?: number;\n}\n/** Default surround of a fixed-size chart: an 18 % grey plane. */\nexport const CHART_SIZE_DEFAULT_SURROUND_REFLECTANCE = 0.18;\n/** Internal: validates a chart size and fills its defaults; `defaulted` names the fields taken from defaults. */\nexport function resolveChartSizeOption(value: unknown, frameAspect: number): { widthM: number; heightM: number; surroundReflectance: number; defaulted: (\"heightM\" | \"surroundReflectance\")[] } {\n requireInputObject(value, \"chartSize\");\n const record = value as Record<string, unknown>;\n for (const key of Object.keys(record)) if (![\"widthM\", \"heightM\", \"surroundReflectance\"].includes(key)) throw new InvalidConfigurationError(\"Unknown chartSize field: \" + key + \".\");\n const size = (x: unknown, name: string): number => {\n if (typeof x !== \"number\" || !Number.isFinite(x) || x <= 0 || x > 10_000) throw new InvalidConfigurationError(\"chartSize.\" + name + \" must be a positive number of metres up to 10000.\");\n return x;\n };\n const defaulted: (\"heightM\" | \"surroundReflectance\")[] = [];\n const widthM = size(record.widthM, \"widthM\");\n const heightM = record.heightM === undefined ? (defaulted.push(\"heightM\"), widthM * frameAspect) : size(record.heightM, \"heightM\");\n const surround = record.surroundReflectance === undefined ? (defaulted.push(\"surroundReflectance\"), CHART_SIZE_DEFAULT_SURROUND_REFLECTANCE) : record.surroundReflectance;\n if (typeof surround !== \"number\" || !Number.isFinite(surround) || surround < 0 || surround > 1) throw new InvalidConfigurationError(\"chartSize.surroundReflectance must be a reflectance in [0, 1].\");\n return { widthM, heightM, surroundReflectance: surround, defaulted };\n}\n\n/**\n * Public scene-preset provider. Places an engine chart (or a caller reflectance or radiance function) on\n * a plane `distanceM` in front of the camera and `framedWidthM` wide (frame units u = ±1 at its edges),\n * lit by `illuminant` at `illuminanceLux`. The returned `evaluateRadiance` and `evaluateApertureRadiance`\n * follow the native environment RAW provider contract. They answer requests for scene `sceneId` and\n * provider `providerProfileId`.\n */\nexport function createPlanarSceneRadianceProvider(input: {\n scene: ChartScene | CallerReflectanceScene | CallerRadianceScene | CallerMaterialScene;\n illuminant: CaptureIlluminant;\n illuminanceLux: number;\n distanceM: number;\n framedWidthM: number;\n /** Frame height / width. */\n aspect: number;\n sceneId: string;\n providerProfileId: string;\n /**\n * 2.3, opt-in: place the chart at this physical size, centred, instead of filling the frame; the chart preset\n * is resolved with aspect heightM / widthM and the rest of the plane is the surround.\n */\n chartSize?: ChartSizeOption;\n}): PlanarSceneRadianceProvider & { chart: ResolvedChartScene | null } {\n requireInputObject(input, \"createPlanarSceneRadianceProvider input\");\n const keys = [\"scene\", \"illuminant\", \"illuminanceLux\", \"distanceM\", \"framedWidthM\", \"aspect\", \"sceneId\", \"providerProfileId\", \"chartSize\"];\n for (const key of Object.keys(input)) if (!keys.includes(key)) throw new InvalidConfigurationError(\"createPlanarSceneRadianceProvider input has unknown field \\\"\" + key + \"\\\".\");\n for (const key of [\"illuminanceLux\", \"distanceM\", \"framedWidthM\", \"aspect\"] as const) {\n const value = input[key];\n if (typeof value !== \"number\" || !Number.isFinite(value) || value <= 0) throw new InvalidConfigurationError(key + \" must be a positive finite number.\");\n }\n for (const key of [\"sceneId\", \"providerProfileId\"] as const) if (typeof input[key] !== \"string\" || !/^[A-Za-z0-9][A-Za-z0-9._:-]{0,127}$/.test(input[key])) throw new InvalidConfigurationError(key + \" must be a public opaque ID.\");\n requireInputObject(input.scene, \"scene\");\n const caller = \"kind\" in input.scene ? requireCallerScene(input.scene) : undefined;\n const size = input.chartSize === undefined ? undefined : resolveChartSizeOption(input.chartSize, input.aspect);\n const chart = caller ? null : resolveChartScene({ scene: input.scene as ChartScene, aspect: size ? size.heightM / size.widthM : input.aspect });\n const illuminant = resolveCaptureIlluminant(input.illuminant);\n const provider = buildPlanarSceneRadianceProvider({ scene: chart ?? caller!, sceneId: input.sceneId, providerProfileId: input.providerProfileId, illuminant,\n irradianceScale: calculateIlluminantIrradianceScale(illuminant.shape, input.illuminanceLux),\n geometry: { distanceM: input.distanceM, metresPerFrameUnit: input.framedWidthM / 2,\n ...(size ? { chart: { widthM: size.widthM, heightM: size.heightM, surroundReflectance: size.surroundReflectance } } : {}) },\n evidence: [{ sourceOrigin: \"photivra\", sourceReference: \"photivra:planar-scene-provider\", reuseStatus: \"photivra-owned\" }],\n limitations: [\"Planar Lambertian scene under uniform illumination; no shadows, inter-reflection, gloss or fluorescence.\"] });\n return { ...provider, chart };\n}\n\n/** Validates a caller scene record (a function scene as given; a material scene with its materials prepared). */\nexport function requireCallerScene(value: unknown): ResolvedCallerScene {\n requireInputObject(value, \"scene\");\n const record = value as Record<string, unknown>;\n if (record.kind === \"material-function\") {\n for (const key of Object.keys(record)) if (key !== \"kind\" && key !== \"sceneId\" && key !== \"materials\" && key !== \"materialAt\") throw new InvalidConfigurationError(\"Unknown scene field: \" + key + \".\");\n if (typeof record.materialAt !== \"function\" || typeof record.sceneId !== \"string\" || !/^[A-Za-z0-9][A-Za-z0-9._:-]{0,63}$/.test(record.sceneId) ||\n !Array.isArray(record.materials) || record.materials.length < 1 || record.materials.length > CALLER_MATERIAL_SCENE_MAX_MATERIALS)\n throw new InvalidConfigurationError(\"A material scene needs a public sceneId, 1 to \" + CALLER_MATERIAL_SCENE_MAX_MATERIALS + \" materials and a materialAt function.\");\n const inputs = [...record.materials as unknown[]];\n return Object.freeze({ kind: \"material-function\" as const, sceneId: record.sceneId, materialAt: record.materialAt as ResolvedCallerMaterialScene[\"materialAt\"],\n materials: Object.freeze(inputs.map((m, index) => resolveChartMaterial(m, \"scene.materials[\" + index + \"]\"))),\n materialInputs: Object.freeze(inputs.map((m) => (typeof m === \"number\" ? undefined : m))) });\n }\n for (const key of Object.keys(record)) if (key !== \"kind\" && key !== \"sceneId\" && key !== \"evaluate\") throw new InvalidConfigurationError(\"Unknown scene field: \" + key + \".\");\n if ((record.kind !== \"reflectance-function\" && record.kind !== \"radiance-function\") || typeof record.evaluate !== \"function\" ||\n typeof record.sceneId !== \"string\" || !/^[A-Za-z0-9][A-Za-z0-9._:-]{0,63}$/.test(record.sceneId)) throw new InvalidConfigurationError(\"A caller scene needs kind, a public sceneId and an evaluate function.\");\n return record as unknown as CallerReflectanceScene | CallerRadianceScene;\n}\n"]}
1
+ {"version":3,"file":"scene-radiance.js","sourceRoot":"","sources":["../../src/facade/scene-radiance.ts"],"names":[],"mappings":"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","sourcesContent":["// SPDX-License-Identifier: Apache-2.0\n\n/**\n * Turns a facade scene and an illuminant into a scene radiance provider for the existing native\n * environment RAW contract (`NativeEnvironmentRawProvider.evaluateRadiance` and, for pupil sampling,\n * `evaluateApertureRadiance`). The scene is an engine chart, a caller reflectance function or a caller\n * radiance function.\n *\n * Geometry: one plane perpendicular to the optical axis at `distanceM` in front of the camera. A query's\n * outgoing direction o (scene toward camera, see docs/SENSOR_ENVIRONMENT_QUERY.md) gives the look\n * direction l = -o; the plane point is l·distanceM/l.z. With a pupil ray, the plane point is the ray from\n * its lens origin to z = distanceM.\n *\n * Radiometry: a Lambertian reflector of reflectance ρ(λ) under irradiance E(λ) has radiance\n * L(λ) = ρ(λ)·E(λ)/π (W·m⁻²·sr⁻¹·nm⁻¹). The illuminant spectral shape S(λ) is scaled so that the\n * plane illuminance is E_v = K_m ∫ E(λ) V(λ) dλ with K_m = 683 lm/W (CIE photometric definition) and\n * V(λ) = ȳ(λ) from the engine's analytic CIE 1931 fit. The light is uniform\n * over the plane, with no shadows. Inter-reflection, gloss and fluorescence are not modelled.\n * @see docs/QUICK_START.md\n */\n\nimport { InvalidConfigurationError } from \"../core/configuration-error.js\";\nimport { requireInputObject } from \"../core/record-validation.js\";\nimport { estimateCie1931ColorMatchingFunctions, prepareColorimetricSpectrum, type ColorimetricSpectrum,\n type PreparedColorimetricSpectrum } from \"../color/color-matching-functions.js\";\nimport { createCieIlluminantASpectrum, createCieDaylightSpectrum, createPlanckianSpectrum, createPortableCieDaylightSpectrum, createPortableCieIlluminantASpectrum,\n createPortablePlanckianSpectrum, type CieDaylightBasis } from \"../color/illuminants.js\";\nimport type { SceneRadianceEvaluationRequest, SceneRadianceEvaluationResult } from \"../schema/scene-radiance.js\";\nimport type { EvidenceProvenance } from \"../core/evidence-provenance.js\";\nimport type { SensorApertureRay } from \"../optics/sensor-aperture-rays.js\";\nimport { resolveChartMaterial, resolveChartScene, type ChartReflectance, type ChartScene, type ResolvedChartScene } from \"./chart-scenes.js\";\nimport { resolveChartMaterialLayers, type ChartMaterialLayerScene } from \"./chart-material-layers.js\";\n\n/** CIE maximum luminous efficacy for photopic vision, lm/W. */\nexport const PHOTOPIC_MAXIMUM_LUMINOUS_EFFICACY_LM_PER_W = 683;\n/** Wavelength range of every facade spectrum and of the facade sensor quadrature, nm. */\nexport const FACADE_SPECTRAL_RANGE_NANOMETERS = Object.freeze({ minimum: 380, maximum: 780 });\n\n/**\n * Illuminant choices. CIE D65 is not bundled: its S0/S1/S2 basis tables must come from the caller\n * (`daylight`). `planckian` is Planck's law; `cie-a` is CIE illuminant A from its defining formula.\n */\nexport type CaptureIlluminant =\n | \"cie-a\"\n | { kind: \"planckian\"; temperatureKelvin: number }\n | { kind: \"cie-a\" }\n | { kind: \"daylight\"; correlatedColorTemperatureKelvin: number; basis: CieDaylightBasis }\n | { kind: \"spectrum\"; spectrum: ColorimetricSpectrum; label?: string };\n\nexport interface ResolvedCaptureIlluminant {\n /** Short public description, for example \"planckian-6500K\". */\n id: string;\n description: string;\n /** Relative spectral shape (arbitrary scale) over at least 380-780 nm. */\n shape: PreparedColorimetricSpectrum;\n /** Original spectrum, for colorimetric white-balance calculations. */\n spectrum: ColorimetricSpectrum;\n}\n\nexport function resolveCaptureIlluminant(value: CaptureIlluminant): ResolvedCaptureIlluminant {\n return resolveIlluminant(value, CAPTURE_SPECTRA);\n}\n/**\n * The spectrum constructors of the engine's own illuminant formulas: the capture's, or the portable ones (the display view).\n * They are passed in rather than chosen inside {@link resolveIlluminant}, so a bundle that only captures does not contain the\n * portable ones.\n */\ninterface IlluminantSpectra { planckian: typeof createPlanckianSpectrum; cieA: typeof createCieIlluminantASpectrum; daylight: typeof createCieDaylightSpectrum }\nconst CAPTURE_SPECTRA: IlluminantSpectra = { planckian: createPlanckianSpectrum, cieA: createCieIlluminantASpectrum, daylight: createCieDaylightSpectrum };\n/**\n * Internal (not exported from the package): {@link resolveCaptureIlluminant} with the engine's own formulas (Planckian,\n * CIE A, daylight locus) evaluated with the portable power and e^x − 1 (`portablePow`, `portableExpm1`), so the spectrum\n * has the same bits in every JavaScript engine. The display view uses it; captures keep {@link resolveCaptureIlluminant}.\n * A caller spectrum is the caller's own.\n */\nexport function resolvePortableCaptureIlluminant(value: CaptureIlluminant): ResolvedCaptureIlluminant {\n return resolveIlluminant(value, { planckian: createPortablePlanckianSpectrum, cieA: createPortableCieIlluminantASpectrum, daylight: createPortableCieDaylightSpectrum });\n}\nfunction resolveIlluminant(value: CaptureIlluminant, spectra: IlluminantSpectra): ResolvedCaptureIlluminant {\n if (value === \"cie-a\") return resolveIlluminant({ kind: \"cie-a\" }, spectra);\n requireInputObject(value, \"illuminant\");\n const record = value as unknown as Record<string, unknown>;\n const allowed: Record<string, readonly string[]> = { planckian: [\"kind\", \"temperatureKelvin\"], \"cie-a\": [\"kind\"],\n daylight: [\"kind\", \"correlatedColorTemperatureKelvin\", \"basis\"], spectrum: [\"kind\", \"spectrum\", \"label\"] };\n const keys = typeof record.kind === \"string\" ? allowed[record.kind] : undefined;\n if (!keys) throw new InvalidConfigurationError(\"Unknown illuminant kind.\");\n for (const key of Object.keys(record)) if (!keys.includes(key)) throw new InvalidConfigurationError(\"Unknown illuminant field: \" + key + \".\");\n let spectrum: ColorimetricSpectrum, id: string, description: string;\n try {\n switch (value.kind) {\n case \"planckian\": {\n const t = value.temperatureKelvin;\n if (typeof t !== \"number\" || !Number.isFinite(t) || t < 1000 || t > 25000) throw new InvalidConfigurationError(\"Planckian temperature must be 1000-25000 K.\");\n spectrum = spectra.planckian({ temperatureKelvin: t, wavelengthRangeNanometers: { ...FACADE_SPECTRAL_RANGE_NANOMETERS } });\n id = \"planckian-\" + t + \"K\"; description = \"Planck blackbody spectrum at \" + t + \" K (Planck's law).\";\n break;\n }\n case \"cie-a\":\n spectrum = spectra.cieA(); id = \"cie-a\"; description = \"CIE standard illuminant A from its defining formula: Planck's law with c2 = 1.435e-2 m·K and T = 2848 K, 100 at 560 nm.\";\n break;\n case \"daylight\":\n spectrum = spectra.daylight({ correlatedColorTemperatureKelvin: value.correlatedColorTemperatureKelvin, coefficientRounding: \"cie-three-decimals\", basis: value.basis });\n id = \"cie-daylight-\" + value.correlatedColorTemperatureKelvin + \"K\"; description = \"CIE daylight from the caller's S0/S1/S2 basis (\" + value.basis.datasetId + \").\";\n break;\n case \"spectrum\":\n spectrum = value.spectrum; id = \"caller-spectrum\";\n description = \"Caller illuminant spectrum\" + (typeof value.label === \"string\" ? \" (\" + value.label + \")\" : \"\") + \".\";\n break;\n }\n } catch (error) {\n if (error instanceof InvalidConfigurationError) throw error;\n throw new InvalidConfigurationError(\"Invalid illuminant: \" + (error instanceof Error ? error.message : \"invalid\"));\n }\n let shape: PreparedColorimetricSpectrum;\n try { shape = prepareColorimetricSpectrum(spectrum, \"illuminant\"); } catch (error) {\n throw new InvalidConfigurationError(\"Invalid illuminant spectrum: \" + (error instanceof Error ? error.message : \"invalid\"));\n }\n const range = shape.wavelengthRangeNanometers;\n if (range.minimum > FACADE_SPECTRAL_RANGE_NANOMETERS.minimum || range.maximum < FACADE_SPECTRAL_RANGE_NANOMETERS.maximum)\n throw new InvalidConfigurationError(\"The illuminant spectrum must cover 380-780 nm.\");\n for (let nm = FACADE_SPECTRAL_RANGE_NANOMETERS.minimum; nm <= FACADE_SPECTRAL_RANGE_NANOMETERS.maximum; nm += 1) {\n const s = shape.evaluate(nm);\n if (!(s >= 0)) throw new InvalidConfigurationError(\"The illuminant spectrum must be non-negative over 380-780 nm.\");\n }\n return Object.freeze({ id, description, shape, spectrum });\n}\n\n/**\n * Factor k such that k·S(λ) (W·m⁻²·nm⁻¹) gives `illuminanceLux` on the plane: E_v = 683 ∫ k S ȳ dλ,\n * integrated with the 1 nm trapezoid rule over 380-780 nm (ȳ outside this range is below 4e-5 of its peak).\n */\nexport function calculateIlluminantIrradianceScale(shape: PreparedColorimetricSpectrum, illuminanceLux: number): number {\n if (typeof shape !== \"object\" || shape === null || typeof shape.evaluate !== \"function\") throw new InvalidConfigurationError(\"A prepared illuminant spectrum is required.\");\n if (typeof illuminanceLux !== \"number\" || !Number.isFinite(illuminanceLux) || illuminanceLux <= 0 || illuminanceLux > 1e7)\n throw new InvalidConfigurationError(\"Illuminance must be a positive number of lux up to 1e7.\");\n let sum = 0;\n for (let nm = FACADE_SPECTRAL_RANGE_NANOMETERS.minimum; nm <= FACADE_SPECTRAL_RANGE_NANOMETERS.maximum; nm++) {\n const w = nm === FACADE_SPECTRAL_RANGE_NANOMETERS.minimum || nm === FACADE_SPECTRAL_RANGE_NANOMETERS.maximum ? 0.5 : 1;\n sum += w * shape.evaluate(nm) * estimateCie1931ColorMatchingFunctions(nm).y;\n }\n if (!(sum > 0)) throw new InvalidConfigurationError(\"The illuminant has no luminous power.\");\n return illuminanceLux / (PHOTOPIC_MAXIMUM_LUMINOUS_EFFICACY_LM_PER_W * sum);\n}\n\n/**\n * A point of the scene plane passed to caller scene functions: a new object for every call, which the engine does not read\n * after the call (not frozen: freezing cost about 40 % of a chart lookup).\n */\nexport interface ScenePlanePoint {\n /** Metres on the plane, from the optical axis: +x right, +y up (as seen from the camera). */\n xM: number;\n yM: number;\n /** The same point in frame units (u = ±1 at the left/right frame edges, v up on the same scale). */\n u: number;\n v: number;\n wavelengthNanometers: number;\n /**\n * 2.3, only with a fixed-size chart (`chartSize`): the point in chart-local frame units (±1 at the chart's\n * left/right edges, v up on the same scale, ±chart height/width at its top/bottom). The function is then\n * called only for points on the chart; the surround is the placement's surround reflectance.\n */\n chartU?: number;\n chartV?: number;\n}\n/** Caller Lambertian reflectance (in [0, 1]) lit by the facade illuminant. */\nexport interface CallerReflectanceScene { kind: \"reflectance-function\"; sceneId: string; evaluate(point: Readonly<ScenePlanePoint>): number }\n/** Caller absolute spectral radiance in W·m⁻²·sr⁻¹·nm⁻¹; the facade illuminant is not used. */\nexport interface CallerRadianceScene { kind: \"radiance-function\"; sceneId: string; evaluate(point: Readonly<ScenePlanePoint>): number }\n/** 2.7: a scene-plane point without a wavelength, passed to a material scene's `materialAt`. */\nexport type SceneMaterialPoint = Omit<ScenePlanePoint, \"wavelengthNanometers\">;\n/**\n * 2.7 (#386): a piecewise-constant caller scene, lit by the facade illuminant like a reflectance function. `materials` are\n * reflectances as a chart's patches take them (a neutral number in [0, 1] or a reflectance spectrum covering 380–780 nm, at\n * most {@link CALLER_MATERIAL_SCENE_MAX_MATERIALS}); `materialAt` returns the index of the material at a plane point (an\n * integer from 0 to materials.length − 1). The radiance at a point is that material's, exactly as for a reflectance function\n * returning its reflectance, but renderers can tabulate each material once: the display view then takes the chart path.\n */\nexport interface CallerMaterialScene {\n kind: \"material-function\";\n sceneId: string;\n materials: readonly ChartReflectance[];\n materialAt(point: Readonly<SceneMaterialPoint>): number;\n}\n/** Most materials a {@link CallerMaterialScene} may list. */\nexport const CALLER_MATERIAL_SCENE_MAX_MATERIALS = 65_536;\n/** Internal: a validated material scene with its materials prepared (and the caller inputs, for the scene digest). */\nexport interface ResolvedCallerMaterialScene {\n kind: \"material-function\";\n sceneId: string;\n materials: ResolvedChartScene[\"materials\"];\n materialInputs: readonly unknown[];\n materialAt(point: Readonly<SceneMaterialPoint>): number;\n}\n/** Internal: a validated caller scene. */\nexport type ResolvedCallerScene = CallerReflectanceScene | CallerRadianceScene | ResolvedCallerMaterialScene;\n\nexport interface PlanarSceneGeometry {\n distanceM: number;\n /** Metres per frame unit on the plane (half the framed width). */\n metresPerFrameUnit: number;\n /**\n * 2.3, opt-in fixed-size chart: the chart is `widthM` × `heightM` on the plane, centred on the optical axis;\n * outside it the plane is a neutral Lambertian surround of `surroundReflectance`, lit by the same illuminant.\n * A chart preset is then resolved in its own frame (aspect heightM / widthM). Without it the chart fills the frame.\n */\n chart?: { widthM: number; heightM: number; surroundReflectance: number };\n}\n\nexport interface PlanarSceneRadianceProvider {\n sceneId: string;\n providerProfileId: string;\n evaluateRadiance(request: Readonly<SceneRadianceEvaluationRequest>): SceneRadianceEvaluationResult;\n evaluateApertureRadiance(request: Readonly<SceneRadianceEvaluationRequest>, ray: Readonly<SensorApertureRay>): SceneRadianceEvaluationResult;\n /** Spectral radiance at a plane point (frame units), the same value the callbacks return. */\n radianceAt(u: number, v: number, wavelengthNanometers: number): number;\n /**\n * 2.3, chart scenes only: the chart material at a plane point (frame units), or `materials.length` for the\n * surround of a fixed-size chart; `materialRadiance` gives that material's spectral radiance, the same value\n * `radianceAt` returns at its points.\n */\n chartMaterialAt?(u: number, v: number): number;\n materialRadiance?(material: number, wavelengthNanometers: number): number;\n}\n\n/**\n * Internal (#394, not exported from the package): per provider of a chart preset or caller material scene, the material its\n * `evaluateRadiance` reads for an environment-direction query with a given outgoing direction (the same plane-point\n * arithmetic), or undefined where `evaluateRadiance` would throw. Its radiance is `materialRadiance(material, wavelength)`.\n */\nconst MATERIAL_OF_DIRECTION = new WeakMap<PlanarSceneRadianceProvider, (direction: Readonly<{ x: number; y: number; z: number }>) => number | undefined>();\n\n/** Internal (#394): the material lookup of a provider built by {@link buildPlanarSceneRadianceProvider}, if it has one. */\nexport function planarProviderMaterialOfDirection(provider: PlanarSceneRadianceProvider):\n ((direction: Readonly<{ x: number; y: number; z: number }>) => number | undefined) | undefined {\n return MATERIAL_OF_DIRECTION.get(provider);\n}\n\nconst UNCERTAINTY = Object.freeze({ kind: \"not-quantified\" as const, limitation: \"Analytic planar Lambertian scene; no measured scene, BRDF or illumination.\" });\n\n/** Most distinct wavelengths {@link tabulatedSpectrum} keeps; later ones are evaluated on every call. */\nconst TABULATED_SPECTRUM_MAX_ENTRIES = 4096;\n\n/**\n * Internal (#385): `spectrum.evaluate` remembered per distinct wavelength. A prepared spectrum is a pure function of the\n * wavelength, so the table returns the same double the call would; renderers ask for the same few spectral nodes millions\n * of times, and the illuminant's formula (two transcendental evaluations) was about 30 % of a caller-scene display view.\n */\nexport function tabulatedSpectrum(spectrum: Readonly<PreparedColorimetricSpectrum>): (wavelengthNanometers: number) => number {\n const table = new Map<number, number>();\n return (nm) => {\n let value = table.get(nm);\n if (value === undefined) {\n value = spectrum.evaluate(nm);\n if (table.size < TABULATED_SPECTRUM_MAX_ENTRIES) table.set(nm, value);\n }\n return value;\n };\n}\n\n/**\n * Wraps a chart or caller scene as a provider for the native environment RAW task. `irradianceScale` is\n * from {@link calculateIlluminantIrradianceScale}; caller radiance scenes ignore the illuminant.\n */\nexport function buildPlanarSceneRadianceProvider(input: {\n scene: ResolvedChartScene | ResolvedCallerScene;\n sceneId: string;\n providerProfileId: string;\n illuminant: ResolvedCaptureIlluminant;\n irradianceScale: number;\n geometry: PlanarSceneGeometry;\n evidence: readonly EvidenceProvenance[];\n limitations: readonly string[];\n}): PlanarSceneRadianceProvider {\n const { scene, illuminant, irradianceScale, geometry } = input;\n const scale = geometry.metresPerFrameUnit, distance = geometry.distanceM, sceneId = input.sceneId, providerProfileId = input.providerProfileId;\n const evidence = input.evidence, limitations = input.limitations;\n const caller = \"kind\" in scene ? scene : undefined, chart = caller ? undefined : scene as ResolvedChartScene;\n const materialScene = caller?.kind === \"material-function\" ? caller : undefined, materials = chart ? chart.materials : materialScene?.materials;\n const placed = geometry.chart, half = placed ? placed.widthM / 2 : 0, chartAspect = placed ? placed.heightM / placed.widthM : 0;\n const shapeAt = tabulatedSpectrum(illuminant.shape);\n /** A material scene's material at a frame point: the caller's index, or `materials.length` for a fixed-size chart's surround. */\n function callerMaterialAt(u: number, v: number): number {\n const xM = u * scale, yM = v * scale;\n let point: SceneMaterialPoint;\n if (placed) {\n const cu = xM / half, cv = yM / half;\n if (!(Math.abs(cu) <= 1 && Math.abs(cv) <= chartAspect)) return materialScene!.materials.length;\n point = { xM, yM, u, v, chartU: cu, chartV: cv };\n } else point = { xM, yM, u, v };\n const index = materialScene!.materialAt(point);\n if (!Number.isInteger(index) || index < 0 || index >= materialScene!.materials.length) throw new InvalidConfigurationError(\"Scene materialAt must return an index into its materials.\");\n return index;\n }\n function radianceAt(u: number, v: number, nm: number): number {\n if (materialScene) return materialRadianceOf(callerMaterialAt(u, v), nm);\n if (placed) {\n // Fixed-size chart (2.3): chart-local frame units from the plane point in metres.\n const xM = u * scale, yM = v * scale, cu = xM / half, cv = yM / half;\n if (!(Math.abs(cu) <= 1 && Math.abs(cv) <= chartAspect)) return placed.surroundReflectance * irradianceScale * shapeAt(nm) / Math.PI;\n if (chart) return chart.reflectanceAt(cu, cv, nm) * irradianceScale * shapeAt(nm) / Math.PI;\n return callerValue({ xM, yM, u, v, wavelengthNanometers: nm, chartU: cu, chartV: cv }, nm);\n }\n if (chart) return chart.reflectanceAt(u, v, nm) * irradianceScale * shapeAt(nm) / Math.PI;\n return callerValue({ xM: u * scale, yM: v * scale, u, v, wavelengthNanometers: nm }, nm);\n }\n function callerValue(point: Readonly<ScenePlanePoint>, nm: number): number {\n const value = (caller as CallerReflectanceScene | CallerRadianceScene).evaluate(point);\n if (caller!.kind === \"reflectance-function\") {\n if (typeof value !== \"number\" || !Number.isFinite(value) || value < 0 || value > 1) throw new InvalidConfigurationError(\"Scene reflectance function must return a value in [0, 1].\");\n return value * irradianceScale * shapeAt(nm) / Math.PI;\n }\n if (typeof value !== \"number\" || !Number.isFinite(value) || value < 0) throw new InvalidConfigurationError(\"Scene radiance function must return a finite non-negative radiance.\");\n return value;\n }\n function result(request: Readonly<SceneRadianceEvaluationRequest>, radiance: number): SceneRadianceEvaluationResult {\n return { schemaVersion: \"0.1.0\", sampleId: request.sampleId, sceneId, providerProfileId, wavelengthNanometers: request.wavelengthNanometers,\n wavelengthBasis: request.wavelengthBasis as SceneRadianceEvaluationResult[\"wavelengthBasis\"], quantity: \"outgoing-spectral-radiance\", unit: \"W/m^2/sr/nm\",\n spectralRadianceWattsPerSquareMeterSteradianNanometer: radiance, scientificStatus: \"approximation\", uncertainty: UNCERTAINTY, evidence, limitations };\n }\n /** Spectral radiance of material `material` (`materials.length`: a fixed-size chart's surround), in the chart's expression order. */\n function materialRadianceOf(material: number, nm: number): number {\n const m = materials![material];\n let value: number;\n if (m === undefined) value = placed ? placed.surroundReflectance : NaN;\n else if (m.kind === \"neutral\") value = m.reflectance;\n else {\n value = m.spectrum.evaluate(nm);\n if (!(value >= 0 && value <= 1)) throw new InvalidConfigurationError(\"Chart reflectance spectrum left [0, 1].\");\n }\n if (!(value >= 0)) throw new InvalidConfigurationError(\"Unknown chart material.\");\n return value * irradianceScale * shapeAt(nm) / Math.PI;\n }\n function chartMaterialAt(u: number, v: number): number {\n if (!placed) return chart!.materialAt(u, v);\n const cu = u * scale / half, cv = v * scale / half;\n return Math.abs(cu) <= 1 && Math.abs(cv) <= chartAspect ? chart!.materialAt(cu, cv) : chart!.materials.length;\n }\n const chartAccess = chart ? { chartMaterialAt, materialRadiance: materialRadianceOf } :\n materialScene ? { chartMaterialAt: callerMaterialAt, materialRadiance: materialRadianceOf } : {};\n // #394: evaluateRadiance's own plane-point arithmetic; radianceAt is then materialRadianceOf(material, nm) for both scene forms.\n const materialAtPoint = chart ? chartMaterialAt : materialScene ? callerMaterialAt : undefined;\n const materialOfDirection = materialAtPoint === undefined ? undefined : (o: Readonly<{ x: number; y: number; z: number }>): number | undefined => {\n const lz = -o.z;\n if (!(lz > 0)) return undefined;\n const t = distance / lz;\n return materialAtPoint(-o.x * t / scale, -o.y * t / scale);\n };\n const provider: PlanarSceneRadianceProvider = {\n sceneId, providerProfileId, radianceAt, ...chartAccess,\n evaluateRadiance(request): SceneRadianceEvaluationResult {\n const target = request.target;\n if (target.kind !== \"environment-direction\") throw new InvalidConfigurationError(\"Planar scene provider needs environment-direction queries.\");\n const o = target.outgoingDirectionUnitVector, lz = -o.z;\n if (!(lz > 0)) throw new InvalidConfigurationError(\"Planar scene query does not point toward the scene plane.\");\n const t = distance / lz;\n return result(request, radianceAt(-o.x * t / scale, -o.y * t / scale, request.wavelengthNanometers));\n },\n evaluateApertureRadiance(request, ray): SceneRadianceEvaluationResult {\n const d = ray.directionUnitVector, origin = ray.originM;\n if (!(d.z > 0)) throw new InvalidConfigurationError(\"Planar scene pupil ray does not point toward the scene plane.\");\n const t = (distance - origin.z) / d.z;\n return result(request, radianceAt((origin.x + d.x * t) / scale, (origin.y + d.y * t) / scale, request.wavelengthNanometers));\n }\n };\n if (materialOfDirection) MATERIAL_OF_DIRECTION.set(provider, materialOfDirection);\n return provider;\n}\n\n/** 2.3: a chart's physical size on the scene plane (`simulateCapture` `chartSize`, `createPlanarSceneRadianceProvider` `chartSize`). */\nexport interface ChartSizeOption {\n /** Chart width in metres, (0, 10 000]. */\n widthM: number;\n /** Chart height in metres. Default: widthM × the frame aspect (height / width), so the chart has the frame's shape. */\n heightM?: number;\n /** Neutral reflectance of the plane around the chart, lit by the same illuminant. Default 0.18. */\n surroundReflectance?: number;\n}\n/** Default surround of a fixed-size chart: an 18 % grey plane. */\nexport const CHART_SIZE_DEFAULT_SURROUND_REFLECTANCE = 0.18;\n/** Internal: validates a chart size and fills its defaults; `defaulted` names the fields taken from defaults. */\nexport function resolveChartSizeOption(value: unknown, frameAspect: number): { widthM: number; heightM: number; surroundReflectance: number; defaulted: (\"heightM\" | \"surroundReflectance\")[] } {\n requireInputObject(value, \"chartSize\");\n const record = value as Record<string, unknown>;\n for (const key of Object.keys(record)) if (![\"widthM\", \"heightM\", \"surroundReflectance\"].includes(key)) throw new InvalidConfigurationError(\"Unknown chartSize field: \" + key + \".\");\n const size = (x: unknown, name: string): number => {\n if (typeof x !== \"number\" || !Number.isFinite(x) || x <= 0 || x > 10_000) throw new InvalidConfigurationError(\"chartSize.\" + name + \" must be a positive number of metres up to 10000.\");\n return x;\n };\n const defaulted: (\"heightM\" | \"surroundReflectance\")[] = [];\n const widthM = size(record.widthM, \"widthM\");\n const heightM = record.heightM === undefined ? (defaulted.push(\"heightM\"), widthM * frameAspect) : size(record.heightM, \"heightM\");\n const surround = record.surroundReflectance === undefined ? (defaulted.push(\"surroundReflectance\"), CHART_SIZE_DEFAULT_SURROUND_REFLECTANCE) : record.surroundReflectance;\n if (typeof surround !== \"number\" || !Number.isFinite(surround) || surround < 0 || surround > 1) throw new InvalidConfigurationError(\"chartSize.surroundReflectance must be a reflectance in [0, 1].\");\n return { widthM, heightM, surroundReflectance: surround, defaulted };\n}\n\n/**\n * Public scene-preset provider. Places an engine chart (or a declared `material-layers` scene, #491, evaluated as\n * its `callerScene`; or a caller reflectance, radiance or material function) on\n * a plane `distanceM` in front of the camera and `framedWidthM` wide (frame units u = ±1 at its edges),\n * lit by `illuminant` at `illuminanceLux`. The returned `evaluateRadiance` and `evaluateApertureRadiance`\n * follow the native environment RAW provider contract. They answer requests for scene `sceneId` and\n * provider `providerProfileId`.\n */\nexport function createPlanarSceneRadianceProvider(input: {\n scene: ChartScene | ChartMaterialLayerScene | CallerReflectanceScene | CallerRadianceScene | CallerMaterialScene;\n illuminant: CaptureIlluminant;\n illuminanceLux: number;\n distanceM: number;\n framedWidthM: number;\n /** Frame height / width. */\n aspect: number;\n sceneId: string;\n providerProfileId: string;\n /**\n * 2.3, opt-in: place the chart at this physical size, centred, instead of filling the frame; the chart preset\n * is resolved with aspect heightM / widthM and the rest of the plane is the surround.\n */\n chartSize?: ChartSizeOption;\n}): PlanarSceneRadianceProvider & { chart: ResolvedChartScene | null } {\n requireInputObject(input, \"createPlanarSceneRadianceProvider input\");\n const keys = [\"scene\", \"illuminant\", \"illuminanceLux\", \"distanceM\", \"framedWidthM\", \"aspect\", \"sceneId\", \"providerProfileId\", \"chartSize\"];\n for (const key of Object.keys(input)) if (!keys.includes(key)) throw new InvalidConfigurationError(\"createPlanarSceneRadianceProvider input has unknown field \\\"\" + key + \"\\\".\");\n for (const key of [\"illuminanceLux\", \"distanceM\", \"framedWidthM\", \"aspect\"] as const) {\n const value = input[key];\n if (typeof value !== \"number\" || !Number.isFinite(value) || value <= 0) throw new InvalidConfigurationError(key + \" must be a positive finite number.\");\n }\n for (const key of [\"sceneId\", \"providerProfileId\"] as const) if (typeof input[key] !== \"string\" || !/^[A-Za-z0-9][A-Za-z0-9._:-]{0,127}$/.test(input[key])) throw new InvalidConfigurationError(key + \" must be a public opaque ID.\");\n requireInputObject(input.scene, \"scene\");\n const size = input.chartSize === undefined ? undefined : resolveChartSizeOption(input.chartSize, input.aspect), chartAspect = size ? size.heightM / size.widthM : input.aspect;\n const declared = (input.scene as { kind?: unknown }).kind === \"material-layers\" ? resolveChartMaterialLayers({ scene: input.scene as ChartMaterialLayerScene, aspect: chartAspect }) : undefined;\n const caller = declared ? requireCallerScene(declared.callerScene) : \"kind\" in input.scene ? requireCallerScene(input.scene) : undefined;\n const chart = caller ? null : resolveChartScene({ scene: input.scene as ChartScene, aspect: chartAspect });\n const illuminant = resolveCaptureIlluminant(input.illuminant);\n const provider = buildPlanarSceneRadianceProvider({ scene: chart ?? caller!, sceneId: input.sceneId, providerProfileId: input.providerProfileId, illuminant,\n irradianceScale: calculateIlluminantIrradianceScale(illuminant.shape, input.illuminanceLux),\n geometry: { distanceM: input.distanceM, metresPerFrameUnit: input.framedWidthM / 2,\n ...(size ? { chart: { widthM: size.widthM, heightM: size.heightM, surroundReflectance: size.surroundReflectance } } : {}) },\n evidence: [{ sourceOrigin: \"photivra\", sourceReference: \"photivra:planar-scene-provider\", reuseStatus: \"photivra-owned\" }],\n limitations: [\"Planar Lambertian scene under uniform illumination; no shadows, inter-reflection, gloss or fluorescence.\"] });\n return { ...provider, chart };\n}\n\n/** Validates a caller scene record (a function scene as given; a material scene with its materials prepared). */\nexport function requireCallerScene(value: unknown): ResolvedCallerScene {\n requireInputObject(value, \"scene\");\n const record = value as Record<string, unknown>;\n if (record.kind === \"material-function\") {\n for (const key of Object.keys(record)) if (key !== \"kind\" && key !== \"sceneId\" && key !== \"materials\" && key !== \"materialAt\") throw new InvalidConfigurationError(\"Unknown scene field: \" + key + \".\");\n if (typeof record.materialAt !== \"function\" || typeof record.sceneId !== \"string\" || !/^[A-Za-z0-9][A-Za-z0-9._:-]{0,63}$/.test(record.sceneId) ||\n !Array.isArray(record.materials) || record.materials.length < 1 || record.materials.length > CALLER_MATERIAL_SCENE_MAX_MATERIALS)\n throw new InvalidConfigurationError(\"A material scene needs a public sceneId, 1 to \" + CALLER_MATERIAL_SCENE_MAX_MATERIALS + \" materials and a materialAt function.\");\n const inputs = [...record.materials as unknown[]];\n return Object.freeze({ kind: \"material-function\" as const, sceneId: record.sceneId, materialAt: record.materialAt as ResolvedCallerMaterialScene[\"materialAt\"],\n materials: Object.freeze(inputs.map((m, index) => resolveChartMaterial(m, \"scene.materials[\" + index + \"]\"))),\n materialInputs: Object.freeze(inputs.map((m) => (typeof m === \"number\" ? undefined : m))) });\n }\n for (const key of Object.keys(record)) if (key !== \"kind\" && key !== \"sceneId\" && key !== \"evaluate\") throw new InvalidConfigurationError(\"Unknown scene field: \" + key + \".\");\n if ((record.kind !== \"reflectance-function\" && record.kind !== \"radiance-function\") || typeof record.evaluate !== \"function\" ||\n typeof record.sceneId !== \"string\" || !/^[A-Za-z0-9][A-Za-z0-9._:-]{0,63}$/.test(record.sceneId)) throw new InvalidConfigurationError(\"A caller scene needs kind, a public sceneId and an evaluate function.\");\n return record as unknown as CallerReflectanceScene | CallerRadianceScene;\n}\n"]}
@@ -3,6 +3,7 @@ import { type GenericEquipmentTier, type GenericEquipmentTierPreset } from "../e
3
3
  import { resolveColorTemperatureWhiteBalance, type ResolvedWhiteBalanceState } from "../color/white-balance.js";
4
4
  import { type CaptureWhiteBalanceIntent } from "../capture/simulated-capture.js";
5
5
  import { type NativeRawOutput, type NativeRawPlan } from "../capture/native-raw.js";
6
+ import type { DisplayViewFastReport } from "./display-view-gpu.js";
6
7
  import { type NativeEnvironmentRawInput } from "../capture/native-environment-raw.js";
7
8
  import { type NativeRawDevelopmentInput, type RawHighlightDiagnostics } from "../capture/native-raw-development.js";
8
9
  import type { RawFrameReconstructionPhaseProfile } from "../capture/raw-frame-reconstruction.js";
@@ -17,9 +18,11 @@ import type { IlluminationVignettingProfile } from "../optics/illumination-vigne
17
18
  import type { CalculateSensorPsfIrradianceQuadratureInput } from "../optics/sensor-psf-quadrature.js";
18
19
  import type { CalculateEnvironmentSensorPhotoSignalInput } from "../sensor/environment-photo-signal.js";
19
20
  import { type DiffractionLimitedPsfProfile } from "../optics/diffraction-psf-profile.js";
21
+ import { type ResolvedDefocusDisc } from "../optics/defocus-disc-kernel.js";
20
22
  import { type AntiAliasingPointSplitComponent } from "../sensor/optical-stack.js";
21
23
  import { type NativeRawDng } from "../capture/native-raw-dng.js";
22
24
  import { type ChartScene, type ResolvedChartScene } from "./chart-scenes.js";
25
+ import { type ChartMaterialLayerScene, type ResolvedChartMaterialLayers } from "./chart-material-layers.js";
23
26
  import { type ChartSizeOption, type CaptureIlluminant, type CallerMaterialScene, type CallerRadianceScene, type CallerReflectanceScene, type ResolvedCallerScene, type PlanarSceneRadianceProvider, type ResolvedCaptureIlluminant } from "./scene-radiance.js";
24
27
  /** Version of how the facade builds requests. It changes whenever the same input would build a different request. */
25
28
  export declare const SIMULATE_CAPTURE_FACADE_VERSION: "1.0.0";
@@ -171,6 +174,19 @@ export interface SimulateCaptureOptions {
171
174
  * the longest spectral node, capped at 32 sites. Not combinable with `psf` or `pupilSampling`. Default off.
172
175
  */
173
176
  diffraction?: SimulateCaptureLensDiffraction;
177
+ /**
178
+ * Opt-in (#492): defocus of the flat scene plane when `focusDistanceM` differs from the subject distance, as a
179
+ * geometric disc (`model: "geometric-disc"`): the thin-lens blur circle of an ideal uniform circular pupil
180
+ * (`calculateDefocusCircle`), an approximation. The blur diameter is recorded in the `lens.defocus` assumption.
181
+ * `simulateCapture` renders the blur as an object-space convolution of the scene radiance on the site lattice and
182
+ * `simulateDisplayView` as a site kernel in its expected signal; with `diffraction` each spectral node's diffraction
183
+ * kernel is convolved with the disc (a further approximation). In focus the result is that of the same request
184
+ * without the option, plus the assumption.
185
+ * Not combinable with `pupilSampling` or `psf`. Default off.
186
+ */
187
+ defocus?: {
188
+ model: "geometric-disc";
189
+ };
174
190
  };
175
191
  exposure?: {
176
192
  /** Default "manual". */
@@ -182,8 +198,12 @@ export interface SimulateCaptureOptions {
182
198
  /** Exposure compensation applied to the meter target, in stops. Default 0. */
183
199
  compensationStops?: number;
184
200
  };
185
- /** Required: an engine chart (for example `{ preset: "uniform" }`, an 18 % grey card) or a caller reflectance/radiance function. */
186
- scene: ChartScene | CallerReflectanceScene | CallerRadianceScene | CallerMaterialScene;
201
+ /**
202
+ * Required: an engine chart (for example `{ preset: "uniform" }`, an 18 % grey card), a declared `material-layers` scene (#491:
203
+ * a chart under shape-mask layers, as `resolveChartMaterialLayers` takes it; the capture is that of its `callerScene`, byte for
204
+ * byte, and the display view can render it on the GPU), or a caller reflectance, radiance or material function.
205
+ */
206
+ scene: ChartScene | ChartMaterialLayerScene | CallerReflectanceScene | CallerRadianceScene | CallerMaterialScene;
187
207
  /** Distance from the camera to the scene plane in metres. Default 5. */
188
208
  subjectDistanceM?: number;
189
209
  /**
@@ -305,7 +325,7 @@ export interface SimulateCaptureOptions {
305
325
  * Options reported in `diagnostics.options` (2.1), in this order, when they ran: the ones that change how much work
306
326
  * a capture does. `motion.rotation` is a non-zero angular velocity; `sensor.temporalSampleCount` a count above 1.
307
327
  */
308
- export declare const SIMULATE_CAPTURE_COST_OPTIONS: readonly ["lens.pupilSampling", "lens.projection", "lens.distortion", "lens.vignetting", "lens.psf", "lens.diffraction", "sensor.antiAliasing", "sensor.pixelAperture.box", "sensor.temporalSampleCount", "motion.rotation", "motion.shutter.rolling", "output.borderHandling.mirror", "output.region", "output.whiteBalance.auto", "output.demosaic.ahd", "output.highlightMode.reconstruct", "output.colorEncoding.wide-gamut", "output.gamutMapping.perceptual", "output.format.jpeg", "output.format.png", "output.format.dng"];
328
+ export declare const SIMULATE_CAPTURE_COST_OPTIONS: readonly ["lens.pupilSampling", "lens.projection", "lens.distortion", "lens.vignetting", "lens.psf", "lens.diffraction", "lens.defocus", "sensor.antiAliasing", "sensor.pixelAperture.box", "sensor.temporalSampleCount", "motion.rotation", "motion.shutter.rolling", "output.borderHandling.mirror", "output.region", "output.whiteBalance.auto", "output.demosaic.ahd", "output.highlightMode.reconstruct", "output.colorEncoding.wide-gamut", "output.gamutMapping.perceptual", "output.format.jpeg", "output.format.png", "output.format.dng"];
309
329
  export type SimulateCaptureCostOption = typeof SIMULATE_CAPTURE_COST_OPTIONS[number];
310
330
  /**
311
331
  * The options that take the exact-or-fast flag (#395), in the path style of {@link SIMULATE_CAPTURE_COST_OPTIONS}: each accepts
@@ -470,6 +490,8 @@ export interface SimulateCaptureResult {
470
490
  * `diffraction` (the object-space convolution of `lens.diffraction`; part of `raw` and `whiteBalance`), `demosaic`
471
491
  * (the AHD demosaic; part of `development`) and `encode` (PNG, JPEG or DNG serialization), with sub-millisecond
472
492
  * resolution where the host has `performance.now()`. Timings vary from run to run and never enter any digest or output byte.
493
+ * #492: `defocus`, the object-space convolution of `lens.defocus` out of focus (with `lens.diffraction` the combined
494
+ * kernel's convolution, reported here instead of under `diffraction`).
473
495
  */
474
496
  timingsMs: {
475
497
  raw: number;
@@ -478,6 +500,7 @@ export interface SimulateCaptureResult {
478
500
  jpeg: number;
479
501
  total: number;
480
502
  diffraction?: number;
503
+ defocus?: number;
481
504
  demosaic?: number;
482
505
  encode?: number;
483
506
  };
@@ -703,8 +726,8 @@ export interface DisplayViewResult {
703
726
  view: number;
704
727
  total: number;
705
728
  };
706
- /** #395: exact or fast, as requested and as run (see {@link SimulateCaptureFastReport}). */
707
- fast: SimulateCaptureFastReport;
729
+ /** #395: exact or fast, as requested and as run; 2.11 (#481): plus `execution`, where the render ran (see {@link DisplayViewFastReport}). */
730
+ fast: DisplayViewFastReport;
708
731
  };
709
732
  provenance: {
710
733
  scientificStatus: "approximation";
@@ -734,6 +757,8 @@ export interface DisplayViewRunContext {
734
757
  buildProvider: (sceneIlluminant: ResolvedCaptureIlluminant, scale: number) => PlanarSceneRadianceProvider;
735
758
  callerScene: ResolvedCallerScene | undefined;
736
759
  chart: ResolvedChartScene | undefined;
760
+ /** #491: the declared material-layers scene behind `callerScene`, when the request gave one. */
761
+ materialLayers: ResolvedChartMaterialLayers | undefined;
737
762
  chartReport: {
738
763
  widthM: number;
739
764
  heightM: number;
@@ -753,6 +778,8 @@ export interface DisplayViewRunContext {
753
778
  defaulted: ("heightM" | "surroundReflectance")[];
754
779
  } | undefined;
755
780
  diffraction: DiffractionLimitedPsfProfile | undefined;
781
+ /** `lens.defocus` (#492): the resolved geometric disc out of focus; undefined in focus or without the option. */
782
+ defocus: ResolvedDefocusDisc | undefined;
756
783
  diffractionPsf: {
757
784
  kind: "sampled-local";
758
785
  configuration: Pick<CalculateSensorPsfIrradianceQuadratureInput, "psf" | "psfWavelengthBasis" | "spatialModel">;