@photivra/engine 2.8.1 → 2.10.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 (91) hide show
  1. package/CHANGELOG.md +144 -1
  2. package/CITATION.cff +1 -1
  3. package/README.md +8 -6
  4. package/SECURITY.md +1 -1
  5. package/THIRD_PARTY.md +2 -0
  6. package/dist/capture/export-jpeg.d.ts +19 -0
  7. package/dist/capture/export-jpeg.js +190 -108
  8. package/dist/capture/export-jpeg.js.map +1 -1
  9. package/dist/capture/native-environment-lean.js +106 -12
  10. package/dist/capture/native-environment-lean.js.map +1 -1
  11. package/dist/capture/native-environment-tabulated.d.ts +37 -0
  12. package/dist/capture/native-environment-tabulated.js +42 -6
  13. package/dist/capture/native-environment-tabulated.js.map +1 -1
  14. package/dist/core/portable-math.d.ts +13 -0
  15. package/dist/core/portable-math.js +43 -0
  16. package/dist/core/portable-math.js.map +1 -1
  17. package/dist/core/version.d.ts +1 -1
  18. package/dist/core/version.js +1 -1
  19. package/dist/core/version.js.map +1 -1
  20. package/dist/facade/channel-response.d.ts +15 -0
  21. package/dist/facade/channel-response.js +33 -0
  22. package/dist/facade/channel-response.js.map +1 -0
  23. package/dist/facade/diffraction-provider.js +50 -15
  24. package/dist/facade/diffraction-provider.js.map +1 -1
  25. package/dist/facade/display-view.d.ts +75 -0
  26. package/dist/facade/display-view.js +471 -109
  27. package/dist/facade/display-view.js.map +1 -1
  28. package/dist/facade/expected-signal-setup.js +2 -1
  29. package/dist/facade/expected-signal-setup.js.map +1 -1
  30. package/dist/facade/expected-signal.d.ts +36 -4
  31. package/dist/facade/expected-signal.js +331 -43
  32. package/dist/facade/expected-signal.js.map +1 -1
  33. package/dist/facade/scene-radiance.d.ts +4 -1
  34. package/dist/facade/scene-radiance.js +4 -4
  35. package/dist/facade/scene-radiance.js.map +1 -1
  36. package/dist/facade/simulate-capture.d.ts +77 -5
  37. package/dist/facade/simulate-capture.js +232 -40
  38. package/dist/facade/simulate-capture.js.map +1 -1
  39. package/dist/facade/simulate-display-view.d.ts +25 -2
  40. package/dist/facade/simulate-display-view.js +55 -21
  41. package/dist/facade/simulate-display-view.js.map +1 -1
  42. package/dist/gpu/image-kernel-execution.d.ts +5 -0
  43. package/dist/gpu/image-kernel-execution.js +2 -2
  44. package/dist/gpu/image-kernel-execution.js.map +1 -1
  45. package/dist/index.d.ts +5 -4
  46. package/dist/index.js +3 -3
  47. package/dist/index.js.map +1 -1
  48. package/dist/optics/diffraction-psf-profile.d.ts +19 -17
  49. package/dist/optics/diffraction-psf-profile.js +49 -18
  50. package/dist/optics/diffraction-psf-profile.js.map +1 -1
  51. package/dist/optics/irradiance-convolution.d.ts +11 -0
  52. package/dist/optics/irradiance-convolution.js +64 -24
  53. package/dist/optics/irradiance-convolution.js.map +1 -1
  54. package/dist/optics/scene-to-sensor-irradiance.d.ts +13 -0
  55. package/dist/optics/scene-to-sensor-irradiance.js +58 -24
  56. package/dist/optics/scene-to-sensor-irradiance.js.map +1 -1
  57. package/dist/optics/sensor-aperture-rays.js +2 -1
  58. package/dist/optics/sensor-aperture-rays.js.map +1 -1
  59. package/dist/optics/sensor-environment-query.js +4 -3
  60. package/dist/optics/sensor-environment-query.js.map +1 -1
  61. package/dist/optics/site-diffraction-kernel.d.ts +16 -0
  62. package/dist/optics/site-diffraction-kernel.js +60 -8
  63. package/dist/optics/site-diffraction-kernel.js.map +1 -1
  64. package/dist/output/print-jpeg.d.ts +28 -1
  65. package/dist/output/print-jpeg.js +79 -7
  66. package/dist/output/print-jpeg.js.map +1 -1
  67. package/dist/processing/demosaic.js +114 -37
  68. package/dist/processing/demosaic.js.map +1 -1
  69. package/dist/schema/scene-radiance.d.ts +8 -0
  70. package/dist/schema/scene-radiance.js +28 -17
  71. package/dist/schema/scene-radiance.js.map +1 -1
  72. package/dist/sensor/environment-photo-signal.d.ts +21 -0
  73. package/dist/sensor/environment-photo-signal.js +68 -2
  74. package/dist/sensor/environment-photo-signal.js.map +1 -1
  75. package/dist/sensor/stochastic-seed.d.ts +12 -0
  76. package/dist/sensor/stochastic-seed.js +25 -0
  77. package/dist/sensor/stochastic-seed.js.map +1 -1
  78. package/docs/API_REFERENCE.md +23 -1
  79. package/docs/QUICK_START.md +77 -8
  80. package/docs/USAGE.md +30 -0
  81. package/docs/api/capture-export-jpeg.md +10 -0
  82. package/docs/api/core-version.md +1 -1
  83. package/docs/api/exports.json +77 -2
  84. package/docs/api/facade-display-view.md +50 -0
  85. package/docs/api/facade-scene-radiance.md +2 -1
  86. package/docs/api/facade-simulate-capture.md +88 -8
  87. package/docs/api/facade-simulate-display-view.md +23 -1
  88. package/docs/api/gpu-image-kernel-execution.md +5 -0
  89. package/docs/api/optics-diffraction-psf-profile.md +1 -1
  90. package/docs/api/output-print-jpeg.md +41 -0
  91. package/package.json +1 -1
@@ -1 +1 @@
1
- {"version":3,"file":"scene-radiance.js","sourceRoot":"","sources":["../../src/schema/scene-radiance.ts"],"names":[],"mappings":"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","sourcesContent":["// SPDX-License-Identifier: Apache-2.0\n\n/**\n * Contracts for scene-radiance providers: the renderer or other code that reports how much\n * light leaves a scene point toward the camera.\n *\n * It covers material-response metadata, provider capability profiles, single evaluation\n * requests and results, and identity checks between them. The engine validates this data\n * but does not compute scene radiance itself.\n * @see docs/SCENE_RADIANCE_AND_ILLUMINATION.md for equations, coordinate/unit conventions, blockers\n * and support limits.\n */\n\nimport { InvalidConfigurationError } from \"../core/configuration-error.js\";\nimport {\n parseEvidenceList,\n type EvidenceProvenance\n} from \"../core/evidence-provenance.js\";\nimport {\n parseSpectralWavelengthBasis,\n parseSpectralWavelengthRangeNanometers,\n type SpectralWavelengthBasis,\n type SpectralWavelengthRangeNanometers\n} from \"../core/spectral.js\";\nimport type {\n SceneIlluminationProfile\n} from \"./illumination.js\";\nimport type {\n SceneIlluminationTemporalProfile\n} from \"./illumination-temporal.js\";\nimport type { Vector3 } from \"./scene.js\";\nimport { requireInputObject, requireInputArray, requireInputKeys, rejectUnknownFields, rejectUnknownVariantFields, UNCERTAINTY_VARIANT_FIELDS } from \"../core/record-validation.js\";\n\ntype UnknownRecord = Record<string, unknown>;\n\nexport const SCENE_MATERIAL_RESPONSE_PROFILE_SCHEMA_VERSION =\n \"0.1.0\" as const;\nexport const SCENE_RADIANCE_PROVIDER_PROFILE_SCHEMA_VERSION =\n \"0.1.0\" as const;\nexport const SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION =\n \"0.1.0\" as const;\n\nexport type SceneRadianceScientificStatus =\n | \"calibrated\"\n | \"approximation\";\n\nexport type SceneRadianceUncertainty =\n | {\n kind: \"relative\";\n fraction: number;\n basis: string;\n }\n | {\n kind: \"not-quantified\";\n limitation: string;\n };\n\nexport interface SceneRadianceDataArtifactReference {\n id: string;\n checksumSha256: string;\n}\n\nexport type SceneMaterialResponseRepresentation =\n | {\n kind: \"unresolved\";\n limitation: string;\n }\n | {\n kind: \"rgb-pbr-approximation\";\n colorSpace: \"linear-srgb\";\n baseColor: {\n red: number;\n green: number;\n blue: number;\n };\n metallic: number;\n roughness: number;\n limitation: string;\n }\n | {\n kind: \"spectral-wavelength-preserving-data\";\n dataArtifact:\n SceneRadianceDataArtifactReference;\n wavelengthBasis:\n SpectralWavelengthBasis;\n wavelengthRangeNanometers:\n SpectralWavelengthRangeNanometers;\n scatteringModel:\n \"provider-defined-wavelength-preserving\";\n scientificStatus:\n SceneRadianceScientificStatus;\n uncertainty:\n SceneRadianceUncertainty;\n wavelengthChangingBehaviorModeled: false;\n emissionModeled: false;\n };\n\nexport interface SceneMaterialResponseDefinition {\n materialResponseId: string;\n evidence: readonly EvidenceProvenance[];\n representation:\n SceneMaterialResponseRepresentation;\n}\n\nexport interface SceneMaterialResponseProfile {\n schemaVersion:\n typeof SCENE_MATERIAL_RESPONSE_PROFILE_SCHEMA_VERSION;\n profileId: string;\n sceneId: string;\n evidence: readonly EvidenceProvenance[];\n materials:\n readonly SceneMaterialResponseDefinition[];\n fluorescenceModeled: false;\n volumetricMaterialTransportModeled: false;\n polarizationModeled: false;\n}\n\nexport type SceneMaterialResponseFidelity =\n | \"spectral-data\"\n | \"rgb-pbr-approximation\"\n | \"mixed\"\n | \"unresolved\";\n\nexport type SceneRadianceProviderSpectralFidelity =\n | \"wavelength-resolved\"\n | \"rgb-derived-approximation\";\n\nexport type SceneRadianceProviderVisibilityFidelity =\n | \"resolved\"\n | \"approximation\"\n | \"not-modeled\";\n\nexport type SceneRadianceProviderTransportFidelity =\n | \"resolved\"\n | \"approximation\"\n | \"not-modeled\";\n\nexport interface SceneRadianceProviderProfile {\n schemaVersion:\n typeof SCENE_RADIANCE_PROVIDER_PROFILE_SCHEMA_VERSION;\n profileId: string;\n sceneId: string;\n illuminationProfileId: string;\n illuminationTemporalProfileId?: string;\n materialResponseProfileId: string;\n outputQuantity:\n \"outgoing-spectral-radiance\";\n outputUnit:\n \"W/m^2/sr/nm\";\n scientificStatus: \"approximation\";\n uncertainty: SceneRadianceUncertainty;\n fidelity: {\n spectral:\n SceneRadianceProviderSpectralFidelity;\n material:\n SceneMaterialResponseFidelity;\n visibility:\n SceneRadianceProviderVisibilityFidelity;\n directTransport:\n SceneRadianceProviderTransportFidelity;\n indirectTransport:\n SceneRadianceProviderTransportFidelity;\n };\n wavelengthChangingTransportModeled: false;\n volumetricTransportModeled: false;\n polarizationModeled: false;\n evidence: readonly EvidenceProvenance[];\n limitations: readonly string[];\n}\n\nexport type SceneRadianceEvaluationTarget =\n | {\n kind: \"surface-point\";\n sceneObjectId: string;\n materialResponseId: string;\n positionM: Vector3;\n outgoingDirectionUnitVector: Vector3;\n }\n | {\n kind: \"environment-direction\";\n outgoingDirectionUnitVector: Vector3;\n };\n\nexport interface SceneRadianceEvaluationRequest {\n schemaVersion:\n typeof SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION;\n sampleId: string;\n providerProfileId: string;\n sceneId: string;\n illuminationProfileId: string;\n materialResponseProfileId: string;\n target: SceneRadianceEvaluationTarget;\n timeSecondsFromExposureStart: number;\n wavelengthNanometers: number;\n wavelengthBasis:\n Exclude<SpectralWavelengthBasis, \"unspecified\">;\n}\n\nexport interface SceneRadianceEvaluationResult {\n schemaVersion:\n typeof SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION;\n sampleId: string;\n providerProfileId: string;\n sceneId: string;\n wavelengthNanometers: number;\n wavelengthBasis:\n Exclude<SpectralWavelengthBasis, \"unspecified\">;\n quantity:\n \"outgoing-spectral-radiance\";\n unit: \"W/m^2/sr/nm\";\n spectralRadianceWattsPerSquareMeterSteradianNanometer:\n number;\n scientificStatus: \"approximation\";\n uncertainty: SceneRadianceUncertainty;\n evidence: readonly EvidenceProvenance[];\n limitations: readonly string[];\n}\n\nexport interface ValidateSceneRadianceEvaluationBindingsInput {\n providerProfile: SceneRadianceProviderProfile;\n illuminationProfile: SceneIlluminationProfile;\n illuminationTemporalProfile?:\n SceneIlluminationTemporalProfile;\n materialResponseProfile:\n SceneMaterialResponseProfile;\n request: SceneRadianceEvaluationRequest;\n result: SceneRadianceEvaluationResult;\n}\n\nexport interface SceneRadianceEvaluationBindingAssessment {\n providerBindingsMatched: true;\n requestResultIdentityMatched: true;\n materialResponseFidelity:\n SceneMaterialResponseFidelity;\n temporalIlluminationProfileBound:\n boolean;\n calibratedRadianceClaimAuthorized: false;\n sensorPlaneIrradianceCalculated: false;\n opticsApplied: false;\n photonsCalculated: false;\n}\n\nfunction requireRecord(\n value: unknown,\n path: string,\n allowedKeys: readonly string[] | null\n): UnknownRecord {\n if (\n typeof value !== \"object\" ||\n value === null ||\n Array.isArray(value)\n ) {\n throw new InvalidConfigurationError(\n path + \" must be an object.\"\n );\n }\n if (allowedKeys !== null) rejectUnknownFields(value, allowedKeys, path);\n return value as UnknownRecord;\n}\n\nfunction requireNonEmptyString(\n value: unknown,\n path: string\n): string {\n if (\n typeof value !== \"string\" ||\n value.trim().length === 0\n ) {\n throw new InvalidConfigurationError(\n path + \" must be a non-empty string.\"\n );\n }\n return value.trim();\n}\n\nfunction requireFinite(\n value: unknown,\n path: string\n): number {\n if (\n typeof value !== \"number\" ||\n !Number.isFinite(value)\n ) {\n throw new InvalidConfigurationError(\n path + \" must be a finite number.\"\n );\n }\n return value;\n}\n\nfunction requireNonNegativeFinite(\n value: unknown,\n path: string\n): number {\n const number = requireFinite(value, path);\n if (number < 0) {\n throw new InvalidConfigurationError(\n path +\n \" must be greater than or equal to zero.\"\n );\n }\n return number;\n}\n\nfunction requireFraction(\n value: unknown,\n path: string\n): number {\n const number = requireFinite(value, path);\n if (number < 0 || number > 1) {\n throw new InvalidConfigurationError(\n path +\n \" must be a finite fraction from 0 through 1.\"\n );\n }\n return number;\n}\n\nfunction parseVector3(\n value: unknown,\n path: string\n): Vector3 {\n const record = requireRecord(value, path, [\"x\", \"y\", \"z\"]);\n return {\n x: requireFinite(record.x, path + \".x\"),\n y: requireFinite(record.y, path + \".y\"),\n z: requireFinite(record.z, path + \".z\")\n };\n}\n\nfunction parseUnitDirection(\n value: unknown,\n path: string\n): Vector3 {\n const vector = parseVector3(value, path);\n const length = Math.hypot(\n vector.x,\n vector.y,\n vector.z\n );\n if (\n !Number.isFinite(length) ||\n Math.abs(length - 1) > 1e-9\n ) {\n throw new InvalidConfigurationError(\n path +\n \" must be a unit-length direction vector.\"\n );\n }\n return vector;\n}\n\nfunction parseUncertainty(\n value: unknown,\n path: string\n): SceneRadianceUncertainty {\n const record = requireRecord(value, path, null);\n rejectUnknownVariantFields(record, \"kind\", UNCERTAINTY_VARIANT_FIELDS, path);\n if (record.kind === \"relative\") {\n return {\n kind: \"relative\",\n fraction: requireNonNegativeFinite(\n record.fraction,\n path + \".fraction\"\n ),\n basis: requireNonEmptyString(\n record.basis,\n path + \".basis\"\n )\n };\n }\n if (record.kind === \"not-quantified\") {\n return {\n kind: \"not-quantified\",\n limitation: requireNonEmptyString(\n record.limitation,\n path + \".limitation\"\n )\n };\n }\n throw new InvalidConfigurationError(\n path + \".kind is invalid.\"\n );\n}\n\nfunction parseLimitations(\n value: unknown,\n path: string\n): readonly string[] {\n if (!Array.isArray(value)) {\n throw new InvalidConfigurationError(\n path + \" must be an array.\"\n );\n }\n const limitations = value.map(\n (entry, index) =>\n requireNonEmptyString(\n entry,\n path + \"[\" + index + \"]\"\n )\n );\n if (\n new Set(limitations).size !==\n limitations.length\n ) {\n throw new InvalidConfigurationError(\n path + \" must not contain duplicates.\"\n );\n }\n return limitations;\n}\n\nfunction parseArtifact(\n value: unknown,\n path: string\n): SceneRadianceDataArtifactReference {\n const record = requireRecord(value, path, [\"checksumSha256\", \"id\"]);\n const checksumSha256 =\n requireNonEmptyString(\n record.checksumSha256,\n path + \".checksumSha256\"\n );\n if (\n !/^[a-f0-9]{64}$/iu.test(\n checksumSha256\n )\n ) {\n throw new InvalidConfigurationError(\n path +\n \".checksumSha256 must be a 64-character SHA-256 hex digest.\"\n );\n }\n return {\n id: requireNonEmptyString(\n record.id,\n path + \".id\"\n ),\n checksumSha256:\n checksumSha256.toLowerCase()\n };\n}\n\nfunction parseMaterialRepresentation(\n value: unknown,\n path: string\n): SceneMaterialResponseRepresentation {\n const record = requireRecord(value, path, null);\n rejectUnknownVariantFields(record, \"kind\", {\n unresolved: [\"kind\", \"limitation\"],\n \"rgb-pbr-approximation\": [\"kind\", \"colorSpace\", \"baseColor\", \"metallic\", \"roughness\", \"limitation\"],\n \"spectral-wavelength-preserving-data\": [\"kind\", \"dataArtifact\", \"wavelengthBasis\", \"wavelengthRangeNanometers\", \"scatteringModel\",\n \"scientificStatus\", \"uncertainty\", \"wavelengthChangingBehaviorModeled\", \"emissionModeled\"]\n }, path);\n\n if (record.kind === \"unresolved\") {\n return {\n kind: \"unresolved\",\n limitation: requireNonEmptyString(\n record.limitation,\n path + \".limitation\"\n )\n };\n }\n\n if (\n record.kind ===\n \"rgb-pbr-approximation\"\n ) {\n if (record.colorSpace !== \"linear-srgb\") {\n throw new InvalidConfigurationError(\n path +\n '.colorSpace must be \"linear-srgb\".'\n );\n }\n const baseColor = requireRecord(\n record.baseColor,\n path + \".baseColor\", [\"red\", \"green\", \"blue\"]\n );\n return {\n kind: \"rgb-pbr-approximation\",\n colorSpace: \"linear-srgb\",\n baseColor: {\n red: requireFraction(\n baseColor.red,\n path + \".baseColor.red\"\n ),\n green: requireFraction(\n baseColor.green,\n path + \".baseColor.green\"\n ),\n blue: requireFraction(\n baseColor.blue,\n path + \".baseColor.blue\"\n )\n },\n metallic: requireFraction(\n record.metallic,\n path + \".metallic\"\n ),\n roughness: requireFraction(\n record.roughness,\n path + \".roughness\"\n ),\n limitation: requireNonEmptyString(\n record.limitation,\n path + \".limitation\"\n )\n };\n }\n\n if (\n record.kind !==\n \"spectral-wavelength-preserving-data\"\n ) {\n throw new InvalidConfigurationError(\n path + \".kind is invalid.\"\n );\n }\n\n if (\n record.scatteringModel !==\n \"provider-defined-wavelength-preserving\"\n ) {\n throw new InvalidConfigurationError(\n path +\n '.scatteringModel must be \"provider-defined-wavelength-preserving\".'\n );\n }\n if (\n record.scientificStatus !==\n \"calibrated\" &&\n record.scientificStatus !==\n \"approximation\"\n ) {\n throw new InvalidConfigurationError(\n path + \".scientificStatus is invalid.\"\n );\n }\n const scientificStatus =\n record.scientificStatus;\n const wavelengthBasis =\n parseSpectralWavelengthBasis(\n record.wavelengthBasis,\n path + \".wavelengthBasis\"\n );\n const uncertainty = parseUncertainty(\n record.uncertainty,\n path + \".uncertainty\"\n );\n if (\n scientificStatus === \"calibrated\" &&\n wavelengthBasis === \"unspecified\"\n ) {\n throw new InvalidConfigurationError(\n path +\n \" calibrated spectral material data requires an air or vacuum wavelength basis.\"\n );\n }\n if (\n scientificStatus === \"calibrated\" &&\n uncertainty.kind !== \"relative\"\n ) {\n throw new InvalidConfigurationError(\n path +\n \" calibrated spectral material data requires quantified relative uncertainty.\"\n );\n }\n if (\n record.wavelengthChangingBehaviorModeled !==\n false\n ) {\n throw new InvalidConfigurationError(\n path +\n \".wavelengthChangingBehaviorModeled must be false in schema 0.1.0.\"\n );\n }\n if (record.emissionModeled !== false) {\n throw new InvalidConfigurationError(\n path +\n \".emissionModeled must be false in schema 0.1.0.\"\n );\n }\n\n return {\n kind:\n \"spectral-wavelength-preserving-data\",\n dataArtifact: parseArtifact(\n record.dataArtifact,\n path + \".dataArtifact\"\n ),\n wavelengthBasis,\n wavelengthRangeNanometers:\n parseSpectralWavelengthRangeNanometers(\n record.wavelengthRangeNanometers,\n path + \".wavelengthRangeNanometers\"\n ),\n scatteringModel:\n \"provider-defined-wavelength-preserving\",\n scientificStatus,\n uncertainty,\n wavelengthChangingBehaviorModeled:\n false,\n emissionModeled: false\n };\n}\n\n/**\n * Parses material-response metadata used by a scene-radiance provider.\n *\n * RGB or PBR (physically based rendering) material data is always an approximation.\n * Spectral data is a per-wavelength provider input. It does not itself compute a BSDF\n * (how a surface scatters light), scene radiance, fluorescence, emission, volumetric\n * effects or polarization.\n */\nexport function parseSceneMaterialResponseProfile(\n value: unknown\n): SceneMaterialResponseProfile {\n const record = requireRecord(\n value,\n \"sceneMaterialResponseProfile\", [\"schemaVersion\", \"materials\", \"fluorescenceModeled\", \"volumetricMaterialTransportModeled\", \"polarizationModeled\", \"profileId\", \"sceneId\", \"evidence\"]\n );\n if (\n record.schemaVersion !==\n SCENE_MATERIAL_RESPONSE_PROFILE_SCHEMA_VERSION\n ) {\n throw new InvalidConfigurationError(\n 'sceneMaterialResponseProfile.schemaVersion must be \"' +\n SCENE_MATERIAL_RESPONSE_PROFILE_SCHEMA_VERSION +\n '\".'\n );\n }\n if (!Array.isArray(record.materials)) {\n throw new InvalidConfigurationError(\n \"sceneMaterialResponseProfile.materials must be an array.\"\n );\n }\n\n const materials = record.materials.map(\n (entry, index) => {\n const path =\n \"sceneMaterialResponseProfile.materials[\" +\n index +\n \"]\";\n const material = requireRecord(\n entry,\n path, [\"materialResponseId\", \"evidence\", \"representation\"]\n );\n return {\n materialResponseId:\n requireNonEmptyString(\n material.materialResponseId,\n path + \".materialResponseId\"\n ),\n evidence: parseEvidenceList(\n material.evidence,\n path + \".evidence\"\n ),\n representation:\n parseMaterialRepresentation(\n material.representation,\n path + \".representation\"\n )\n };\n }\n );\n const ids = materials.map(\n (entry) => entry.materialResponseId\n );\n if (new Set(ids).size !== ids.length) {\n throw new InvalidConfigurationError(\n \"sceneMaterialResponseProfile.materials[].materialResponseId must not contain duplicates.\"\n );\n }\n\n if (record.fluorescenceModeled !== false) {\n throw new InvalidConfigurationError(\n \"sceneMaterialResponseProfile.fluorescenceModeled must be false in schema 0.1.0.\"\n );\n }\n if (\n record.volumetricMaterialTransportModeled !==\n false\n ) {\n throw new InvalidConfigurationError(\n \"sceneMaterialResponseProfile.volumetricMaterialTransportModeled must be false in schema 0.1.0.\"\n );\n }\n if (record.polarizationModeled !== false) {\n throw new InvalidConfigurationError(\n \"sceneMaterialResponseProfile.polarizationModeled must be false in schema 0.1.0.\"\n );\n }\n\n return {\n schemaVersion:\n SCENE_MATERIAL_RESPONSE_PROFILE_SCHEMA_VERSION,\n profileId: requireNonEmptyString(\n record.profileId,\n \"sceneMaterialResponseProfile.profileId\"\n ),\n sceneId: requireNonEmptyString(\n record.sceneId,\n \"sceneMaterialResponseProfile.sceneId\"\n ),\n evidence: parseEvidenceList(\n record.evidence,\n \"sceneMaterialResponseProfile.evidence\"\n ),\n materials,\n fluorescenceModeled: false,\n volumetricMaterialTransportModeled:\n false,\n polarizationModeled: false\n };\n}\n\n/**\n * Returns the material fidelity a profile supports, choosing the lower level when in doubt.\n */\nexport function assessSceneMaterialResponseFidelity(\n profile: SceneMaterialResponseProfile\n): SceneMaterialResponseFidelity {\n requireInputObject(profile, \"assessSceneMaterialResponseFidelity input\");\n // 2.0.0: the whole profile is validated, so an unknown field at any level is rejected.\n parseSceneMaterialResponseProfile(profile);\n requireInputArray(profile.materials, \"profile.materials\");\n if (\n profile.materials.some(\n (entry) =>\n entry.representation.kind ===\n \"unresolved\"\n )\n ) {\n return \"unresolved\";\n }\n\n const kinds = new Set(\n profile.materials.map(\n (entry) => entry.representation.kind\n )\n );\n if (\n kinds.size === 0 ||\n kinds.has(\"unresolved\")\n ) {\n return \"unresolved\";\n }\n if (\n kinds.size === 1 &&\n kinds.has(\n \"spectral-wavelength-preserving-data\"\n )\n ) {\n return \"spectral-data\";\n }\n if (\n kinds.size === 1 &&\n kinds.has(\"rgb-pbr-approximation\")\n ) {\n return \"rgb-pbr-approximation\";\n }\n return \"mixed\";\n}\n\nfunction parseProviderFidelity(\n value: unknown,\n path: string\n): SceneRadianceProviderProfile[\"fidelity\"] {\n const record = requireRecord(value, path, [\"spectral\", \"material\", \"visibility\", \"directTransport\", \"indirectTransport\"]);\n const spectral = record.spectral;\n if (\n spectral !== \"wavelength-resolved\" &&\n spectral !==\n \"rgb-derived-approximation\"\n ) {\n throw new InvalidConfigurationError(\n path + \".spectral is invalid.\"\n );\n }\n const material = record.material;\n if (\n material !== \"spectral-data\" &&\n material !== \"rgb-pbr-approximation\" &&\n material !== \"mixed\" &&\n material !== \"unresolved\"\n ) {\n throw new InvalidConfigurationError(\n path + \".material is invalid.\"\n );\n }\n const parseVisibility = (\n candidate: unknown,\n candidatePath: string\n ): SceneRadianceProviderVisibilityFidelity => {\n if (\n candidate !== \"resolved\" &&\n candidate !== \"approximation\" &&\n candidate !== \"not-modeled\"\n ) {\n throw new InvalidConfigurationError(\n candidatePath + \" is invalid.\"\n );\n }\n return candidate;\n };\n const parseTransport = (\n candidate: unknown,\n candidatePath: string\n ): SceneRadianceProviderTransportFidelity => {\n if (\n candidate !== \"resolved\" &&\n candidate !== \"approximation\" &&\n candidate !== \"not-modeled\"\n ) {\n throw new InvalidConfigurationError(\n candidatePath + \" is invalid.\"\n );\n }\n return candidate;\n };\n\n return {\n spectral,\n material,\n visibility: parseVisibility(\n record.visibility,\n path + \".visibility\"\n ),\n directTransport: parseTransport(\n record.directTransport,\n path + \".directTransport\"\n ),\n indirectTransport: parseTransport(\n record.indirectTransport,\n path + \".indirectTransport\"\n )\n };\n}\n\n/**\n * Parses a provider's declaration of what it can do (its profile). Works with any renderer.\n *\n * Schema 0.1.0 is approximation-only by design. A provider may use calibrated inputs,\n * but this contract cannot support a claim of calibrated outgoing radiance. That needs\n * later work on complete spectral and light-transport models.\n */\nexport function parseSceneRadianceProviderProfile(\n value: unknown\n): SceneRadianceProviderProfile {\n const record = requireRecord(\n value,\n \"sceneRadianceProviderProfile\", [\"schemaVersion\", \"outputQuantity\", \"outputUnit\", \"scientificStatus\", \"wavelengthChangingTransportModeled\", \"volumetricTransportModeled\", \"polarizationModeled\", \"profileId\", \"sceneId\", \"illuminationProfileId\", \"illuminationTemporalProfileId\", \"materialResponseProfileId\", \"uncertainty\", \"fidelity\", \"evidence\", \"limitations\"]\n );\n if (\n record.schemaVersion !==\n SCENE_RADIANCE_PROVIDER_PROFILE_SCHEMA_VERSION\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceProviderProfile.schemaVersion must be \"' +\n SCENE_RADIANCE_PROVIDER_PROFILE_SCHEMA_VERSION +\n '\".'\n );\n }\n if (\n record.outputQuantity !==\n \"outgoing-spectral-radiance\"\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceProviderProfile.outputQuantity must be \"outgoing-spectral-radiance\".'\n );\n }\n if (record.outputUnit !== \"W/m^2/sr/nm\") {\n throw new InvalidConfigurationError(\n 'sceneRadianceProviderProfile.outputUnit must be \"W/m^2/sr/nm\".'\n );\n }\n if (\n record.scientificStatus !==\n \"approximation\"\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceProviderProfile.scientificStatus must be \"approximation\" in schema 0.1.0.'\n );\n }\n if (\n record.wavelengthChangingTransportModeled !==\n false ||\n record.volumetricTransportModeled !==\n false ||\n record.polarizationModeled !== false\n ) {\n throw new InvalidConfigurationError(\n \"sceneRadianceProviderProfile wavelength-changing, volumetric, and polarization transport flags must all be false in schema 0.1.0.\"\n );\n }\n\n return {\n schemaVersion:\n SCENE_RADIANCE_PROVIDER_PROFILE_SCHEMA_VERSION,\n profileId: requireNonEmptyString(\n record.profileId,\n \"sceneRadianceProviderProfile.profileId\"\n ),\n sceneId: requireNonEmptyString(\n record.sceneId,\n \"sceneRadianceProviderProfile.sceneId\"\n ),\n illuminationProfileId:\n requireNonEmptyString(\n record.illuminationProfileId,\n \"sceneRadianceProviderProfile.illuminationProfileId\"\n ),\n ...(record.illuminationTemporalProfileId ===\n undefined\n ? {}\n : {\n illuminationTemporalProfileId:\n requireNonEmptyString(\n record.illuminationTemporalProfileId,\n \"sceneRadianceProviderProfile.illuminationTemporalProfileId\"\n )\n }),\n materialResponseProfileId:\n requireNonEmptyString(\n record.materialResponseProfileId,\n \"sceneRadianceProviderProfile.materialResponseProfileId\"\n ),\n outputQuantity:\n \"outgoing-spectral-radiance\",\n outputUnit: \"W/m^2/sr/nm\",\n scientificStatus: \"approximation\",\n uncertainty: parseUncertainty(\n record.uncertainty,\n \"sceneRadianceProviderProfile.uncertainty\"\n ),\n fidelity: parseProviderFidelity(\n record.fidelity,\n \"sceneRadianceProviderProfile.fidelity\"\n ),\n wavelengthChangingTransportModeled:\n false,\n volumetricTransportModeled: false,\n polarizationModeled: false,\n evidence: parseEvidenceList(\n record.evidence,\n \"sceneRadianceProviderProfile.evidence\"\n ),\n limitations: parseLimitations(\n record.limitations,\n \"sceneRadianceProviderProfile.limitations\"\n )\n };\n}\n\nfunction parsePositiveWavelengthNanometers(\n value: unknown,\n path: string\n): number {\n const wavelength = requireFinite(\n value,\n path\n );\n if (wavelength <= 0) {\n throw new InvalidConfigurationError(\n path + \" must be greater than zero.\"\n );\n }\n return wavelength;\n}\n\nfunction parseResolvedWavelengthBasis(\n value: unknown,\n path: string\n): Exclude<\n SpectralWavelengthBasis,\n \"unspecified\"\n> {\n const basis = parseSpectralWavelengthBasis(\n value,\n path\n );\n if (basis === \"unspecified\") {\n throw new InvalidConfigurationError(\n path +\n \" must be air or vacuum for outgoing spectral radiance.\"\n );\n }\n return basis;\n}\n\nfunction parseEvaluationTarget(\n value: unknown,\n path: string\n): SceneRadianceEvaluationTarget {\n const record = requireRecord(value, path, null);\n rejectUnknownVariantFields(record, \"kind\", {\n \"surface-point\": [\"kind\", \"sceneObjectId\", \"materialResponseId\", \"positionM\", \"outgoingDirectionUnitVector\"],\n \"environment-direction\": [\"kind\", \"outgoingDirectionUnitVector\"]\n }, path);\n if (record.kind === \"surface-point\") {\n return {\n kind: \"surface-point\",\n sceneObjectId: requireNonEmptyString(\n record.sceneObjectId,\n path + \".sceneObjectId\"\n ),\n materialResponseId:\n requireNonEmptyString(\n record.materialResponseId,\n path + \".materialResponseId\"\n ),\n positionM: parseVector3(\n record.positionM,\n path + \".positionM\"\n ),\n outgoingDirectionUnitVector:\n parseUnitDirection(\n record.outgoingDirectionUnitVector,\n path +\n \".outgoingDirectionUnitVector\"\n )\n };\n }\n if (\n record.kind ===\n \"environment-direction\"\n ) {\n return {\n kind: \"environment-direction\",\n outgoingDirectionUnitVector:\n parseUnitDirection(\n record.outgoingDirectionUnitVector,\n path +\n \".outgoingDirectionUnitVector\"\n )\n };\n }\n throw new InvalidConfigurationError(\n path + \".kind is invalid.\"\n );\n}\n\n/**\n * Parses one provider evaluation request at an explicit scene target,\n * physical time, wavelength, and outgoing direction.\n */\nexport function parseSceneRadianceEvaluationRequest(\n value: unknown\n): SceneRadianceEvaluationRequest {\n const record = requireRecord(\n value,\n \"sceneRadianceEvaluationRequest\", [\"schemaVersion\", \"sampleId\", \"providerProfileId\", \"sceneId\", \"illuminationProfileId\", \"materialResponseProfileId\", \"target\", \"timeSecondsFromExposureStart\", \"wavelengthNanometers\", \"wavelengthBasis\"]\n );\n if (\n record.schemaVersion !==\n SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceEvaluationRequest.schemaVersion must be \"' +\n SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION +\n '\".'\n );\n }\n\n return {\n schemaVersion:\n SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION,\n sampleId: requireNonEmptyString(\n record.sampleId,\n \"sceneRadianceEvaluationRequest.sampleId\"\n ),\n providerProfileId:\n requireNonEmptyString(\n record.providerProfileId,\n \"sceneRadianceEvaluationRequest.providerProfileId\"\n ),\n sceneId: requireNonEmptyString(\n record.sceneId,\n \"sceneRadianceEvaluationRequest.sceneId\"\n ),\n illuminationProfileId:\n requireNonEmptyString(\n record.illuminationProfileId,\n \"sceneRadianceEvaluationRequest.illuminationProfileId\"\n ),\n materialResponseProfileId:\n requireNonEmptyString(\n record.materialResponseProfileId,\n \"sceneRadianceEvaluationRequest.materialResponseProfileId\"\n ),\n target: parseEvaluationTarget(\n record.target,\n \"sceneRadianceEvaluationRequest.target\"\n ),\n timeSecondsFromExposureStart:\n requireNonNegativeFinite(\n record.timeSecondsFromExposureStart,\n \"sceneRadianceEvaluationRequest.timeSecondsFromExposureStart\"\n ),\n wavelengthNanometers:\n parsePositiveWavelengthNanometers(\n record.wavelengthNanometers,\n \"sceneRadianceEvaluationRequest.wavelengthNanometers\"\n ),\n wavelengthBasis:\n parseResolvedWavelengthBasis(\n record.wavelengthBasis,\n \"sceneRadianceEvaluationRequest.wavelengthBasis\"\n )\n };\n}\n\n/**\n * Parses one outgoing spectral-radiance result from a provider.\n *\n * The number is accepted as the provider reported it. Parsing checks units, that the\n * value is finite and nonnegative, provenance and identity fields. It does not prove\n * the provider's light-transport calculation is physically correct.\n */\nexport function parseSceneRadianceEvaluationResult(\n value: unknown\n): SceneRadianceEvaluationResult {\n const record = requireRecord(\n value,\n \"sceneRadianceEvaluationResult\", SCENE_RADIANCE_EVALUATION_RESULT_KEYS\n );\n return parseSceneRadianceEvaluationResultRecord(record, undefined);\n}\n\nconst SCENE_RADIANCE_EVALUATION_RESULT_KEYS = [\"schemaVersion\", \"quantity\", \"unit\", \"scientificStatus\", \"sampleId\", \"providerProfileId\", \"sceneId\", \"wavelengthNanometers\", \"wavelengthBasis\", \"spectralRadianceWattsPerSquareMeterSteradianNanometer\", \"uncertainty\", \"evidence\", \"limitations\"] as const;\n\n/** An earlier fully parsed result whose deep-frozen uncertainty, evidence and limitations records may be reused. */\nexport interface ValidatedSceneRadianceRecords {\n readonly uncertainty: unknown;\n readonly evidence: unknown;\n readonly limitations: unknown;\n readonly parsed: SceneRadianceEvaluationResult;\n}\n\n/**\n * Internal (2.6; not exported from the package): parses a result of an engine-built evaluator\n * (`isInternalSceneRadianceEvaluator`). It runs every check of `parseSceneRadianceEvaluationResult` with the same\n * helpers, order and messages (object shape, schema version, quantity, unit, status, the three identifiers, the\n * wavelength, its basis and the radiance value) except two: the scan for unknown keys, and re-parsing uncertainty,\n * evidence and limitations when they are the very (deep-frozen) objects of `validated`, an earlier result that\n * passed the full parse. Any other result takes the full parse.\n */\nexport function parseSceneRadianceEvaluationResultWithValidatedRecords(\n value: unknown,\n validated: ValidatedSceneRadianceRecords\n): SceneRadianceEvaluationResult {\n if (typeof value !== \"object\" || value === null || Array.isArray(value)) return parseSceneRadianceEvaluationResult(value);\n const record = value as UnknownRecord;\n if (record.uncertainty !== validated.uncertainty || record.evidence !== validated.evidence || record.limitations !== validated.limitations) {\n return parseSceneRadianceEvaluationResult(value);\n }\n return parseSceneRadianceEvaluationResultRecord(record, validated.parsed);\n}\n\nfunction parseSceneRadianceEvaluationResultRecord(\n record: UnknownRecord,\n validated: SceneRadianceEvaluationResult | undefined\n): SceneRadianceEvaluationResult {\n if (\n record.schemaVersion !==\n SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceEvaluationResult.schemaVersion must be \"' +\n SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION +\n '\".'\n );\n }\n if (\n record.quantity !==\n \"outgoing-spectral-radiance\"\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceEvaluationResult.quantity must be \"outgoing-spectral-radiance\".'\n );\n }\n if (record.unit !== \"W/m^2/sr/nm\") {\n throw new InvalidConfigurationError(\n 'sceneRadianceEvaluationResult.unit must be \"W/m^2/sr/nm\".'\n );\n }\n if (\n record.scientificStatus !==\n \"approximation\"\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceEvaluationResult.scientificStatus must be \"approximation\" in schema 0.1.0.'\n );\n }\n\n return {\n schemaVersion:\n SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION,\n sampleId: requireNonEmptyString(\n record.sampleId,\n \"sceneRadianceEvaluationResult.sampleId\"\n ),\n providerProfileId:\n requireNonEmptyString(\n record.providerProfileId,\n \"sceneRadianceEvaluationResult.providerProfileId\"\n ),\n sceneId: requireNonEmptyString(\n record.sceneId,\n \"sceneRadianceEvaluationResult.sceneId\"\n ),\n wavelengthNanometers:\n parsePositiveWavelengthNanometers(\n record.wavelengthNanometers,\n \"sceneRadianceEvaluationResult.wavelengthNanometers\"\n ),\n wavelengthBasis:\n parseResolvedWavelengthBasis(\n record.wavelengthBasis,\n \"sceneRadianceEvaluationResult.wavelengthBasis\"\n ),\n quantity:\n \"outgoing-spectral-radiance\",\n unit: \"W/m^2/sr/nm\",\n spectralRadianceWattsPerSquareMeterSteradianNanometer:\n requireNonNegativeFinite(\n record.spectralRadianceWattsPerSquareMeterSteradianNanometer,\n \"sceneRadianceEvaluationResult.spectralRadianceWattsPerSquareMeterSteradianNanometer\"\n ),\n scientificStatus: \"approximation\",\n uncertainty: validated ? validated.uncertainty : parseUncertainty(\n record.uncertainty,\n \"sceneRadianceEvaluationResult.uncertainty\"\n ),\n evidence: validated ? validated.evidence : parseEvidenceList(\n record.evidence,\n \"sceneRadianceEvaluationResult.evidence\"\n ),\n limitations: validated ? validated.limitations : parseLimitations(\n record.limitations,\n \"sceneRadianceEvaluationResult.limitations\"\n )\n };\n}\n\nfunction requireEqual(\n actual: unknown,\n expected: unknown,\n message: string\n): void {\n if (actual !== expected) {\n throw new InvalidConfigurationError(\n message\n );\n }\n}\n\n/**\n * Checks that a provider result matches its request and profile identities exactly.\n *\n * It never recomputes the radiance value, and never upgrades the provider's\n * approximation to calibrated radiometry.\n */\nexport function validateSceneRadianceEvaluationBindings(\n input:\n ValidateSceneRadianceEvaluationBindingsInput\n): SceneRadianceEvaluationBindingAssessment {\n requireInputKeys(input, \"validateSceneRadianceEvaluationBindings\", [\"providerProfile\", \"illuminationProfile\", \"illuminationTemporalProfile\", \"materialResponseProfile\", \"request\", \"result\"]);\n const {\n providerProfile,\n illuminationProfile,\n illuminationTemporalProfile,\n materialResponseProfile,\n request,\n result\n } = input;\n\n requireInputObject(providerProfile, \"providerProfile input\");\n requireEqual(\n providerProfile.sceneId,\n illuminationProfile.sceneId,\n \"Provider and illumination profiles must reference the same sceneId.\"\n );\n requireEqual(\n providerProfile.sceneId,\n materialResponseProfile.sceneId,\n \"Provider and material-response profiles must reference the same sceneId.\"\n );\n requireEqual(\n providerProfile.illuminationProfileId,\n illuminationProfile.profileId,\n \"Provider illuminationProfileId must match the supplied illumination profile.\"\n );\n requireEqual(\n providerProfile.materialResponseProfileId,\n materialResponseProfile.profileId,\n \"Provider materialResponseProfileId must match the supplied material-response profile.\"\n );\n\n if (\n providerProfile\n .illuminationTemporalProfileId ===\n undefined\n ) {\n if (\n illuminationTemporalProfile !==\n undefined\n ) {\n throw new InvalidConfigurationError(\n \"A temporal illumination profile was supplied but the provider profile does not bind one.\"\n );\n }\n } else {\n if (\n illuminationTemporalProfile ===\n undefined\n ) {\n throw new InvalidConfigurationError(\n \"Provider illuminationTemporalProfileId requires the matching temporal illumination profile.\"\n );\n }\n requireEqual(\n providerProfile\n .illuminationTemporalProfileId,\n illuminationTemporalProfile\n .profileId,\n \"Provider illuminationTemporalProfileId must match the supplied temporal illumination profile.\"\n );\n requireEqual(\n providerProfile.sceneId,\n illuminationTemporalProfile.sceneId,\n \"Provider and temporal illumination profiles must reference the same sceneId.\"\n );\n requireEqual(\n providerProfile\n .illuminationProfileId,\n illuminationTemporalProfile\n .illuminationProfileId,\n \"Temporal illumination profile must bind the provider's illuminationProfileId.\"\n );\n }\n\n const materialResponseFidelity =\n assessSceneMaterialResponseFidelity(\n materialResponseProfile\n );\n requireEqual(\n providerProfile.fidelity.material,\n materialResponseFidelity,\n \"Provider material fidelity must match the supplied material-response profile.\"\n );\n\n requireEqual(\n request.providerProfileId,\n providerProfile.profileId,\n \"Request providerProfileId must match the supplied provider profile.\"\n );\n requireEqual(\n request.sceneId,\n providerProfile.sceneId,\n \"Request sceneId must match the supplied provider profile.\"\n );\n requireEqual(\n request.illuminationProfileId,\n illuminationProfile.profileId,\n \"Request illuminationProfileId must match the supplied illumination profile.\"\n );\n requireEqual(\n request.materialResponseProfileId,\n materialResponseProfile.profileId,\n \"Request materialResponseProfileId must match the supplied material-response profile.\"\n );\n\n if (request.target.kind === \"surface-point\") {\n const target = request.target;\n if (\n !materialResponseProfile.materials.some(\n (material) =>\n material.materialResponseId ===\n target.materialResponseId\n )\n ) {\n throw new InvalidConfigurationError(\n \"Request surface target materialResponseId is not declared by the supplied material-response profile.\"\n );\n }\n }\n\n requireEqual(\n result.sampleId,\n request.sampleId,\n \"Result sampleId must match the request.\"\n );\n requireEqual(\n result.providerProfileId,\n request.providerProfileId,\n \"Result providerProfileId must match the request.\"\n );\n requireEqual(\n result.sceneId,\n request.sceneId,\n \"Result sceneId must match the request.\"\n );\n requireEqual(\n result.wavelengthNanometers,\n request.wavelengthNanometers,\n \"Result wavelengthNanometers must match the request exactly.\"\n );\n requireEqual(\n result.wavelengthBasis,\n request.wavelengthBasis,\n \"Result wavelengthBasis must match the request.\"\n );\n\n return {\n providerBindingsMatched: true,\n requestResultIdentityMatched: true,\n materialResponseFidelity,\n temporalIlluminationProfileBound:\n illuminationTemporalProfile !==\n undefined,\n calibratedRadianceClaimAuthorized: false,\n sensorPlaneIrradianceCalculated:\n false,\n opticsApplied: false,\n photonsCalculated: false\n };\n}\n"]}
1
+ {"version":3,"file":"scene-radiance.js","sourceRoot":"","sources":["../../src/schema/scene-radiance.ts"],"names":[],"mappings":"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","sourcesContent":["// SPDX-License-Identifier: Apache-2.0\n\n/**\n * Contracts for scene-radiance providers: the renderer or other code that reports how much\n * light leaves a scene point toward the camera.\n *\n * It covers material-response metadata, provider capability profiles, single evaluation\n * requests and results, and identity checks between them. The engine validates this data\n * but does not compute scene radiance itself.\n * @see docs/SCENE_RADIANCE_AND_ILLUMINATION.md for equations, coordinate/unit conventions, blockers\n * and support limits.\n */\n\nimport { InvalidConfigurationError } from \"../core/configuration-error.js\";\nimport {\n parseEvidenceList,\n type EvidenceProvenance\n} from \"../core/evidence-provenance.js\";\nimport {\n parseSpectralWavelengthBasis,\n parseSpectralWavelengthRangeNanometers,\n type SpectralWavelengthBasis,\n type SpectralWavelengthRangeNanometers\n} from \"../core/spectral.js\";\nimport type {\n SceneIlluminationProfile\n} from \"./illumination.js\";\nimport type {\n SceneIlluminationTemporalProfile\n} from \"./illumination-temporal.js\";\nimport type { Vector3 } from \"./scene.js\";\nimport { requireInputObject, requireInputArray, requireInputKeys, rejectUnknownFields, rejectUnknownVariantFields, UNCERTAINTY_VARIANT_FIELDS } from \"../core/record-validation.js\";\nimport { hypot3 } from \"../core/portable-math.js\";\n\ntype UnknownRecord = Record<string, unknown>;\n\nexport const SCENE_MATERIAL_RESPONSE_PROFILE_SCHEMA_VERSION =\n \"0.1.0\" as const;\nexport const SCENE_RADIANCE_PROVIDER_PROFILE_SCHEMA_VERSION =\n \"0.1.0\" as const;\nexport const SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION =\n \"0.1.0\" as const;\n\nexport type SceneRadianceScientificStatus =\n | \"calibrated\"\n | \"approximation\";\n\nexport type SceneRadianceUncertainty =\n | {\n kind: \"relative\";\n fraction: number;\n basis: string;\n }\n | {\n kind: \"not-quantified\";\n limitation: string;\n };\n\nexport interface SceneRadianceDataArtifactReference {\n id: string;\n checksumSha256: string;\n}\n\nexport type SceneMaterialResponseRepresentation =\n | {\n kind: \"unresolved\";\n limitation: string;\n }\n | {\n kind: \"rgb-pbr-approximation\";\n colorSpace: \"linear-srgb\";\n baseColor: {\n red: number;\n green: number;\n blue: number;\n };\n metallic: number;\n roughness: number;\n limitation: string;\n }\n | {\n kind: \"spectral-wavelength-preserving-data\";\n dataArtifact:\n SceneRadianceDataArtifactReference;\n wavelengthBasis:\n SpectralWavelengthBasis;\n wavelengthRangeNanometers:\n SpectralWavelengthRangeNanometers;\n scatteringModel:\n \"provider-defined-wavelength-preserving\";\n scientificStatus:\n SceneRadianceScientificStatus;\n uncertainty:\n SceneRadianceUncertainty;\n wavelengthChangingBehaviorModeled: false;\n emissionModeled: false;\n };\n\nexport interface SceneMaterialResponseDefinition {\n materialResponseId: string;\n evidence: readonly EvidenceProvenance[];\n representation:\n SceneMaterialResponseRepresentation;\n}\n\nexport interface SceneMaterialResponseProfile {\n schemaVersion:\n typeof SCENE_MATERIAL_RESPONSE_PROFILE_SCHEMA_VERSION;\n profileId: string;\n sceneId: string;\n evidence: readonly EvidenceProvenance[];\n materials:\n readonly SceneMaterialResponseDefinition[];\n fluorescenceModeled: false;\n volumetricMaterialTransportModeled: false;\n polarizationModeled: false;\n}\n\nexport type SceneMaterialResponseFidelity =\n | \"spectral-data\"\n | \"rgb-pbr-approximation\"\n | \"mixed\"\n | \"unresolved\";\n\nexport type SceneRadianceProviderSpectralFidelity =\n | \"wavelength-resolved\"\n | \"rgb-derived-approximation\";\n\nexport type SceneRadianceProviderVisibilityFidelity =\n | \"resolved\"\n | \"approximation\"\n | \"not-modeled\";\n\nexport type SceneRadianceProviderTransportFidelity =\n | \"resolved\"\n | \"approximation\"\n | \"not-modeled\";\n\nexport interface SceneRadianceProviderProfile {\n schemaVersion:\n typeof SCENE_RADIANCE_PROVIDER_PROFILE_SCHEMA_VERSION;\n profileId: string;\n sceneId: string;\n illuminationProfileId: string;\n illuminationTemporalProfileId?: string;\n materialResponseProfileId: string;\n outputQuantity:\n \"outgoing-spectral-radiance\";\n outputUnit:\n \"W/m^2/sr/nm\";\n scientificStatus: \"approximation\";\n uncertainty: SceneRadianceUncertainty;\n fidelity: {\n spectral:\n SceneRadianceProviderSpectralFidelity;\n material:\n SceneMaterialResponseFidelity;\n visibility:\n SceneRadianceProviderVisibilityFidelity;\n directTransport:\n SceneRadianceProviderTransportFidelity;\n indirectTransport:\n SceneRadianceProviderTransportFidelity;\n };\n wavelengthChangingTransportModeled: false;\n volumetricTransportModeled: false;\n polarizationModeled: false;\n evidence: readonly EvidenceProvenance[];\n limitations: readonly string[];\n}\n\nexport type SceneRadianceEvaluationTarget =\n | {\n kind: \"surface-point\";\n sceneObjectId: string;\n materialResponseId: string;\n positionM: Vector3;\n outgoingDirectionUnitVector: Vector3;\n }\n | {\n kind: \"environment-direction\";\n outgoingDirectionUnitVector: Vector3;\n };\n\nexport interface SceneRadianceEvaluationRequest {\n schemaVersion:\n typeof SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION;\n sampleId: string;\n providerProfileId: string;\n sceneId: string;\n illuminationProfileId: string;\n materialResponseProfileId: string;\n target: SceneRadianceEvaluationTarget;\n timeSecondsFromExposureStart: number;\n wavelengthNanometers: number;\n wavelengthBasis:\n Exclude<SpectralWavelengthBasis, \"unspecified\">;\n}\n\nexport interface SceneRadianceEvaluationResult {\n schemaVersion:\n typeof SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION;\n sampleId: string;\n providerProfileId: string;\n sceneId: string;\n wavelengthNanometers: number;\n wavelengthBasis:\n Exclude<SpectralWavelengthBasis, \"unspecified\">;\n quantity:\n \"outgoing-spectral-radiance\";\n unit: \"W/m^2/sr/nm\";\n spectralRadianceWattsPerSquareMeterSteradianNanometer:\n number;\n scientificStatus: \"approximation\";\n uncertainty: SceneRadianceUncertainty;\n evidence: readonly EvidenceProvenance[];\n limitations: readonly string[];\n}\n\nexport interface ValidateSceneRadianceEvaluationBindingsInput {\n providerProfile: SceneRadianceProviderProfile;\n illuminationProfile: SceneIlluminationProfile;\n illuminationTemporalProfile?:\n SceneIlluminationTemporalProfile;\n materialResponseProfile:\n SceneMaterialResponseProfile;\n request: SceneRadianceEvaluationRequest;\n result: SceneRadianceEvaluationResult;\n}\n\nexport interface SceneRadianceEvaluationBindingAssessment {\n providerBindingsMatched: true;\n requestResultIdentityMatched: true;\n materialResponseFidelity:\n SceneMaterialResponseFidelity;\n temporalIlluminationProfileBound:\n boolean;\n calibratedRadianceClaimAuthorized: false;\n sensorPlaneIrradianceCalculated: false;\n opticsApplied: false;\n photonsCalculated: false;\n}\n\nfunction requireRecord(\n value: unknown,\n path: string,\n allowedKeys: readonly string[] | null\n): UnknownRecord {\n if (\n typeof value !== \"object\" ||\n value === null ||\n Array.isArray(value)\n ) {\n throw new InvalidConfigurationError(\n path + \" must be an object.\"\n );\n }\n if (allowedKeys !== null) rejectUnknownFields(value, allowedKeys, path);\n return value as UnknownRecord;\n}\n\nfunction requireNonEmptyString(\n value: unknown,\n path: string\n): string {\n if (\n typeof value !== \"string\" ||\n value.trim().length === 0\n ) {\n throw new InvalidConfigurationError(\n path + \" must be a non-empty string.\"\n );\n }\n return value.trim();\n}\n\nfunction requireFinite(\n value: unknown,\n path: string\n): number {\n if (\n typeof value !== \"number\" ||\n !Number.isFinite(value)\n ) {\n throw new InvalidConfigurationError(\n path + \" must be a finite number.\"\n );\n }\n return value;\n}\n\nfunction requireNonNegativeFinite(\n value: unknown,\n path: string\n): number {\n const number = requireFinite(value, path);\n if (number < 0) {\n throw new InvalidConfigurationError(\n path +\n \" must be greater than or equal to zero.\"\n );\n }\n return number;\n}\n\nfunction requireFraction(\n value: unknown,\n path: string\n): number {\n const number = requireFinite(value, path);\n if (number < 0 || number > 1) {\n throw new InvalidConfigurationError(\n path +\n \" must be a finite fraction from 0 through 1.\"\n );\n }\n return number;\n}\n\nfunction parseVector3(\n value: unknown,\n path: string\n): Vector3 {\n const record = requireRecord(value, path, [\"x\", \"y\", \"z\"]);\n return {\n x: requireFinite(record.x, path + \".x\"),\n y: requireFinite(record.y, path + \".y\"),\n z: requireFinite(record.z, path + \".z\")\n };\n}\n\nfunction parseUnitDirection(\n value: unknown,\n path: string\n): Vector3 {\n const vector = parseVector3(value, path);\n const length = hypot3(\n vector.x,\n vector.y,\n vector.z\n );\n if (\n !Number.isFinite(length) ||\n Math.abs(length - 1) > 1e-9\n ) {\n throw new InvalidConfigurationError(\n path +\n \" must be a unit-length direction vector.\"\n );\n }\n return vector;\n}\n\nfunction parseUncertainty(\n value: unknown,\n path: string\n): SceneRadianceUncertainty {\n const record = requireRecord(value, path, null);\n rejectUnknownVariantFields(record, \"kind\", UNCERTAINTY_VARIANT_FIELDS, path);\n if (record.kind === \"relative\") {\n return {\n kind: \"relative\",\n fraction: requireNonNegativeFinite(\n record.fraction,\n path + \".fraction\"\n ),\n basis: requireNonEmptyString(\n record.basis,\n path + \".basis\"\n )\n };\n }\n if (record.kind === \"not-quantified\") {\n return {\n kind: \"not-quantified\",\n limitation: requireNonEmptyString(\n record.limitation,\n path + \".limitation\"\n )\n };\n }\n throw new InvalidConfigurationError(\n path + \".kind is invalid.\"\n );\n}\n\nfunction parseLimitations(\n value: unknown,\n path: string\n): readonly string[] {\n if (!Array.isArray(value)) {\n throw new InvalidConfigurationError(\n path + \" must be an array.\"\n );\n }\n const limitations = value.map(\n (entry, index) =>\n requireNonEmptyString(\n entry,\n path + \"[\" + index + \"]\"\n )\n );\n if (\n new Set(limitations).size !==\n limitations.length\n ) {\n throw new InvalidConfigurationError(\n path + \" must not contain duplicates.\"\n );\n }\n return limitations;\n}\n\nfunction parseArtifact(\n value: unknown,\n path: string\n): SceneRadianceDataArtifactReference {\n const record = requireRecord(value, path, [\"checksumSha256\", \"id\"]);\n const checksumSha256 =\n requireNonEmptyString(\n record.checksumSha256,\n path + \".checksumSha256\"\n );\n if (\n !/^[a-f0-9]{64}$/iu.test(\n checksumSha256\n )\n ) {\n throw new InvalidConfigurationError(\n path +\n \".checksumSha256 must be a 64-character SHA-256 hex digest.\"\n );\n }\n return {\n id: requireNonEmptyString(\n record.id,\n path + \".id\"\n ),\n checksumSha256:\n checksumSha256.toLowerCase()\n };\n}\n\nfunction parseMaterialRepresentation(\n value: unknown,\n path: string\n): SceneMaterialResponseRepresentation {\n const record = requireRecord(value, path, null);\n rejectUnknownVariantFields(record, \"kind\", {\n unresolved: [\"kind\", \"limitation\"],\n \"rgb-pbr-approximation\": [\"kind\", \"colorSpace\", \"baseColor\", \"metallic\", \"roughness\", \"limitation\"],\n \"spectral-wavelength-preserving-data\": [\"kind\", \"dataArtifact\", \"wavelengthBasis\", \"wavelengthRangeNanometers\", \"scatteringModel\",\n \"scientificStatus\", \"uncertainty\", \"wavelengthChangingBehaviorModeled\", \"emissionModeled\"]\n }, path);\n\n if (record.kind === \"unresolved\") {\n return {\n kind: \"unresolved\",\n limitation: requireNonEmptyString(\n record.limitation,\n path + \".limitation\"\n )\n };\n }\n\n if (\n record.kind ===\n \"rgb-pbr-approximation\"\n ) {\n if (record.colorSpace !== \"linear-srgb\") {\n throw new InvalidConfigurationError(\n path +\n '.colorSpace must be \"linear-srgb\".'\n );\n }\n const baseColor = requireRecord(\n record.baseColor,\n path + \".baseColor\", [\"red\", \"green\", \"blue\"]\n );\n return {\n kind: \"rgb-pbr-approximation\",\n colorSpace: \"linear-srgb\",\n baseColor: {\n red: requireFraction(\n baseColor.red,\n path + \".baseColor.red\"\n ),\n green: requireFraction(\n baseColor.green,\n path + \".baseColor.green\"\n ),\n blue: requireFraction(\n baseColor.blue,\n path + \".baseColor.blue\"\n )\n },\n metallic: requireFraction(\n record.metallic,\n path + \".metallic\"\n ),\n roughness: requireFraction(\n record.roughness,\n path + \".roughness\"\n ),\n limitation: requireNonEmptyString(\n record.limitation,\n path + \".limitation\"\n )\n };\n }\n\n if (\n record.kind !==\n \"spectral-wavelength-preserving-data\"\n ) {\n throw new InvalidConfigurationError(\n path + \".kind is invalid.\"\n );\n }\n\n if (\n record.scatteringModel !==\n \"provider-defined-wavelength-preserving\"\n ) {\n throw new InvalidConfigurationError(\n path +\n '.scatteringModel must be \"provider-defined-wavelength-preserving\".'\n );\n }\n if (\n record.scientificStatus !==\n \"calibrated\" &&\n record.scientificStatus !==\n \"approximation\"\n ) {\n throw new InvalidConfigurationError(\n path + \".scientificStatus is invalid.\"\n );\n }\n const scientificStatus =\n record.scientificStatus;\n const wavelengthBasis =\n parseSpectralWavelengthBasis(\n record.wavelengthBasis,\n path + \".wavelengthBasis\"\n );\n const uncertainty = parseUncertainty(\n record.uncertainty,\n path + \".uncertainty\"\n );\n if (\n scientificStatus === \"calibrated\" &&\n wavelengthBasis === \"unspecified\"\n ) {\n throw new InvalidConfigurationError(\n path +\n \" calibrated spectral material data requires an air or vacuum wavelength basis.\"\n );\n }\n if (\n scientificStatus === \"calibrated\" &&\n uncertainty.kind !== \"relative\"\n ) {\n throw new InvalidConfigurationError(\n path +\n \" calibrated spectral material data requires quantified relative uncertainty.\"\n );\n }\n if (\n record.wavelengthChangingBehaviorModeled !==\n false\n ) {\n throw new InvalidConfigurationError(\n path +\n \".wavelengthChangingBehaviorModeled must be false in schema 0.1.0.\"\n );\n }\n if (record.emissionModeled !== false) {\n throw new InvalidConfigurationError(\n path +\n \".emissionModeled must be false in schema 0.1.0.\"\n );\n }\n\n return {\n kind:\n \"spectral-wavelength-preserving-data\",\n dataArtifact: parseArtifact(\n record.dataArtifact,\n path + \".dataArtifact\"\n ),\n wavelengthBasis,\n wavelengthRangeNanometers:\n parseSpectralWavelengthRangeNanometers(\n record.wavelengthRangeNanometers,\n path + \".wavelengthRangeNanometers\"\n ),\n scatteringModel:\n \"provider-defined-wavelength-preserving\",\n scientificStatus,\n uncertainty,\n wavelengthChangingBehaviorModeled:\n false,\n emissionModeled: false\n };\n}\n\n/**\n * Parses material-response metadata used by a scene-radiance provider.\n *\n * RGB or PBR (physically based rendering) material data is always an approximation.\n * Spectral data is a per-wavelength provider input. It does not itself compute a BSDF\n * (how a surface scatters light), scene radiance, fluorescence, emission, volumetric\n * effects or polarization.\n */\nexport function parseSceneMaterialResponseProfile(\n value: unknown\n): SceneMaterialResponseProfile {\n const record = requireRecord(\n value,\n \"sceneMaterialResponseProfile\", [\"schemaVersion\", \"materials\", \"fluorescenceModeled\", \"volumetricMaterialTransportModeled\", \"polarizationModeled\", \"profileId\", \"sceneId\", \"evidence\"]\n );\n if (\n record.schemaVersion !==\n SCENE_MATERIAL_RESPONSE_PROFILE_SCHEMA_VERSION\n ) {\n throw new InvalidConfigurationError(\n 'sceneMaterialResponseProfile.schemaVersion must be \"' +\n SCENE_MATERIAL_RESPONSE_PROFILE_SCHEMA_VERSION +\n '\".'\n );\n }\n if (!Array.isArray(record.materials)) {\n throw new InvalidConfigurationError(\n \"sceneMaterialResponseProfile.materials must be an array.\"\n );\n }\n\n const materials = record.materials.map(\n (entry, index) => {\n const path =\n \"sceneMaterialResponseProfile.materials[\" +\n index +\n \"]\";\n const material = requireRecord(\n entry,\n path, [\"materialResponseId\", \"evidence\", \"representation\"]\n );\n return {\n materialResponseId:\n requireNonEmptyString(\n material.materialResponseId,\n path + \".materialResponseId\"\n ),\n evidence: parseEvidenceList(\n material.evidence,\n path + \".evidence\"\n ),\n representation:\n parseMaterialRepresentation(\n material.representation,\n path + \".representation\"\n )\n };\n }\n );\n const ids = materials.map(\n (entry) => entry.materialResponseId\n );\n if (new Set(ids).size !== ids.length) {\n throw new InvalidConfigurationError(\n \"sceneMaterialResponseProfile.materials[].materialResponseId must not contain duplicates.\"\n );\n }\n\n if (record.fluorescenceModeled !== false) {\n throw new InvalidConfigurationError(\n \"sceneMaterialResponseProfile.fluorescenceModeled must be false in schema 0.1.0.\"\n );\n }\n if (\n record.volumetricMaterialTransportModeled !==\n false\n ) {\n throw new InvalidConfigurationError(\n \"sceneMaterialResponseProfile.volumetricMaterialTransportModeled must be false in schema 0.1.0.\"\n );\n }\n if (record.polarizationModeled !== false) {\n throw new InvalidConfigurationError(\n \"sceneMaterialResponseProfile.polarizationModeled must be false in schema 0.1.0.\"\n );\n }\n\n return {\n schemaVersion:\n SCENE_MATERIAL_RESPONSE_PROFILE_SCHEMA_VERSION,\n profileId: requireNonEmptyString(\n record.profileId,\n \"sceneMaterialResponseProfile.profileId\"\n ),\n sceneId: requireNonEmptyString(\n record.sceneId,\n \"sceneMaterialResponseProfile.sceneId\"\n ),\n evidence: parseEvidenceList(\n record.evidence,\n \"sceneMaterialResponseProfile.evidence\"\n ),\n materials,\n fluorescenceModeled: false,\n volumetricMaterialTransportModeled:\n false,\n polarizationModeled: false\n };\n}\n\n/**\n * Returns the material fidelity a profile supports, choosing the lower level when in doubt.\n */\nexport function assessSceneMaterialResponseFidelity(\n profile: SceneMaterialResponseProfile\n): SceneMaterialResponseFidelity {\n requireInputObject(profile, \"assessSceneMaterialResponseFidelity input\");\n // 2.0.0: the whole profile is validated, so an unknown field at any level is rejected.\n parseSceneMaterialResponseProfile(profile);\n requireInputArray(profile.materials, \"profile.materials\");\n if (\n profile.materials.some(\n (entry) =>\n entry.representation.kind ===\n \"unresolved\"\n )\n ) {\n return \"unresolved\";\n }\n\n const kinds = new Set(\n profile.materials.map(\n (entry) => entry.representation.kind\n )\n );\n if (\n kinds.size === 0 ||\n kinds.has(\"unresolved\")\n ) {\n return \"unresolved\";\n }\n if (\n kinds.size === 1 &&\n kinds.has(\n \"spectral-wavelength-preserving-data\"\n )\n ) {\n return \"spectral-data\";\n }\n if (\n kinds.size === 1 &&\n kinds.has(\"rgb-pbr-approximation\")\n ) {\n return \"rgb-pbr-approximation\";\n }\n return \"mixed\";\n}\n\nfunction parseProviderFidelity(\n value: unknown,\n path: string\n): SceneRadianceProviderProfile[\"fidelity\"] {\n const record = requireRecord(value, path, [\"spectral\", \"material\", \"visibility\", \"directTransport\", \"indirectTransport\"]);\n const spectral = record.spectral;\n if (\n spectral !== \"wavelength-resolved\" &&\n spectral !==\n \"rgb-derived-approximation\"\n ) {\n throw new InvalidConfigurationError(\n path + \".spectral is invalid.\"\n );\n }\n const material = record.material;\n if (\n material !== \"spectral-data\" &&\n material !== \"rgb-pbr-approximation\" &&\n material !== \"mixed\" &&\n material !== \"unresolved\"\n ) {\n throw new InvalidConfigurationError(\n path + \".material is invalid.\"\n );\n }\n const parseVisibility = (\n candidate: unknown,\n candidatePath: string\n ): SceneRadianceProviderVisibilityFidelity => {\n if (\n candidate !== \"resolved\" &&\n candidate !== \"approximation\" &&\n candidate !== \"not-modeled\"\n ) {\n throw new InvalidConfigurationError(\n candidatePath + \" is invalid.\"\n );\n }\n return candidate;\n };\n const parseTransport = (\n candidate: unknown,\n candidatePath: string\n ): SceneRadianceProviderTransportFidelity => {\n if (\n candidate !== \"resolved\" &&\n candidate !== \"approximation\" &&\n candidate !== \"not-modeled\"\n ) {\n throw new InvalidConfigurationError(\n candidatePath + \" is invalid.\"\n );\n }\n return candidate;\n };\n\n return {\n spectral,\n material,\n visibility: parseVisibility(\n record.visibility,\n path + \".visibility\"\n ),\n directTransport: parseTransport(\n record.directTransport,\n path + \".directTransport\"\n ),\n indirectTransport: parseTransport(\n record.indirectTransport,\n path + \".indirectTransport\"\n )\n };\n}\n\n/**\n * Parses a provider's declaration of what it can do (its profile). Works with any renderer.\n *\n * Schema 0.1.0 is approximation-only by design. A provider may use calibrated inputs,\n * but this contract cannot support a claim of calibrated outgoing radiance. That needs\n * later work on complete spectral and light-transport models.\n */\nexport function parseSceneRadianceProviderProfile(\n value: unknown\n): SceneRadianceProviderProfile {\n const record = requireRecord(\n value,\n \"sceneRadianceProviderProfile\", [\"schemaVersion\", \"outputQuantity\", \"outputUnit\", \"scientificStatus\", \"wavelengthChangingTransportModeled\", \"volumetricTransportModeled\", \"polarizationModeled\", \"profileId\", \"sceneId\", \"illuminationProfileId\", \"illuminationTemporalProfileId\", \"materialResponseProfileId\", \"uncertainty\", \"fidelity\", \"evidence\", \"limitations\"]\n );\n if (\n record.schemaVersion !==\n SCENE_RADIANCE_PROVIDER_PROFILE_SCHEMA_VERSION\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceProviderProfile.schemaVersion must be \"' +\n SCENE_RADIANCE_PROVIDER_PROFILE_SCHEMA_VERSION +\n '\".'\n );\n }\n if (\n record.outputQuantity !==\n \"outgoing-spectral-radiance\"\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceProviderProfile.outputQuantity must be \"outgoing-spectral-radiance\".'\n );\n }\n if (record.outputUnit !== \"W/m^2/sr/nm\") {\n throw new InvalidConfigurationError(\n 'sceneRadianceProviderProfile.outputUnit must be \"W/m^2/sr/nm\".'\n );\n }\n if (\n record.scientificStatus !==\n \"approximation\"\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceProviderProfile.scientificStatus must be \"approximation\" in schema 0.1.0.'\n );\n }\n if (\n record.wavelengthChangingTransportModeled !==\n false ||\n record.volumetricTransportModeled !==\n false ||\n record.polarizationModeled !== false\n ) {\n throw new InvalidConfigurationError(\n \"sceneRadianceProviderProfile wavelength-changing, volumetric, and polarization transport flags must all be false in schema 0.1.0.\"\n );\n }\n\n return {\n schemaVersion:\n SCENE_RADIANCE_PROVIDER_PROFILE_SCHEMA_VERSION,\n profileId: requireNonEmptyString(\n record.profileId,\n \"sceneRadianceProviderProfile.profileId\"\n ),\n sceneId: requireNonEmptyString(\n record.sceneId,\n \"sceneRadianceProviderProfile.sceneId\"\n ),\n illuminationProfileId:\n requireNonEmptyString(\n record.illuminationProfileId,\n \"sceneRadianceProviderProfile.illuminationProfileId\"\n ),\n ...(record.illuminationTemporalProfileId ===\n undefined\n ? {}\n : {\n illuminationTemporalProfileId:\n requireNonEmptyString(\n record.illuminationTemporalProfileId,\n \"sceneRadianceProviderProfile.illuminationTemporalProfileId\"\n )\n }),\n materialResponseProfileId:\n requireNonEmptyString(\n record.materialResponseProfileId,\n \"sceneRadianceProviderProfile.materialResponseProfileId\"\n ),\n outputQuantity:\n \"outgoing-spectral-radiance\",\n outputUnit: \"W/m^2/sr/nm\",\n scientificStatus: \"approximation\",\n uncertainty: parseUncertainty(\n record.uncertainty,\n \"sceneRadianceProviderProfile.uncertainty\"\n ),\n fidelity: parseProviderFidelity(\n record.fidelity,\n \"sceneRadianceProviderProfile.fidelity\"\n ),\n wavelengthChangingTransportModeled:\n false,\n volumetricTransportModeled: false,\n polarizationModeled: false,\n evidence: parseEvidenceList(\n record.evidence,\n \"sceneRadianceProviderProfile.evidence\"\n ),\n limitations: parseLimitations(\n record.limitations,\n \"sceneRadianceProviderProfile.limitations\"\n )\n };\n}\n\nfunction parsePositiveWavelengthNanometers(\n value: unknown,\n path: string\n): number {\n const wavelength = requireFinite(\n value,\n path\n );\n if (wavelength <= 0) {\n throw new InvalidConfigurationError(\n path + \" must be greater than zero.\"\n );\n }\n return wavelength;\n}\n\nfunction parseResolvedWavelengthBasis(\n value: unknown,\n path: string\n): Exclude<\n SpectralWavelengthBasis,\n \"unspecified\"\n> {\n const basis = parseSpectralWavelengthBasis(\n value,\n path\n );\n if (basis === \"unspecified\") {\n throw new InvalidConfigurationError(\n path +\n \" must be air or vacuum for outgoing spectral radiance.\"\n );\n }\n return basis;\n}\n\nfunction parseEvaluationTarget(\n value: unknown,\n path: string\n): SceneRadianceEvaluationTarget {\n const record = requireRecord(value, path, null);\n rejectUnknownVariantFields(record, \"kind\", {\n \"surface-point\": [\"kind\", \"sceneObjectId\", \"materialResponseId\", \"positionM\", \"outgoingDirectionUnitVector\"],\n \"environment-direction\": [\"kind\", \"outgoingDirectionUnitVector\"]\n }, path);\n if (record.kind === \"surface-point\") {\n return {\n kind: \"surface-point\",\n sceneObjectId: requireNonEmptyString(\n record.sceneObjectId,\n path + \".sceneObjectId\"\n ),\n materialResponseId:\n requireNonEmptyString(\n record.materialResponseId,\n path + \".materialResponseId\"\n ),\n positionM: parseVector3(\n record.positionM,\n path + \".positionM\"\n ),\n outgoingDirectionUnitVector:\n parseUnitDirection(\n record.outgoingDirectionUnitVector,\n path +\n \".outgoingDirectionUnitVector\"\n )\n };\n }\n if (\n record.kind ===\n \"environment-direction\"\n ) {\n return {\n kind: \"environment-direction\",\n outgoingDirectionUnitVector:\n parseUnitDirection(\n record.outgoingDirectionUnitVector,\n path +\n \".outgoingDirectionUnitVector\"\n )\n };\n }\n throw new InvalidConfigurationError(\n path + \".kind is invalid.\"\n );\n}\n\n/**\n * Parses one provider evaluation request at an explicit scene target,\n * physical time, wavelength, and outgoing direction.\n */\nexport function parseSceneRadianceEvaluationRequest(\n value: unknown\n): SceneRadianceEvaluationRequest {\n const record = requireRecord(\n value,\n \"sceneRadianceEvaluationRequest\", [\"schemaVersion\", \"sampleId\", \"providerProfileId\", \"sceneId\", \"illuminationProfileId\", \"materialResponseProfileId\", \"target\", \"timeSecondsFromExposureStart\", \"wavelengthNanometers\", \"wavelengthBasis\"]\n );\n if (\n record.schemaVersion !==\n SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceEvaluationRequest.schemaVersion must be \"' +\n SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION +\n '\".'\n );\n }\n\n return {\n schemaVersion:\n SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION,\n sampleId: requireNonEmptyString(\n record.sampleId,\n \"sceneRadianceEvaluationRequest.sampleId\"\n ),\n providerProfileId:\n requireNonEmptyString(\n record.providerProfileId,\n \"sceneRadianceEvaluationRequest.providerProfileId\"\n ),\n sceneId: requireNonEmptyString(\n record.sceneId,\n \"sceneRadianceEvaluationRequest.sceneId\"\n ),\n illuminationProfileId:\n requireNonEmptyString(\n record.illuminationProfileId,\n \"sceneRadianceEvaluationRequest.illuminationProfileId\"\n ),\n materialResponseProfileId:\n requireNonEmptyString(\n record.materialResponseProfileId,\n \"sceneRadianceEvaluationRequest.materialResponseProfileId\"\n ),\n target: parseEvaluationTarget(\n record.target,\n \"sceneRadianceEvaluationRequest.target\"\n ),\n timeSecondsFromExposureStart:\n requireNonNegativeFinite(\n record.timeSecondsFromExposureStart,\n \"sceneRadianceEvaluationRequest.timeSecondsFromExposureStart\"\n ),\n wavelengthNanometers:\n parsePositiveWavelengthNanometers(\n record.wavelengthNanometers,\n \"sceneRadianceEvaluationRequest.wavelengthNanometers\"\n ),\n wavelengthBasis:\n parseResolvedWavelengthBasis(\n record.wavelengthBasis,\n \"sceneRadianceEvaluationRequest.wavelengthBasis\"\n )\n };\n}\n\n/**\n * Parses one outgoing spectral-radiance result from a provider.\n *\n * The number is accepted as the provider reported it. Parsing checks units, that the\n * value is finite and nonnegative, provenance and identity fields. It does not prove\n * the provider's light-transport calculation is physically correct.\n */\nexport function parseSceneRadianceEvaluationResult(\n value: unknown\n): SceneRadianceEvaluationResult {\n const record = requireRecord(\n value,\n \"sceneRadianceEvaluationResult\", SCENE_RADIANCE_EVALUATION_RESULT_KEYS\n );\n return parseSceneRadianceEvaluationResultRecord(record, undefined);\n}\n\nconst SCENE_RADIANCE_EVALUATION_RESULT_KEYS = [\"schemaVersion\", \"quantity\", \"unit\", \"scientificStatus\", \"sampleId\", \"providerProfileId\", \"sceneId\", \"wavelengthNanometers\", \"wavelengthBasis\", \"spectralRadianceWattsPerSquareMeterSteradianNanometer\", \"uncertainty\", \"evidence\", \"limitations\"] as const;\n\n/** An earlier fully parsed result whose deep-frozen uncertainty, evidence and limitations records may be reused. */\nexport interface ValidatedSceneRadianceRecords {\n readonly uncertainty: unknown;\n readonly evidence: unknown;\n readonly limitations: unknown;\n readonly parsed: SceneRadianceEvaluationResult;\n}\n\n/**\n * Internal (2.6; not exported from the package): parses a result of an engine-built evaluator\n * (`isInternalSceneRadianceEvaluator`). It runs every check of `parseSceneRadianceEvaluationResult` with the same\n * helpers, order and messages (object shape, schema version, quantity, unit, status, the three identifiers, the\n * wavelength, its basis and the radiance value) except two: the scan for unknown keys, and re-parsing uncertainty,\n * evidence and limitations when they are the very (deep-frozen) objects of `validated`, an earlier result that\n * passed the full parse. Any other result takes the full parse.\n */\nexport function parseSceneRadianceEvaluationResultWithValidatedRecords(\n value: unknown,\n validated: ValidatedSceneRadianceRecords\n): SceneRadianceEvaluationResult {\n if (typeof value !== \"object\" || value === null || Array.isArray(value)) return parseSceneRadianceEvaluationResult(value);\n const record = value as UnknownRecord;\n if (record.uncertainty !== validated.uncertainty || record.evidence !== validated.evidence || record.limitations !== validated.limitations) {\n return parseSceneRadianceEvaluationResult(value);\n }\n return parseSceneRadianceEvaluationResultRecord(record, validated.parsed);\n}\n\nfunction parseSceneRadianceEvaluationResultRecord(\n record: UnknownRecord,\n validated: SceneRadianceEvaluationResult | undefined\n): SceneRadianceEvaluationResult {\n if (\n record.schemaVersion !==\n SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceEvaluationResult.schemaVersion must be \"' +\n SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION +\n '\".'\n );\n }\n if (\n record.quantity !==\n \"outgoing-spectral-radiance\"\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceEvaluationResult.quantity must be \"outgoing-spectral-radiance\".'\n );\n }\n if (record.unit !== \"W/m^2/sr/nm\") {\n throw new InvalidConfigurationError(\n 'sceneRadianceEvaluationResult.unit must be \"W/m^2/sr/nm\".'\n );\n }\n if (\n record.scientificStatus !==\n \"approximation\"\n ) {\n throw new InvalidConfigurationError(\n 'sceneRadianceEvaluationResult.scientificStatus must be \"approximation\" in schema 0.1.0.'\n );\n }\n\n return {\n schemaVersion:\n SCENE_RADIANCE_EVALUATION_SCHEMA_VERSION,\n sampleId: requireNonEmptyString(\n record.sampleId,\n \"sceneRadianceEvaluationResult.sampleId\"\n ),\n providerProfileId:\n requireNonEmptyString(\n record.providerProfileId,\n \"sceneRadianceEvaluationResult.providerProfileId\"\n ),\n sceneId: requireNonEmptyString(\n record.sceneId,\n \"sceneRadianceEvaluationResult.sceneId\"\n ),\n wavelengthNanometers:\n parsePositiveWavelengthNanometers(\n record.wavelengthNanometers,\n \"sceneRadianceEvaluationResult.wavelengthNanometers\"\n ),\n wavelengthBasis:\n parseResolvedWavelengthBasis(\n record.wavelengthBasis,\n \"sceneRadianceEvaluationResult.wavelengthBasis\"\n ),\n quantity:\n \"outgoing-spectral-radiance\",\n unit: \"W/m^2/sr/nm\",\n spectralRadianceWattsPerSquareMeterSteradianNanometer:\n requireNonNegativeFinite(\n record.spectralRadianceWattsPerSquareMeterSteradianNanometer,\n \"sceneRadianceEvaluationResult.spectralRadianceWattsPerSquareMeterSteradianNanometer\"\n ),\n scientificStatus: \"approximation\",\n uncertainty: validated ? validated.uncertainty : parseUncertainty(\n record.uncertainty,\n \"sceneRadianceEvaluationResult.uncertainty\"\n ),\n evidence: validated ? validated.evidence : parseEvidenceList(\n record.evidence,\n \"sceneRadianceEvaluationResult.evidence\"\n ),\n limitations: validated ? validated.limitations : parseLimitations(\n record.limitations,\n \"sceneRadianceEvaluationResult.limitations\"\n )\n };\n}\n\nfunction requireEqual(\n actual: unknown,\n expected: unknown,\n message: string\n): void {\n if (actual !== expected) {\n throw new InvalidConfigurationError(\n message\n );\n }\n}\n\n/**\n * Internal (#453; not exported from the package): the request and result checks of\n * {@link validateSceneRadianceEvaluationBindings} (the request against the three profiles, a surface target's material, and\n * the result against the request), with its messages and order. The profile-to-profile checks before them depend only on the\n * profiles; an engine caller that has run the full function once for these profile objects may run only this part for\n * further requests and results.\n */\nexport function validateSceneRadianceRequestResultBindings(\n providerProfile: ValidateSceneRadianceEvaluationBindingsInput[\"providerProfile\"],\n illuminationProfile: ValidateSceneRadianceEvaluationBindingsInput[\"illuminationProfile\"],\n materialResponseProfile: ValidateSceneRadianceEvaluationBindingsInput[\"materialResponseProfile\"],\n request: ValidateSceneRadianceEvaluationBindingsInput[\"request\"],\n result: ValidateSceneRadianceEvaluationBindingsInput[\"result\"]\n): void {\n requireEqual(\n request.providerProfileId,\n providerProfile.profileId,\n \"Request providerProfileId must match the supplied provider profile.\"\n );\n requireEqual(\n request.sceneId,\n providerProfile.sceneId,\n \"Request sceneId must match the supplied provider profile.\"\n );\n requireEqual(\n request.illuminationProfileId,\n illuminationProfile.profileId,\n \"Request illuminationProfileId must match the supplied illumination profile.\"\n );\n requireEqual(\n request.materialResponseProfileId,\n materialResponseProfile.profileId,\n \"Request materialResponseProfileId must match the supplied material-response profile.\"\n );\n\n if (request.target.kind === \"surface-point\") {\n const target = request.target;\n if (\n !materialResponseProfile.materials.some(\n (material) =>\n material.materialResponseId ===\n target.materialResponseId\n )\n ) {\n throw new InvalidConfigurationError(\n \"Request surface target materialResponseId is not declared by the supplied material-response profile.\"\n );\n }\n }\n\n requireEqual(\n result.sampleId,\n request.sampleId,\n \"Result sampleId must match the request.\"\n );\n requireEqual(\n result.providerProfileId,\n request.providerProfileId,\n \"Result providerProfileId must match the request.\"\n );\n requireEqual(\n result.sceneId,\n request.sceneId,\n \"Result sceneId must match the request.\"\n );\n requireEqual(\n result.wavelengthNanometers,\n request.wavelengthNanometers,\n \"Result wavelengthNanometers must match the request exactly.\"\n );\n requireEqual(\n result.wavelengthBasis,\n request.wavelengthBasis,\n \"Result wavelengthBasis must match the request.\"\n );\n}\n\n/**\n * Checks that a provider result matches its request and profile identities exactly.\n *\n * It never recomputes the radiance value, and never upgrades the provider's\n * approximation to calibrated radiometry.\n */\nexport function validateSceneRadianceEvaluationBindings(\n input:\n ValidateSceneRadianceEvaluationBindingsInput\n): SceneRadianceEvaluationBindingAssessment {\n requireInputKeys(input, \"validateSceneRadianceEvaluationBindings\", [\"providerProfile\", \"illuminationProfile\", \"illuminationTemporalProfile\", \"materialResponseProfile\", \"request\", \"result\"]);\n const {\n providerProfile,\n illuminationProfile,\n illuminationTemporalProfile,\n materialResponseProfile,\n request,\n result\n } = input;\n\n requireInputObject(providerProfile, \"providerProfile input\");\n requireEqual(\n providerProfile.sceneId,\n illuminationProfile.sceneId,\n \"Provider and illumination profiles must reference the same sceneId.\"\n );\n requireEqual(\n providerProfile.sceneId,\n materialResponseProfile.sceneId,\n \"Provider and material-response profiles must reference the same sceneId.\"\n );\n requireEqual(\n providerProfile.illuminationProfileId,\n illuminationProfile.profileId,\n \"Provider illuminationProfileId must match the supplied illumination profile.\"\n );\n requireEqual(\n providerProfile.materialResponseProfileId,\n materialResponseProfile.profileId,\n \"Provider materialResponseProfileId must match the supplied material-response profile.\"\n );\n\n if (\n providerProfile\n .illuminationTemporalProfileId ===\n undefined\n ) {\n if (\n illuminationTemporalProfile !==\n undefined\n ) {\n throw new InvalidConfigurationError(\n \"A temporal illumination profile was supplied but the provider profile does not bind one.\"\n );\n }\n } else {\n if (\n illuminationTemporalProfile ===\n undefined\n ) {\n throw new InvalidConfigurationError(\n \"Provider illuminationTemporalProfileId requires the matching temporal illumination profile.\"\n );\n }\n requireEqual(\n providerProfile\n .illuminationTemporalProfileId,\n illuminationTemporalProfile\n .profileId,\n \"Provider illuminationTemporalProfileId must match the supplied temporal illumination profile.\"\n );\n requireEqual(\n providerProfile.sceneId,\n illuminationTemporalProfile.sceneId,\n \"Provider and temporal illumination profiles must reference the same sceneId.\"\n );\n requireEqual(\n providerProfile\n .illuminationProfileId,\n illuminationTemporalProfile\n .illuminationProfileId,\n \"Temporal illumination profile must bind the provider's illuminationProfileId.\"\n );\n }\n\n const materialResponseFidelity =\n assessSceneMaterialResponseFidelity(\n materialResponseProfile\n );\n requireEqual(\n providerProfile.fidelity.material,\n materialResponseFidelity,\n \"Provider material fidelity must match the supplied material-response profile.\"\n );\n\n validateSceneRadianceRequestResultBindings(providerProfile, illuminationProfile, materialResponseProfile, request, result);\n\n return {\n providerBindingsMatched: true,\n requestResultIdentityMatched: true,\n materialResponseFidelity,\n temporalIlluminationProfileBound:\n illuminationTemporalProfile !==\n undefined,\n calibratedRadianceClaimAuthorized: false,\n sensorPlaneIrradianceCalculated:\n false,\n opticsApplied: false,\n photonsCalculated: false\n };\n}\n"]}
@@ -177,6 +177,27 @@ export declare function prebuildApertureRadianceQuery(base: SceneRadianceEvaluat
177
177
  * are identical either way.
178
178
  */
179
179
  export declare function executeEnvironmentSensorPhotoSignal(plan: ReturnType<typeof planEnvironmentSensorPhotoSignal>, evaluate: EnvironmentRadianceEvaluator, evaluateAperture?: EnvironmentApertureRadianceEvaluator, retention?: "full" | "photo-only"): CalculationResult<EnvironmentSensorPhotoSignal>;
180
+ /**
181
+ * Internal (#453; not exported from the package): the photo signal of {@link executeEnvironmentSensorPhotoSignal} with
182
+ * retention "photo-only" (its `value.photo`), for a plan of engine-built records (planned as "engine-owned" from a record the
183
+ * engine built, never shown to supplied code and never changed). It is the same chain with the same operations: every query of
184
+ * the plan calls `evaluate` once with the same frozen request, in the same order; each result is parsed and its bindings and
185
+ * identity checked; the optical bridge forms each irradiance with its own code; the taps, nodes and instants are assembled as
186
+ * the full executor does; and `createSensorEqeTemporalPhotoSignal` forms the photo signal from the same input. So the photo
187
+ * signal is the full executor's, value for value.
188
+ *
189
+ * What it skips is only re-validation of records that cannot have changed since they passed it, and records nobody reads:
190
+ * - the first query runs the full per-query steps (full result parse, `validateSceneRadianceEvaluationBindings`,
191
+ * `calculateSceneRadianceToSensorIrradiance`); later queries skip the profile-to-profile binding checks and the optical
192
+ * bridge's re-parse of its unchanged optical inputs, request and result, keeping every per-query check
193
+ * (`validateSceneRadianceRequestResultBindings`, `prepareSceneRadianceToSensorIrradianceValue`), with the same messages;
194
+ * - with `engineBuiltResults` (an evaluator marked by `markInternalSceneRadianceEvaluator`, or one returning such an
195
+ * evaluator's results), later results reuse the first result's parsed uncertainty, evidence and limitations when they are
196
+ * the same deep-frozen objects (`parseSceneRadianceEvaluationResultWithValidatedRecords`, as the lean executor does);
197
+ * - no per-query optical result envelopes and no outer execution envelope are built.
198
+ * Plans with ideal-pupil rays or a sampled PSF run the full executor.
199
+ */
200
+ export declare function executeEngineOwnedEnvironmentPhotoSignal(plan: ReturnType<typeof planEnvironmentSensorPhotoSignal>, evaluate: EnvironmentRadianceEvaluator, engineBuiltResults: boolean): EnvironmentSensorPhotoSignal["photo"];
180
201
  /** Plans, queries the provider and integrates the photo signal for one site, at the site's own midpoint sample positions. */
181
202
  export declare function calculateEnvironmentSensorPhotoSignal(input: CalculateEnvironmentSensorPhotoSignalInput): CalculationResult<EnvironmentSensorPhotoSignal>;
182
203
  export {};
@@ -19,9 +19,10 @@ import { parseEvidenceList } from "../core/evidence-provenance.js";
19
19
  import { InvalidScientificInputError } from "../core/validation.js";
20
20
  import { parseSceneIlluminationProfile } from "../schema/illumination.js";
21
21
  import { parseSceneIlluminationTemporalProfile } from "../schema/illumination-temporal.js";
22
- import { parseSceneMaterialResponseProfile, parseSceneRadianceProviderProfile, parseSceneRadianceEvaluationResult, validateSceneRadianceEvaluationBindings } from "../schema/scene-radiance.js";
22
+ import { parseSceneMaterialResponseProfile, parseSceneRadianceProviderProfile, parseSceneRadianceEvaluationResult, parseSceneRadianceEvaluationResultWithValidatedRecords, validateSceneRadianceEvaluationBindings, validateSceneRadianceRequestResultBindings } from "../schema/scene-radiance.js";
23
23
  import { calculateMappedSensorEnvironmentRadianceQuery, calculateSensorEnvironmentRadianceQuery, prepareEnvironmentLensFieldMapping } from "../optics/sensor-environment-query.js";
24
- import { calculateSceneRadianceToSensorIrradiance } from "../optics/scene-to-sensor-irradiance.js";
24
+ import { calculateSceneRadianceToSensorIrradiance, prepareSceneRadianceToSensorIrradianceValue } from "../optics/scene-to-sensor-irradiance.js";
25
+ import { isDeeplyFrozen } from "../core/internal-radiance-evaluator.js";
25
26
  import { calculateSensorPsfIrradianceQuadrature } from "../optics/sensor-psf-quadrature.js";
26
27
  import { calculateIlluminationVignetting } from "../optics/illumination-vignetting.js";
27
28
  import { calculateSensorApertureRays } from "../optics/sensor-aperture-rays.js";
@@ -292,6 +293,71 @@ export function executeEnvironmentSensorPhotoSignal(plan, evaluate, evaluateAper
292
293
  ])
293
294
  ]);
294
295
  }
296
+ /**
297
+ * Internal (#453; not exported from the package): the photo signal of {@link executeEnvironmentSensorPhotoSignal} with
298
+ * retention "photo-only" (its `value.photo`), for a plan of engine-built records (planned as "engine-owned" from a record the
299
+ * engine built, never shown to supplied code and never changed). It is the same chain with the same operations: every query of
300
+ * the plan calls `evaluate` once with the same frozen request, in the same order; each result is parsed and its bindings and
301
+ * identity checked; the optical bridge forms each irradiance with its own code; the taps, nodes and instants are assembled as
302
+ * the full executor does; and `createSensorEqeTemporalPhotoSignal` forms the photo signal from the same input. So the photo
303
+ * signal is the full executor's, value for value.
304
+ *
305
+ * What it skips is only re-validation of records that cannot have changed since they passed it, and records nobody reads:
306
+ * - the first query runs the full per-query steps (full result parse, `validateSceneRadianceEvaluationBindings`,
307
+ * `calculateSceneRadianceToSensorIrradiance`); later queries skip the profile-to-profile binding checks and the optical
308
+ * bridge's re-parse of its unchanged optical inputs, request and result, keeping every per-query check
309
+ * (`validateSceneRadianceRequestResultBindings`, `prepareSceneRadianceToSensorIrradianceValue`), with the same messages;
310
+ * - with `engineBuiltResults` (an evaluator marked by `markInternalSceneRadianceEvaluator`, or one returning such an
311
+ * evaluator's results), later results reuse the first result's parsed uncertainty, evidence and limitations when they are
312
+ * the same deep-frozen objects (`parseSceneRadianceEvaluationResultWithValidatedRecords`, as the lean executor does);
313
+ * - no per-query optical result envelopes and no outer execution envelope are built.
314
+ * Plans with ideal-pupil rays or a sampled PSF run the full executor.
315
+ */
316
+ export function executeEngineOwnedEnvironmentPhotoSignal(plan, evaluate, engineBuiltResults) {
317
+ const { owned } = plan;
318
+ if (owned.pupil !== undefined || owned.psf.kind !== "not-applied")
319
+ return executeEnvironmentSensorPhotoSignal(plan, evaluate, undefined, "photo-only").value.photo;
320
+ if (typeof evaluate !== "function")
321
+ throw new InvalidScientificInputError("Environment radiance evaluator must be synchronous callable code.");
322
+ const { providerProfile, illuminationProfile, materialResponseProfile } = plan.sceneBindings;
323
+ let validated;
324
+ let irradianceOf;
325
+ const irradiance = [];
326
+ for (const instant of plan.instants) {
327
+ const samples = instant.groups.map(group => ({ node: group.node, sourceSamples: group.taps.map(tap => {
328
+ let integratedIrradiance = 0;
329
+ const request = tap.request, value = evaluate(request);
330
+ let sensorPlane;
331
+ if (irradianceOf === undefined) {
332
+ const result = parseSceneRadianceEvaluationResult(value);
333
+ validateSceneRadianceEvaluationBindings({ ...plan.sceneBindings, request, result });
334
+ sensorPlane = calculateSceneRadianceToSensorIrradiance({ ...owned.optics, sceneRadianceRequest: request,
335
+ sceneRadianceResult: result, imagePointMm: tap.sourcePointImagePlaneMm, fieldThroughput: tap.fieldThroughput }).value.sensorPlaneSpectralIrradianceWattsPerSquareMeterNanometer;
336
+ const record = value;
337
+ if (engineBuiltResults && isDeeplyFrozen(record.uncertainty) && isDeeplyFrozen(record.evidence) && isDeeplyFrozen(record.limitations)) {
338
+ validated = { uncertainty: record.uncertainty, evidence: record.evidence, limitations: record.limitations, parsed: result };
339
+ }
340
+ irradianceOf = prepareSceneRadianceToSensorIrradianceValue(owned.optics);
341
+ }
342
+ else {
343
+ const result = validated ? parseSceneRadianceEvaluationResultWithValidatedRecords(value, validated) : parseSceneRadianceEvaluationResult(value);
344
+ validateSceneRadianceRequestResultBindings(providerProfile, illuminationProfile, materialResponseProfile, request, result);
345
+ sensorPlane = irradianceOf(request, result, tap.sourcePointImagePlaneMm, tap.fieldThroughput);
346
+ }
347
+ // The full executor's sum over the tap's support (one direction, weight 1 without pupil rays).
348
+ integratedIrradiance += sensorPlane * 1;
349
+ if (tap.distortionAreaFactor !== undefined)
350
+ integratedIrradiance *= tap.distortionAreaFactor;
351
+ return { kernelSampleX: tap.kernelSampleX, kernelSampleY: tap.kernelSampleY, sourcePointNativeSensorMm: tap.point,
352
+ timeSecondsFromOpeningReference: instant.time, spectralIrradianceWattsPerSquareMeterPerNanometer: integratedIrradiance };
353
+ }) }));
354
+ irradiance.push({ temporalSampleIndex: instant.temporalSampleIndex, timeSecondsFromOpeningReference: instant.time,
355
+ irradianceSamples: samples.map(s => ({ node: s.node,
356
+ spectralIrradianceWattsPerSquareMeterPerNanometer: s.sourceSamples[0].spectralIrradianceWattsPerSquareMeterPerNanometer })) });
357
+ }
358
+ return createSensorEqeTemporalPhotoSignal({ temporalIntegrationId: owned.temporalIntegrationId,
359
+ exposure: { ...owned.sensor, samples: irradiance } });
360
+ }
295
361
  /** Plans, queries the provider and integrates the photo signal for one site, at the site's own midpoint sample positions. */
296
362
  export function calculateEnvironmentSensorPhotoSignal(input) {
297
363
  requireInputKeys(input, "calculateEnvironmentSensorPhotoSignal", ["temporalIntegrationId", "sensor", "sceneBindings", "optics", "motion", "temporalSampleCount", "pupil", "lensFieldMapping", "fieldThroughput", "psf", "evaluateRadiance", "evaluateApertureRadiance"]);