@photivra/engine 2.4.1 → 2.6.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.
- package/CHANGELOG.md +53 -1
- package/CITATION.cff +1 -1
- package/README.md +6 -6
- package/SECURITY.md +1 -1
- package/THIRD_PARTY.md +1 -0
- package/dist/capture/native-environment-lean.d.ts +1 -1
- package/dist/capture/native-environment-lean.js +17 -3
- package/dist/capture/native-environment-lean.js.map +1 -1
- package/dist/capture/native-environment-raw.d.ts +0 -4
- package/dist/capture/native-environment-raw.js +6 -2
- package/dist/capture/native-environment-raw.js.map +1 -1
- package/dist/color/illuminants.d.ts +15 -0
- package/dist/color/illuminants.js +81 -24
- package/dist/color/illuminants.js.map +1 -1
- package/dist/color/srgb-transfer.d.ts +6 -0
- package/dist/color/srgb-transfer.js +9 -0
- package/dist/color/srgb-transfer.js.map +1 -1
- package/dist/color/white-balance.d.ts +6 -0
- package/dist/color/white-balance.js +15 -2
- package/dist/color/white-balance.js.map +1 -1
- package/dist/core/internal-radiance-evaluator.d.ts +6 -0
- package/dist/core/internal-radiance-evaluator.js +33 -0
- package/dist/core/internal-radiance-evaluator.js.map +1 -0
- package/dist/core/portable-math.d.ts +33 -0
- package/dist/core/portable-math.js +342 -0
- package/dist/core/portable-math.js.map +1 -1
- package/dist/core/version.d.ts +1 -1
- package/dist/core/version.js +1 -1
- package/dist/core/version.js.map +1 -1
- package/dist/facade/chart-scenes.d.ts +9 -0
- package/dist/facade/chart-scenes.js +17 -4
- package/dist/facade/chart-scenes.js.map +1 -1
- package/dist/facade/diffraction-provider.d.ts +10 -0
- package/dist/facade/diffraction-provider.js +38 -17
- package/dist/facade/diffraction-provider.js.map +1 -1
- package/dist/facade/display-view.d.ts +208 -0
- package/dist/facade/display-view.js +1461 -0
- package/dist/facade/display-view.js.map +1 -0
- package/dist/facade/scene-radiance.d.ts +7 -0
- package/dist/facade/scene-radiance.js +18 -5
- package/dist/facade/scene-radiance.js.map +1 -1
- package/dist/facade/simulate-capture.d.ts +229 -5
- package/dist/facade/simulate-capture.js +119 -35
- package/dist/facade/simulate-capture.js.map +1 -1
- package/dist/facade/simulate-display-view.d.ts +21 -0
- package/dist/facade/simulate-display-view.js +168 -0
- package/dist/facade/simulate-display-view.js.map +1 -0
- package/dist/facade/subject-framing.d.ts +78 -0
- package/dist/facade/subject-framing.js +69 -20
- package/dist/facade/subject-framing.js.map +1 -1
- package/dist/index.d.ts +3 -2
- package/dist/index.js +3 -2
- package/dist/index.js.map +1 -1
- package/dist/optics/diffraction-psf-profile.d.ts +59 -3
- package/dist/optics/diffraction-psf-profile.js +147 -5
- package/dist/optics/diffraction-psf-profile.js.map +1 -1
- package/dist/optics/irradiance-convolution.js +1 -1
- package/dist/optics/irradiance-convolution.js.map +1 -1
- package/dist/optics/scene-to-sensor-irradiance.d.ts +7 -0
- package/dist/optics/scene-to-sensor-irradiance.js +10 -5
- package/dist/optics/scene-to-sensor-irradiance.js.map +1 -1
- package/dist/output/print-plan.d.ts +8 -1
- package/dist/output/print-plan.js +8 -1
- package/dist/output/print-plan.js.map +1 -1
- package/dist/schema/scene-radiance.d.ts +16 -0
- package/dist/schema/scene-radiance.js +25 -4
- package/dist/schema/scene-radiance.js.map +1 -1
- package/dist/sensor/raw-readout.d.ts +12 -0
- package/dist/sensor/raw-readout.js +131 -9
- package/dist/sensor/raw-readout.js.map +1 -1
- package/dist/sensor/stochastic-seed.d.ts +13 -0
- package/dist/sensor/stochastic-seed.js +42 -8
- package/dist/sensor/stochastic-seed.js.map +1 -1
- package/docs/AGENT_GUIDE.md +1 -0
- package/docs/API_REFERENCE.md +16 -1
- package/docs/QUICK_START.md +245 -9
- package/docs/USAGE.md +15 -0
- package/docs/api/core-version.md +1 -1
- package/docs/api/exports.json +37 -2
- package/docs/api/facade-simulate-capture.md +70 -2
- package/docs/api/facade-simulate-display-view.md +18 -0
- package/docs/api/facade-subject-framing.md +83 -0
- package/docs/api/optics-diffraction-psf-profile.md +8 -1
- package/docs/api/output-print-plan.md +8 -1
- package/package.json +3 -2
|
@@ -12,7 +12,7 @@ import { InvalidConfigurationError } from "../core/configuration-error.js";
|
|
|
12
12
|
import { parseEvidenceList } from "../core/evidence-provenance.js";
|
|
13
13
|
import { InvalidScientificInputError } from "../core/validation.js";
|
|
14
14
|
import { requireInputObject, requireInputKeys, rejectUnknownFields } from "../core/record-validation.js";
|
|
15
|
-
import { calculateChromaticityFromCorrelatedColorTemperature } from "./illuminants.js";
|
|
15
|
+
import { calculateChromaticityFromCorrelatedColorTemperature, calculatePortableChromaticityFromCorrelatedColorTemperature } from "./illuminants.js";
|
|
16
16
|
import { multiplyMatrixVector, parseMatrix3x3, xyzOfChromaticity } from "./colorimetry-math.js";
|
|
17
17
|
export const WHITE_BALANCE_PROFILE_SCHEMA_VERSION = "0.1.0";
|
|
18
18
|
export const WHITE_BALANCE_STATE_VERSION = "0.1.0";
|
|
@@ -311,6 +311,19 @@ export function createColorTemperatureWhiteBalanceIntent(input) {
|
|
|
311
311
|
* the locus model.
|
|
312
312
|
*/
|
|
313
313
|
export function resolveColorTemperatureWhiteBalance(input) {
|
|
314
|
+
return colorTemperatureWhiteBalance(input, calculateChromaticityFromCorrelatedColorTemperature);
|
|
315
|
+
}
|
|
316
|
+
/**
|
|
317
|
+
* Internal (not exported from the package): {@link resolveColorTemperatureWhiteBalance} with the white point from
|
|
318
|
+
* `calculatePortableChromaticityFromCorrelatedColorTemperature`, so the gains have the same bits in every JavaScript
|
|
319
|
+
* engine. The display view uses it for a Kelvin white balance; captures keep {@link resolveColorTemperatureWhiteBalance}.
|
|
320
|
+
*/
|
|
321
|
+
export function resolvePortableColorTemperatureWhiteBalance(input) {
|
|
322
|
+
return colorTemperatureWhiteBalance(input, calculatePortableChromaticityFromCorrelatedColorTemperature);
|
|
323
|
+
}
|
|
324
|
+
// The white point is computed by the function passed in (the portable one only from resolvePortableColorTemperatureWhiteBalance), so
|
|
325
|
+
// a bundle that never resolves the portable white balance does not contain the portable functions.
|
|
326
|
+
function colorTemperatureWhiteBalance(input, chromaticityFromCct) {
|
|
314
327
|
requireInputKeys(input, "resolveColorTemperatureWhiteBalance", ["stateId", "intent", "whiteLocus", "tintInterpretation", "planckianLocus", "camera"]);
|
|
315
328
|
const intent = input.intent;
|
|
316
329
|
if (typeof intent !== "object" ||
|
|
@@ -334,7 +347,7 @@ export function resolveColorTemperatureWhiteBalance(input) {
|
|
|
334
347
|
const profileVersion = requireScientificNonEmptyString(camera.profileVersion, "camera.profileVersion");
|
|
335
348
|
const matrix = parseMatrix3x3(camera.xyzToCameraRgb, "camera.xyzToCameraRgb");
|
|
336
349
|
const locus = input.planckianLocus ?? { kind: "planck-analytic-cmf" };
|
|
337
|
-
const white =
|
|
350
|
+
const white = chromaticityFromCct({
|
|
338
351
|
correlatedColorTemperatureKelvin: kelvin,
|
|
339
352
|
duv: tint,
|
|
340
353
|
whiteLocus: input.whiteLocus,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"white-balance.js","sourceRoot":"","sources":["../../src/color/white-balance.ts"],"names":[],"mappings":"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","sourcesContent":["// SPDX-License-Identifier: Apache-2.0\n\n/**\n * White balance (WB): generic presets, manual gains, colour temperature and tint, custom (grey-card)\n * WB, auto white balance (AWB), WB lock, and parsing of a committed WB state.\n *\n * The profile defines preset gains and AWB correction strength. A label such as \"Daylight\" is not\n * treated as a universal Kelvin value or as any manufacturer's behaviour.\n * @see docs/CAPTURE_COLOR.md for the equations, units, coordinate conventions, known blockers and\n * support limits.\n */\n\nimport { InvalidConfigurationError } from \"../core/configuration-error.js\";\nimport {\n parseEvidenceList,\n type EvidenceBackedFact,\n type EvidenceProvenance\n} from \"../core/evidence-provenance.js\";\nimport { InvalidScientificInputError } from \"../core/validation.js\";\nimport { requireInputObject, requireInputKeys, rejectUnknownFields } from \"../core/record-validation.js\";\nimport {\n calculateChromaticityFromCorrelatedColorTemperature,\n type PlanckianLocusModel,\n type WhiteLocus\n} from \"./illuminants.js\";\nimport {\n multiplyMatrixVector,\n parseMatrix3x3,\n xyzOfChromaticity,\n type CieXyChromaticity,\n type ColorMatrix3x3\n} from \"./colorimetry-math.js\";\n\ntype UnknownRecord = Record<string, unknown>;\n\nexport const WHITE_BALANCE_PROFILE_SCHEMA_VERSION = \"0.1.0\" as const;\nexport const WHITE_BALANCE_STATE_VERSION = \"0.1.0\" as const;\nexport const COLOR_TEMPERATURE_WHITE_BALANCE_INTENT_VERSION =\n \"0.1.0\" as const;\n\nexport type WhiteBalanceInputDomain =\n \"relative-pre-wb-camera-linear-rgb\";\n\nexport interface WhiteBalanceChannelGains {\n red: number;\n green: number;\n blue: number;\n}\n\nexport type WhiteBalanceAwbIntent =\n | \"neutral-priority\"\n | \"standard\"\n | \"ambience-preserving\";\n\nexport interface WhiteBalancePresetDefinition {\n presetId: string;\n label: string;\n channelGains: EvidenceBackedFact<WhiteBalanceChannelGains>;\n nominalColorTemperatureKelvin?: number;\n nominalTint?: number;\n limitations?: readonly string[];\n}\n\nexport interface WhiteBalanceAwbPolicy {\n policyId: string;\n intent: WhiteBalanceAwbIntent;\n /**\n * How much of a grey-world neutralizing correction to apply, measured in\n * logarithmic gain space. 1 applies the full correction (neutral priority).\n * Lower values keep more of the observed colour cast.\n */\n correctionStrength: EvidenceBackedFact<number>;\n limitations?: readonly string[];\n}\n\nexport interface WhiteBalanceProfile {\n schemaVersion: typeof WHITE_BALANCE_PROFILE_SCHEMA_VERSION;\n profileId: string;\n profileVersion: string;\n scientificStatus: \"approximation\";\n inputDomain: WhiteBalanceInputDomain;\n presets: readonly WhiteBalancePresetDefinition[];\n awbPolicies: readonly WhiteBalanceAwbPolicy[];\n evidence: readonly EvidenceProvenance[];\n limitations: readonly string[];\n}\n\nexport interface PreWhiteBalanceRgbSample {\n sampleId: string;\n red: number;\n green: number;\n blue: number;\n weight: number;\n clipped: boolean;\n}\n\nexport interface PreWhiteBalanceRgbSampleSet {\n imageStateId: string;\n inputDomain: WhiteBalanceInputDomain;\n samples: readonly PreWhiteBalanceRgbSample[];\n}\n\nexport interface ResolvedWhiteBalanceState {\n version: typeof WHITE_BALANCE_STATE_VERSION;\n stateId: string;\n inputDomain: WhiteBalanceInputDomain;\n source:\n | \"preset\"\n | \"manual-gains\"\n | \"custom-measurement\"\n | \"auto-white-balance\"\n | \"color-temperature\";\n channelGains: WhiteBalanceChannelGains;\n locked: boolean;\n sourceProfile?: {\n profileId: string;\n profileVersion: string;\n };\n presetId?: string;\n awbPolicy?: {\n policyId: string;\n intent: WhiteBalanceAwbIntent;\n correctionStrength: number;\n };\n measurement?: {\n imageStateId: string;\n usableSampleCount: number;\n rejectedClippedSampleCount: number;\n weightedMeanPreWbSignal: {\n red: number;\n green: number;\n blue: number;\n };\n };\n /** Present for `color-temperature` states: the declared CCT/tint and its camera neutral. */\n colorTemperature?: ResolvedColorTemperatureWhiteBalance;\n sourceStateId?: string;\n trueIlluminantMetadataUsed: false;\n sceneIlluminationModified: false;\n rawCaptureDestructivelyModified: false;\n physicalExposureModified: false;\n focusModified: false;\n limitations: readonly string[];\n}\n\nexport interface ColorTemperatureWhiteBalanceIntent {\n version: typeof COLOR_TEMPERATURE_WHITE_BALANCE_INTENT_VERSION;\n intentId: string;\n colorTemperatureKelvin: number;\n tint: number;\n channelGainsResolved: false;\n requiresCameraProfileColorimetry: true;\n sceneIlluminationModified: false;\n}\n\n/** Locus/tint interpretation and camera neutral behind a Kelvin + tint WB state. */\nexport interface ResolvedColorTemperatureWhiteBalance {\n intentId: string;\n colorTemperatureKelvin: number;\n tint: number;\n whiteLocus: WhiteLocus;\n tintInterpretation: \"duv-cie-1960-uv\";\n planckianLocusModel: \"planck-analytic-cmf\" | \"planck-integration\";\n /** CIE 1931 xy of the declared white (CCT + Duv). */\n adoptedWhiteChromaticity: CieXyChromaticity;\n /** Pre-WB camera response to that white (XYZ with Y = 1 through xyzToCameraRgb). */\n cameraNeutralRgb: WhiteBalanceChannelGains;\n}\n\n/** Camera colour model used to turn a declared white into channel gains. */\nexport interface ColorTemperatureWhiteBalanceCameraModel {\n profileId: string;\n profileVersion: string;\n /** Row-major CIE XYZ (white Y = 1) → relative pre-WB camera-linear RGB. */\n xyzToCameraRgb: ColorMatrix3x3;\n}\n\nexport interface ResolveColorTemperatureWhiteBalanceInput {\n stateId: string;\n intent: ColorTemperatureWhiteBalanceIntent;\n /** Locus whose temperature defines the white: Planckian or CIE daylight. */\n whiteLocus: WhiteLocus;\n /** Tint is read as Duv in the CIE 1960 UCS (positive = above the Planckian locus, greenish). */\n tintInterpretation: \"duv-cie-1960-uv\";\n /** Defaults to Planck's law integrated against the engine's analytic CIE 1931 CMFs (`planck-analytic-cmf`). */\n planckianLocus?: PlanckianLocusModel;\n camera: ColorTemperatureWhiteBalanceCameraModel;\n}\n\nexport interface ResolvePresetWhiteBalanceInput {\n stateId: string;\n profile: WhiteBalanceProfile;\n presetId: string;\n}\n\nexport interface ResolveManualWhiteBalanceInput {\n stateId: string;\n channelGains: WhiteBalanceChannelGains;\n}\n\nexport interface CreateColorTemperatureWhiteBalanceIntentInput {\n intentId: string;\n colorTemperatureKelvin: number;\n tint: number;\n}\n\nexport interface ResolveCustomWhiteBalanceInput {\n stateId: string;\n sampleSet: PreWhiteBalanceRgbSampleSet;\n}\n\nexport interface EstimateAutoWhiteBalanceInput {\n stateId: string;\n profile: WhiteBalanceProfile;\n policyId: string;\n sampleSet: PreWhiteBalanceRgbSampleSet;\n}\n\nexport interface CreateLockedWhiteBalanceStateInput {\n stateId: string;\n sourceState: ResolvedWhiteBalanceState;\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(path + \" must be an object.\");\n }\n if (allowedKeys !== null) rejectUnknownFields(value, allowedKeys, path);\n return value as UnknownRecord;\n}\n\nfunction requireNonEmptyString(value: unknown, path: string): string {\n if (typeof value !== \"string\" || value.trim().length === 0) {\n throw new InvalidConfigurationError(\n path + \" must be a non-empty string.\"\n );\n }\n return value.trim();\n}\n\nfunction requireFinite(value: unknown, path: string): number {\n if (typeof value !== \"number\" || !Number.isFinite(value)) {\n throw new InvalidConfigurationError(path + \" must be finite.\");\n }\n return value;\n}\n\nfunction requirePositiveFinite(value: unknown, path: string): number {\n const parsed = requireFinite(value, path);\n if (parsed <= 0) {\n throw new InvalidConfigurationError(\n path + \" must be greater than zero.\"\n );\n }\n return parsed;\n}\n\nfunction requireFraction(value: unknown, path: string): number {\n const parsed = requireFinite(value, path);\n if (parsed < 0 || parsed > 1) {\n throw new InvalidConfigurationError(\n path + \" must be from zero through one.\"\n );\n }\n return parsed;\n}\n\nfunction parseChannelGains(\n value: unknown,\n path: string\n): WhiteBalanceChannelGains {\n const record = requireRecord(value, path, [\"red\", \"green\", \"blue\"]);\n return {\n red: requirePositiveFinite(record.red, path + \".red\"),\n green: requirePositiveFinite(record.green, path + \".green\"),\n blue: requirePositiveFinite(record.blue, path + \".blue\")\n };\n}\n\nfunction parseLimitations(\n value: unknown,\n path: string\n): readonly string[] {\n if (!Array.isArray(value)) {\n throw new InvalidConfigurationError(path + \" must be an array.\");\n }\n const parsed = value.map((entry, index) =>\n requireNonEmptyString(entry, path + \"[\" + index + \"]\")\n );\n if (new Set(parsed).size !== parsed.length) {\n throw new InvalidConfigurationError(\n path + \" must not contain duplicates.\"\n );\n }\n return parsed;\n}\n\nfunction parseOptionalLimitations(\n value: unknown,\n path: string\n): readonly string[] | undefined {\n return value === undefined ? undefined : parseLimitations(value, path);\n}\n\nfunction parsePreset(\n value: unknown,\n path: string\n): WhiteBalancePresetDefinition {\n const record = requireRecord(value, path, [\"channelGains\", \"limitations\", \"presetId\", \"label\", \"nominalColorTemperatureKelvin\", \"nominalTint\"]);\n const gainsFact = requireRecord(record.channelGains, path + \".channelGains\", [\"value\", \"evidence\"]);\n const limitations = parseOptionalLimitations(\n record.limitations,\n path + \".limitations\"\n );\n\n return {\n presetId: requireNonEmptyString(record.presetId, path + \".presetId\"),\n label: requireNonEmptyString(record.label, path + \".label\"),\n channelGains: {\n value: parseChannelGains(\n gainsFact.value,\n path + \".channelGains.value\"\n ),\n evidence: parseEvidenceList(\n gainsFact.evidence,\n path + \".channelGains.evidence\"\n )\n },\n ...(record.nominalColorTemperatureKelvin === undefined\n ? {}\n : {\n nominalColorTemperatureKelvin: requirePositiveFinite(\n record.nominalColorTemperatureKelvin,\n path + \".nominalColorTemperatureKelvin\"\n )\n }),\n ...(record.nominalTint === undefined\n ? {}\n : {\n nominalTint: requireFinite(\n record.nominalTint,\n path + \".nominalTint\"\n )\n }),\n ...(limitations === undefined\n ? {}\n : {\n limitations\n })\n };\n}\n\nfunction parseAwbIntent(\n value: unknown,\n path: string\n): WhiteBalanceAwbIntent {\n if (\n value !== \"neutral-priority\" &&\n value !== \"standard\" &&\n value !== \"ambience-preserving\"\n ) {\n throw new InvalidConfigurationError(path + \" is invalid.\");\n }\n return value;\n}\n\nfunction parseAwbPolicy(\n value: unknown,\n path: string\n): WhiteBalanceAwbPolicy {\n const record = requireRecord(value, path, [\"correctionStrength\", \"limitations\", \"policyId\", \"intent\"]);\n const strengthFact = requireRecord(\n record.correctionStrength,\n path + \".correctionStrength\", [\"value\", \"evidence\"]\n );\n const limitations = parseOptionalLimitations(\n record.limitations,\n path + \".limitations\"\n );\n\n return {\n policyId: requireNonEmptyString(record.policyId, path + \".policyId\"),\n intent: parseAwbIntent(record.intent, path + \".intent\"),\n correctionStrength: {\n value: requireFraction(\n strengthFact.value,\n path + \".correctionStrength.value\"\n ),\n evidence: parseEvidenceList(\n strengthFact.evidence,\n path + \".correctionStrength.evidence\"\n )\n },\n ...(limitations === undefined ? {} : { limitations })\n };\n}\n\n/**\n * Parses generic WB presets and AWB policies.\n *\n * The profile defines preset gains and AWB correction strength. A label is not\n * treated as a universal Kelvin value or as any manufacturer's behaviour.\n */\nexport function parseWhiteBalanceProfile(\n value: unknown\n): WhiteBalanceProfile {\n const record = requireRecord(value, \"whiteBalanceProfile\", [\"schemaVersion\", \"scientificStatus\", \"inputDomain\", \"presets\", \"awbPolicies\", \"profileId\", \"profileVersion\", \"evidence\", \"limitations\"]);\n\n if (record.schemaVersion !== WHITE_BALANCE_PROFILE_SCHEMA_VERSION) {\n throw new InvalidConfigurationError(\n 'whiteBalanceProfile.schemaVersion must be \"' +\n WHITE_BALANCE_PROFILE_SCHEMA_VERSION +\n '\".'\n );\n }\n if (record.scientificStatus !== \"approximation\") {\n throw new InvalidConfigurationError(\n 'whiteBalanceProfile.scientificStatus must be \"approximation\".'\n );\n }\n if (record.inputDomain !== \"relative-pre-wb-camera-linear-rgb\") {\n throw new InvalidConfigurationError(\n 'whiteBalanceProfile.inputDomain must be \"relative-pre-wb-camera-linear-rgb\".'\n );\n }\n if (!Array.isArray(record.presets)) {\n throw new InvalidConfigurationError(\n \"whiteBalanceProfile.presets must be an array.\"\n );\n }\n if (!Array.isArray(record.awbPolicies) || record.awbPolicies.length === 0) {\n throw new InvalidConfigurationError(\n \"whiteBalanceProfile.awbPolicies must be a non-empty array.\"\n );\n }\n\n const presets = record.presets.map((entry, index) =>\n parsePreset(entry, \"whiteBalanceProfile.presets[\" + index + \"]\")\n );\n const policies = record.awbPolicies.map((entry, index) =>\n parseAwbPolicy(entry, \"whiteBalanceProfile.awbPolicies[\" + index + \"]\")\n );\n\n const presetIds = presets.map((entry) => entry.presetId);\n const policyIds = policies.map((entry) => entry.policyId);\n if (new Set(presetIds).size !== presetIds.length) {\n throw new InvalidConfigurationError(\n \"whiteBalanceProfile.presets must not contain duplicate presetId values.\"\n );\n }\n if (new Set(policyIds).size !== policyIds.length) {\n throw new InvalidConfigurationError(\n \"whiteBalanceProfile.awbPolicies must not contain duplicate policyId values.\"\n );\n }\n\n return {\n schemaVersion: WHITE_BALANCE_PROFILE_SCHEMA_VERSION,\n profileId: requireNonEmptyString(\n record.profileId,\n \"whiteBalanceProfile.profileId\"\n ),\n profileVersion: requireNonEmptyString(\n record.profileVersion,\n \"whiteBalanceProfile.profileVersion\"\n ),\n scientificStatus: \"approximation\",\n inputDomain: \"relative-pre-wb-camera-linear-rgb\",\n presets,\n awbPolicies: policies,\n evidence: parseEvidenceList(record.evidence, \"whiteBalanceProfile.evidence\"),\n limitations: parseLimitations(\n record.limitations,\n \"whiteBalanceProfile.limitations\"\n )\n };\n}\n\nfunction requireScientificNonEmptyString(\n value: string,\n path: string\n): string {\n if (typeof value !== \"string\" || value.trim().length === 0) {\n throw new InvalidConfigurationError(\n path + \" must be a non-empty string.\"\n );\n }\n return value.trim();\n}\n\nfunction requireScientificFinite(\n value: number,\n path: string\n): number {\n if (!Number.isFinite(value)) {\n throw new InvalidScientificInputError(path + \" must be finite.\");\n }\n return value;\n}\n\nfunction requireScientificPositiveFinite(\n value: number,\n path: string\n): number {\n const parsed = requireScientificFinite(value, path);\n if (parsed <= 0) {\n throw new InvalidScientificInputError(\n path + \" must be greater than zero.\"\n );\n }\n return parsed;\n}\n\nfunction requireScientificNonNegativeFinite(\n value: number,\n path: string\n): number {\n const parsed = requireScientificFinite(value, path);\n if (parsed < 0) {\n throw new InvalidScientificInputError(\n path + \" must be greater than or equal to zero.\"\n );\n }\n return parsed;\n}\n\nfunction validateResolvedGains(\n gains: WhiteBalanceChannelGains,\n path: string\n): WhiteBalanceChannelGains {\n return {\n red: requireScientificPositiveFinite(gains.red, path + \".red\"),\n green: requireScientificPositiveFinite(gains.green, path + \".green\"),\n blue: requireScientificPositiveFinite(gains.blue, path + \".blue\")\n };\n}\n\nfunction immutableState(\n state: ResolvedWhiteBalanceState\n): ResolvedWhiteBalanceState {\n return Object.freeze({\n ...state,\n channelGains: Object.freeze({ ...state.channelGains }),\n limitations: Object.freeze([...state.limitations]),\n ...(state.sourceProfile === undefined\n ? {}\n : { sourceProfile: Object.freeze({ ...state.sourceProfile }) }),\n ...(state.awbPolicy === undefined\n ? {}\n : { awbPolicy: Object.freeze({ ...state.awbPolicy }) }),\n ...(state.colorTemperature === undefined\n ? {}\n : {\n colorTemperature: Object.freeze({\n ...state.colorTemperature,\n adoptedWhiteChromaticity: Object.freeze({ ...state.colorTemperature.adoptedWhiteChromaticity }),\n cameraNeutralRgb: Object.freeze({ ...state.colorTemperature.cameraNeutralRgb })\n })\n }),\n ...(state.measurement === undefined\n ? {}\n : {\n measurement: Object.freeze({\n ...state.measurement,\n weightedMeanPreWbSignal: Object.freeze({\n ...state.measurement.weightedMeanPreWbSignal\n })\n })\n })\n });\n}\n\nfunction stateBase(\n stateId: string,\n source: ResolvedWhiteBalanceState[\"source\"],\n gains: WhiteBalanceChannelGains,\n limitations: readonly string[]\n): Pick<\n ResolvedWhiteBalanceState,\n | \"version\"\n | \"stateId\"\n | \"inputDomain\"\n | \"source\"\n | \"channelGains\"\n | \"locked\"\n | \"trueIlluminantMetadataUsed\"\n | \"sceneIlluminationModified\"\n | \"rawCaptureDestructivelyModified\"\n | \"physicalExposureModified\"\n | \"focusModified\"\n | \"limitations\"\n> {\n return {\n version: WHITE_BALANCE_STATE_VERSION,\n stateId: requireScientificNonEmptyString(stateId, \"stateId\"),\n inputDomain: \"relative-pre-wb-camera-linear-rgb\",\n source,\n channelGains: validateResolvedGains(gains, \"channelGains\"),\n locked: false,\n trueIlluminantMetadataUsed: false,\n sceneIlluminationModified: false,\n rawCaptureDestructivelyModified: false,\n physicalExposureModified: false,\n focusModified: false,\n limitations: [...limitations]\n };\n}\n\n/** Resolves a WB preset defined by the profile. No universal label-to-Kelvin rule is applied. */\nexport function resolvePresetWhiteBalance(\n input: ResolvePresetWhiteBalanceInput\n): ResolvedWhiteBalanceState {\n requireInputKeys(input, \"resolvePresetWhiteBalance\", [\"stateId\", \"profile\", \"presetId\"]);\n const profile = parseWhiteBalanceProfile(input.profile);\n const presetId = requireScientificNonEmptyString(\n input.presetId,\n \"presetId\"\n );\n const preset = profile.presets.find((entry) => entry.presetId === presetId);\n if (preset === undefined) {\n throw new InvalidScientificInputError(\n \"presetId is not declared by the selected white-balance profile.\"\n );\n }\n\n return immutableState({\n ...stateBase(\n input.stateId,\n \"preset\",\n preset.channelGains.value,\n [\n ...profile.limitations,\n ...(preset.limitations ?? [])\n ]\n ),\n sourceProfile: {\n profileId: profile.profileId,\n profileVersion: profile.profileVersion\n },\n presetId\n });\n}\n\n/** Resolves explicit manual camera-linear channel gains. */\nexport function resolveManualWhiteBalance(\n input: ResolveManualWhiteBalanceInput\n): ResolvedWhiteBalanceState {\n requireInputKeys(input, \"resolveManualWhiteBalance\", [\"stateId\", \"channelGains\"]);\n return immutableState(\n stateBase(\n input.stateId,\n \"manual-gains\",\n input.channelGains,\n [\n \"Manual gains are caller-selected WB intent, not a measured physical illuminant.\"\n ]\n )\n );\n}\n\n/**\n * Records independent color-temperature and tint intent.\n *\n * No channel gains are fabricated here; use\n * `resolveColorTemperatureWhiteBalance()` with an explicit camera colour model to\n * resolve gains.\n */\nexport function createColorTemperatureWhiteBalanceIntent(\n input: CreateColorTemperatureWhiteBalanceIntentInput\n): ColorTemperatureWhiteBalanceIntent {\n requireInputKeys(input, \"createColorTemperatureWhiteBalanceIntent\", [\"intentId\", \"colorTemperatureKelvin\", \"tint\"]);\n return Object.freeze({\n version: COLOR_TEMPERATURE_WHITE_BALANCE_INTENT_VERSION,\n intentId: requireScientificNonEmptyString(input.intentId, \"intentId\"),\n colorTemperatureKelvin: requireScientificPositiveFinite(\n input.colorTemperatureKelvin,\n \"colorTemperatureKelvin\"\n ),\n tint: requireScientificFinite(input.tint, \"tint\"),\n channelGainsResolved: false,\n requiresCameraProfileColorimetry: true,\n sceneIlluminationModified: false\n });\n}\n\n/**\n * Resolves a Kelvin + tint WB intent into camera channel gains, for an explicit camera\n * colour model:\n * - white xy = locus(CCT), offset by Duv = tint along the Planckian-locus normal in CIE 1960 uv;\n * - camera neutral n = M_XYZ→camera · XYZ(white, Y = 1);\n * - gains = (n_G/n_R, 1, n_G/n_B).\n * A neutral surface lit by light of exactly that chromaticity then renders with equal channels.\n * The CCT and tint are the white the photographer declares, not a measured scene illuminant.\n * Accuracy is limited by the camera matrix (exact only under the Luther–Ives condition) and by\n * the locus model.\n */\nexport function resolveColorTemperatureWhiteBalance(\n input: ResolveColorTemperatureWhiteBalanceInput\n): ResolvedWhiteBalanceState {\n requireInputKeys(input, \"resolveColorTemperatureWhiteBalance\", [\"stateId\", \"intent\", \"whiteLocus\", \"tintInterpretation\", \"planckianLocus\", \"camera\"]);\n const intent = input.intent;\n if (\n typeof intent !== \"object\" ||\n intent === null ||\n intent.version !== COLOR_TEMPERATURE_WHITE_BALANCE_INTENT_VERSION\n ) {\n throw new InvalidConfigurationError(\n \"intent must be a color-temperature WB intent of version \" +\n COLOR_TEMPERATURE_WHITE_BALANCE_INTENT_VERSION +\n \".\"\n );\n }\n const intentId = requireScientificNonEmptyString(intent.intentId, \"intent.intentId\");\n const kelvin = requireScientificPositiveFinite(intent.colorTemperatureKelvin, \"intent.colorTemperatureKelvin\");\n const tint = requireScientificFinite(intent.tint, \"intent.tint\");\n if (input.tintInterpretation !== \"duv-cie-1960-uv\") {\n throw new InvalidConfigurationError('tintInterpretation must be \"duv-cie-1960-uv\".');\n }\n const camera = input.camera;\n if (typeof camera !== \"object\" || camera === null) {\n throw new InvalidConfigurationError(\"camera must be an object.\");\n }\n const profileId = requireScientificNonEmptyString(camera.profileId, \"camera.profileId\");\n const profileVersion = requireScientificNonEmptyString(camera.profileVersion, \"camera.profileVersion\");\n const matrix = parseMatrix3x3(camera.xyzToCameraRgb, \"camera.xyzToCameraRgb\");\n const locus: PlanckianLocusModel = input.planckianLocus ?? { kind: \"planck-analytic-cmf\" };\n const white = calculateChromaticityFromCorrelatedColorTemperature({\n correlatedColorTemperatureKelvin: kelvin,\n duv: tint,\n whiteLocus: input.whiteLocus,\n locus\n }).value;\n const xyz = xyzOfChromaticity(white);\n const [red, green, blue] = multiplyMatrixVector(matrix, [xyz.x, xyz.y, xyz.z]);\n if (!(red > 0) || !(green > 0) || !(blue > 0)) {\n throw new InvalidScientificInputError(\n \"The camera response to the declared white must be positive in every channel.\"\n );\n }\n return immutableState({\n ...stateBase(\n input.stateId,\n \"color-temperature\",\n { red: green / red, green: 1, blue: green / blue },\n [\n \"Kelvin/tint gains neutralize the declared white through the supplied camera matrix; they do not identify the scene illuminant.\",\n \"Tint is Duv in CIE 1960 uv; accuracy is bounded by the camera matrix and the locus model.\"\n ]\n ),\n sourceProfile: { profileId, profileVersion },\n colorTemperature: {\n intentId,\n colorTemperatureKelvin: kelvin,\n tint,\n whiteLocus: input.whiteLocus,\n tintInterpretation: \"duv-cie-1960-uv\",\n planckianLocusModel: locus.kind,\n adoptedWhiteChromaticity: { x: white.x, y: white.y },\n cameraNeutralRgb: { red, green, blue }\n }\n });\n}\n\nfunction reduceSampleSet(\n sampleSet: PreWhiteBalanceRgbSampleSet,\n clippedPolicy: \"reject-any\" | \"exclude\"\n): {\n imageStateId: string;\n usableSampleCount: number;\n rejectedClippedSampleCount: number;\n weightedMean: {\n red: number;\n green: number;\n blue: number;\n };\n} {\n requireInputObject(sampleSet, \"sampleSet input\");\n if (sampleSet.inputDomain !== \"relative-pre-wb-camera-linear-rgb\") {\n throw new InvalidConfigurationError(\n 'sampleSet.inputDomain must be \"relative-pre-wb-camera-linear-rgb\".'\n );\n }\n const imageStateId = requireScientificNonEmptyString(\n sampleSet.imageStateId,\n \"sampleSet.imageStateId\"\n );\n if (!Array.isArray(sampleSet.samples) || sampleSet.samples.length === 0) {\n throw new InvalidConfigurationError(\n \"sampleSet.samples must be a non-empty array.\"\n );\n }\n\n let weightSum = 0;\n let redSum = 0;\n let greenSum = 0;\n let blueSum = 0;\n let rejectedClippedSampleCount = 0;\n const ids = new Set<string>();\n\n sampleSet.samples.forEach((sample, index) => {\n const path = \"sampleSet.samples[\" + index + \"]\";\n const sampleId = requireScientificNonEmptyString(\n sample.sampleId,\n path + \".sampleId\"\n );\n if (ids.has(sampleId)) {\n throw new InvalidScientificInputError(\n \"sampleSet.samples must not contain duplicate sampleId values.\"\n );\n }\n ids.add(sampleId);\n\n const red = requireScientificNonNegativeFinite(sample.red, path + \".red\");\n const green = requireScientificNonNegativeFinite(\n sample.green,\n path + \".green\"\n );\n const blue = requireScientificNonNegativeFinite(\n sample.blue,\n path + \".blue\"\n );\n const weight = requireScientificPositiveFinite(\n sample.weight,\n path + \".weight\"\n );\n\n if (sample.clipped) {\n rejectedClippedSampleCount += 1;\n if (clippedPolicy === \"reject-any\") {\n throw new InvalidScientificInputError(\n \"Custom white-balance measurement must not contain clipped samples.\"\n );\n }\n return;\n }\n\n weightSum += weight;\n redSum += red * weight;\n greenSum += green * weight;\n blueSum += blue * weight;\n });\n\n if (weightSum <= 0) {\n throw new InvalidScientificInputError(\n \"White-balance estimation requires at least one usable unclipped sample.\"\n );\n }\n\n const weightedMean = {\n red: redSum / weightSum,\n green: greenSum / weightSum,\n blue: blueSum / weightSum\n };\n\n if (\n weightedMean.red <= 0 ||\n weightedMean.green <= 0 ||\n weightedMean.blue <= 0\n ) {\n throw new InvalidScientificInputError(\n \"White-balance estimation requires positive signal in every camera-linear channel.\"\n );\n }\n\n return {\n imageStateId,\n usableSampleCount:\n sampleSet.samples.length - rejectedClippedSampleCount,\n rejectedClippedSampleCount,\n weightedMean\n };\n}\n\nfunction neutralizingGains(\n mean: {\n red: number;\n green: number;\n blue: number;\n }\n): WhiteBalanceChannelGains {\n return {\n red: mean.green / mean.red,\n green: 1,\n blue: mean.green / mean.blue\n };\n}\n\n/**\n * Resolves a user-declared neutral/gray custom-WB measurement.\n *\n * The engine validates and reduces the selected pre-WB sample, but it does not\n * claim the selected object is spectrally neutral in the real scene.\n */\nexport function resolveCustomWhiteBalance(\n input: ResolveCustomWhiteBalanceInput\n): ResolvedWhiteBalanceState {\n requireInputKeys(input, \"resolveCustomWhiteBalance\", [\"stateId\", \"sampleSet\"]);\n const reduced = reduceSampleSet(input.sampleSet, \"reject-any\");\n\n return immutableState({\n ...stateBase(\n input.stateId,\n \"custom-measurement\",\n neutralizingGains(reduced.weightedMean),\n [\n \"Custom WB assumes the caller-selected measurement target is intended to be neutral.\",\n \"Resolved gains are camera-linear relative corrections, not a recovered physical illuminant spectrum.\"\n ]\n ),\n measurement: {\n imageStateId: reduced.imageStateId,\n usableSampleCount: reduced.usableSampleCount,\n rejectedClippedSampleCount: reduced.rejectedClippedSampleCount,\n weightedMeanPreWbSignal: reduced.weightedMean\n }\n });\n}\n\n/**\n * Estimates one global AWB state from declared pre-WB camera-linear samples.\n *\n * It deliberately does not accept metadata about the true illuminant. A\n * grey-world neutralizing estimate is softened by the profile's\n * correctionStrength, so different generic AWB priorities can keep different\n * amounts of colour cast.\n */\nexport function estimateAutoWhiteBalance(\n input: EstimateAutoWhiteBalanceInput\n): ResolvedWhiteBalanceState {\n requireInputKeys(input, \"estimateAutoWhiteBalance\", [\"stateId\", \"profile\", \"policyId\", \"sampleSet\"]);\n const profile = parseWhiteBalanceProfile(input.profile);\n const policyId = requireScientificNonEmptyString(\n input.policyId,\n \"policyId\"\n );\n const policy = profile.awbPolicies.find(\n (entry) => entry.policyId === policyId\n );\n if (policy === undefined) {\n throw new InvalidScientificInputError(\n \"policyId is not declared by the selected white-balance profile.\"\n );\n }\n\n const reduced = reduceSampleSet(input.sampleSet, \"exclude\");\n const neutral = neutralizingGains(reduced.weightedMean);\n const strength = policy.correctionStrength.value;\n const gains = {\n red: Math.pow(neutral.red, strength),\n green: 1,\n blue: Math.pow(neutral.blue, strength)\n };\n\n return immutableState({\n ...stateBase(\n input.stateId,\n \"auto-white-balance\",\n gains,\n [\n ...profile.limitations,\n ...(policy.limitations ?? []),\n \"AWB is a deterministic gray-world-style global estimate over camera-observable pre-WB signal.\",\n \"One global WB may leave local color casts under mixed illumination.\"\n ]\n ),\n sourceProfile: {\n profileId: profile.profileId,\n profileVersion: profile.profileVersion\n },\n awbPolicy: {\n policyId: policy.policyId,\n intent: policy.intent,\n correctionStrength: strength\n },\n measurement: {\n imageStateId: reduced.imageStateId,\n usableSampleCount: reduced.usableSampleCount,\n rejectedClippedSampleCount: reduced.rejectedClippedSampleCount,\n weightedMeanPreWbSignal: reduced.weightedMean\n }\n });\n}\n\n/**\n * Freezes a resolved WB state under a new stable identity.\n *\n * Locking changes neither the scene nor the gains. Later AWB estimates may\n * differ, but this locked state stays the same.\n */\nexport function createLockedWhiteBalanceState(\n input: CreateLockedWhiteBalanceStateInput\n): ResolvedWhiteBalanceState {\n requireInputKeys(input, \"createLockedWhiteBalanceState\", [\"stateId\", \"sourceState\"]);\n const stateId = requireScientificNonEmptyString(input.stateId, \"stateId\");\n const source = input.sourceState;\n\n return immutableState({\n ...source,\n stateId,\n channelGains: validateResolvedGains(\n source.channelGains,\n \"sourceState.channelGains\"\n ),\n locked: true,\n sourceStateId: requireScientificNonEmptyString(\n source.stateId,\n \"sourceState.stateId\"\n ),\n limitations: [...source.limitations]\n });\n}\n\n\nfunction requireNonNegativeSafeInteger(\n value: unknown,\n path: string\n): number {\n if (\n typeof value !== \"number\" ||\n !Number.isSafeInteger(value) ||\n value < 0\n ) {\n throw new InvalidConfigurationError(\n path + \" must be a non-negative safe integer.\"\n );\n }\n return value;\n}\n\nfunction requirePositiveSafeInteger(\n value: unknown,\n path: string\n): number {\n const parsed =\n requireNonNegativeSafeInteger(\n value,\n path\n );\n if (parsed <= 0) {\n throw new InvalidConfigurationError(\n path + \" must be greater than zero.\"\n );\n }\n return parsed;\n}\n\nfunction parseResolvedWhiteBalanceMeasurement(\n value: unknown,\n path: string\n): NonNullable<\n ResolvedWhiteBalanceState[\"measurement\"]\n> {\n const record =\n requireRecord(value, path, [\"weightedMeanPreWbSignal\", \"imageStateId\", \"usableSampleCount\", \"rejectedClippedSampleCount\"]);\n const mean =\n requireRecord(\n record.weightedMeanPreWbSignal,\n path +\n \".weightedMeanPreWbSignal\", [\"red\", \"green\", \"blue\"]\n );\n\n return {\n imageStateId:\n requireNonEmptyString(\n record.imageStateId,\n path + \".imageStateId\"\n ),\n usableSampleCount:\n requirePositiveSafeInteger(\n record.usableSampleCount,\n path +\n \".usableSampleCount\"\n ),\n rejectedClippedSampleCount:\n requireNonNegativeSafeInteger(\n record\n .rejectedClippedSampleCount,\n path +\n \".rejectedClippedSampleCount\"\n ),\n weightedMeanPreWbSignal: {\n red:\n requirePositiveFinite(\n mean.red,\n path +\n \".weightedMeanPreWbSignal.red\"\n ),\n green:\n requirePositiveFinite(\n mean.green,\n path +\n \".weightedMeanPreWbSignal.green\"\n ),\n blue:\n requirePositiveFinite(\n mean.blue,\n path +\n \".weightedMeanPreWbSignal.blue\"\n )\n }\n };\n}\n\nfunction parseResolvedColorTemperature(\n value: unknown,\n path: string\n): ResolvedColorTemperatureWhiteBalance {\n const record = requireRecord(value, path, [\"whiteLocus\", \"tintInterpretation\", \"planckianLocusModel\", \"adoptedWhiteChromaticity\", \"intentId\", \"colorTemperatureKelvin\", \"tint\", \"cameraNeutralRgb\"]);\n if (record.whiteLocus !== \"planckian\" && record.whiteLocus !== \"cie-daylight\") {\n throw new InvalidConfigurationError(path + \".whiteLocus is invalid.\");\n }\n if (record.tintInterpretation !== \"duv-cie-1960-uv\") {\n throw new InvalidConfigurationError(path + \".tintInterpretation is invalid.\");\n }\n if (\n record.planckianLocusModel !== \"planck-analytic-cmf\" &&\n record.planckianLocusModel !== \"planck-integration\"\n ) {\n throw new InvalidConfigurationError(path + \".planckianLocusModel is invalid.\");\n }\n const white = requireRecord(record.adoptedWhiteChromaticity, path + \".adoptedWhiteChromaticity\", [\"x\", \"y\"]);\n return {\n intentId: requireNonEmptyString(record.intentId, path + \".intentId\"),\n colorTemperatureKelvin: requirePositiveFinite(record.colorTemperatureKelvin, path + \".colorTemperatureKelvin\"),\n tint: requireFinite(record.tint, path + \".tint\"),\n whiteLocus: record.whiteLocus,\n tintInterpretation: \"duv-cie-1960-uv\",\n planckianLocusModel: record.planckianLocusModel,\n adoptedWhiteChromaticity: {\n x: requirePositiveFinite(white.x, path + \".adoptedWhiteChromaticity.x\"),\n y: requirePositiveFinite(white.y, path + \".adoptedWhiteChromaticity.y\")\n },\n cameraNeutralRgb: parseChannelGains(record.cameraNeutralRgb, path + \".cameraNeutralRgb\")\n };\n}\n\n/**\n * Parses a committed, resolved white-balance state from untrusted JSON,\n * without estimating WB again.\n *\n * This is deliberately a state parser, not an AWB estimator. It keeps the\n * resolved gains, policy and measurement identity that a capture committed\n * earlier.\n */\nexport function parseResolvedWhiteBalanceState(\n value: unknown\n): ResolvedWhiteBalanceState {\n const record =\n requireRecord(\n value,\n \"resolvedWhiteBalanceState\", [\"version\", \"inputDomain\", \"source\", \"locked\", \"sourceProfile\", \"awbPolicy\", \"measurement\", \"colorTemperature\", \"presetId\", \"sourceStateId\", \"stateId\", \"channelGains\", \"limitations\", \"trueIlluminantMetadataUsed\", \"sceneIlluminationModified\", \"rawCaptureDestructivelyModified\", \"physicalExposureModified\", \"focusModified\"]\n );\n\n if (\n record.version !==\n WHITE_BALANCE_STATE_VERSION\n ) {\n throw new InvalidConfigurationError(\n 'resolvedWhiteBalanceState.version must be \"' +\n WHITE_BALANCE_STATE_VERSION +\n '\".'\n );\n }\n if (\n record.inputDomain !==\n \"relative-pre-wb-camera-linear-rgb\"\n ) {\n throw new InvalidConfigurationError(\n 'resolvedWhiteBalanceState.inputDomain must be \"relative-pre-wb-camera-linear-rgb\".'\n );\n }\n if (\n record.source !== \"preset\" &&\n record.source !==\n \"manual-gains\" &&\n record.source !==\n \"custom-measurement\" &&\n record.source !==\n \"auto-white-balance\" &&\n record.source !==\n \"color-temperature\"\n ) {\n throw new InvalidConfigurationError(\n \"resolvedWhiteBalanceState.source is invalid.\"\n );\n }\n if (\n typeof record.locked !==\n \"boolean\"\n ) {\n throw new InvalidConfigurationError(\n \"resolvedWhiteBalanceState.locked must be boolean.\"\n );\n }\n\n for (const key of [\n \"trueIlluminantMetadataUsed\",\n \"sceneIlluminationModified\",\n \"rawCaptureDestructivelyModified\",\n \"physicalExposureModified\",\n \"focusModified\"\n ] as const) {\n if (record[key] !== false) {\n throw new InvalidConfigurationError(\n \"resolvedWhiteBalanceState.\" +\n key +\n \" must remain false.\"\n );\n }\n }\n\n const sourceProfile =\n record.sourceProfile === undefined\n ? undefined\n : ((): NonNullable<ResolvedWhiteBalanceState[\"sourceProfile\"]> => {\n const profile =\n requireRecord(\n record.sourceProfile,\n \"resolvedWhiteBalanceState.sourceProfile\", [\"profileId\", \"profileVersion\"]\n );\n return {\n profileId:\n requireNonEmptyString(\n profile.profileId,\n \"resolvedWhiteBalanceState.sourceProfile.profileId\"\n ),\n profileVersion:\n requireNonEmptyString(\n profile.profileVersion,\n \"resolvedWhiteBalanceState.sourceProfile.profileVersion\"\n )\n };\n })();\n\n const awbPolicy =\n record.awbPolicy === undefined\n ? undefined\n : ((): NonNullable<ResolvedWhiteBalanceState[\"awbPolicy\"]> => {\n const policy =\n requireRecord(\n record.awbPolicy,\n \"resolvedWhiteBalanceState.awbPolicy\", [\"policyId\", \"intent\", \"correctionStrength\"]\n );\n return {\n policyId:\n requireNonEmptyString(\n policy.policyId,\n \"resolvedWhiteBalanceState.awbPolicy.policyId\"\n ),\n intent:\n parseAwbIntent(\n policy.intent,\n \"resolvedWhiteBalanceState.awbPolicy.intent\"\n ),\n correctionStrength:\n requireFraction(\n policy.correctionStrength,\n \"resolvedWhiteBalanceState.awbPolicy.correctionStrength\"\n )\n };\n })();\n\n const measurement =\n record.measurement === undefined\n ? undefined\n : parseResolvedWhiteBalanceMeasurement(\n record.measurement,\n \"resolvedWhiteBalanceState.measurement\"\n );\n\n const colorTemperature =\n record.colorTemperature === undefined\n ? undefined\n : parseResolvedColorTemperature(\n record.colorTemperature,\n \"resolvedWhiteBalanceState.colorTemperature\"\n );\n\n const presetId =\n record.presetId === undefined\n ? undefined\n : requireNonEmptyString(\n record.presetId,\n \"resolvedWhiteBalanceState.presetId\"\n );\n\n const sourceStateId =\n record.sourceStateId ===\n undefined\n ? undefined\n : requireNonEmptyString(\n record.sourceStateId,\n \"resolvedWhiteBalanceState.sourceStateId\"\n );\n\n if (\n record.source === \"preset\" &&\n (sourceProfile === undefined ||\n presetId === undefined)\n ) {\n throw new InvalidConfigurationError(\n \"A preset WB state requires sourceProfile and presetId.\"\n );\n }\n\n if (\n record.source ===\n \"custom-measurement\" &&\n measurement === undefined\n ) {\n throw new InvalidConfigurationError(\n \"A custom-measurement WB state requires measurement identity.\"\n );\n }\n\n if (\n record.source ===\n \"auto-white-balance\" &&\n (sourceProfile === undefined ||\n awbPolicy === undefined ||\n measurement === undefined)\n ) {\n throw new InvalidConfigurationError(\n \"An auto-white-balance state requires sourceProfile, awbPolicy, and measurement identity.\"\n );\n }\n\n if (\n (record.source === \"color-temperature\") !==\n (colorTemperature !== undefined) ||\n (record.source === \"color-temperature\" &&\n sourceProfile === undefined)\n ) {\n throw new InvalidConfigurationError(\n \"A color-temperature WB state requires sourceProfile and colorTemperature; other sources must not declare colorTemperature.\"\n );\n }\n\n if (\n record.locked &&\n sourceStateId === undefined\n ) {\n throw new InvalidConfigurationError(\n \"A locked WB state requires sourceStateId.\"\n );\n }\n\n if (\n !record.locked &&\n sourceStateId !== undefined\n ) {\n throw new InvalidConfigurationError(\n \"An unlocked WB state must not declare sourceStateId.\"\n );\n }\n\n return immutableState({\n version:\n WHITE_BALANCE_STATE_VERSION,\n stateId:\n requireNonEmptyString(\n record.stateId,\n \"resolvedWhiteBalanceState.stateId\"\n ),\n inputDomain:\n \"relative-pre-wb-camera-linear-rgb\",\n source: record.source,\n channelGains:\n parseChannelGains(\n record.channelGains,\n \"resolvedWhiteBalanceState.channelGains\"\n ),\n locked: record.locked,\n ...(sourceProfile === undefined\n ? {}\n : {\n sourceProfile\n }),\n ...(presetId === undefined\n ? {}\n : {\n presetId\n }),\n ...(awbPolicy === undefined\n ? {}\n : {\n awbPolicy\n }),\n ...(measurement === undefined\n ? {}\n : {\n measurement\n }),\n ...(colorTemperature === undefined\n ? {}\n : {\n colorTemperature\n }),\n ...(sourceStateId === undefined\n ? {}\n : {\n sourceStateId\n }),\n trueIlluminantMetadataUsed:\n false,\n sceneIlluminationModified:\n false,\n rawCaptureDestructivelyModified:\n false,\n physicalExposureModified:\n false,\n focusModified: false,\n limitations:\n parseLimitations(\n record.limitations,\n \"resolvedWhiteBalanceState.limitations\"\n )\n });\n}\n"]}
|
|
1
|
+
{"version":3,"file":"white-balance.js","sourceRoot":"","sources":["../../src/color/white-balance.ts"],"names":[],"mappings":"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","sourcesContent":["// SPDX-License-Identifier: Apache-2.0\n\n/**\n * White balance (WB): generic presets, manual gains, colour temperature and tint, custom (grey-card)\n * WB, auto white balance (AWB), WB lock, and parsing of a committed WB state.\n *\n * The profile defines preset gains and AWB correction strength. A label such as \"Daylight\" is not\n * treated as a universal Kelvin value or as any manufacturer's behaviour.\n * @see docs/CAPTURE_COLOR.md for the equations, units, coordinate conventions, known blockers and\n * support limits.\n */\n\nimport { InvalidConfigurationError } from \"../core/configuration-error.js\";\nimport {\n parseEvidenceList,\n type EvidenceBackedFact,\n type EvidenceProvenance\n} from \"../core/evidence-provenance.js\";\nimport { InvalidScientificInputError } from \"../core/validation.js\";\nimport { requireInputObject, requireInputKeys, rejectUnknownFields } from \"../core/record-validation.js\";\nimport {\n calculateChromaticityFromCorrelatedColorTemperature,\n calculatePortableChromaticityFromCorrelatedColorTemperature,\n type PlanckianLocusModel,\n type WhiteLocus\n} from \"./illuminants.js\";\nimport {\n multiplyMatrixVector,\n parseMatrix3x3,\n xyzOfChromaticity,\n type CieXyChromaticity,\n type ColorMatrix3x3\n} from \"./colorimetry-math.js\";\n\ntype UnknownRecord = Record<string, unknown>;\n\nexport const WHITE_BALANCE_PROFILE_SCHEMA_VERSION = \"0.1.0\" as const;\nexport const WHITE_BALANCE_STATE_VERSION = \"0.1.0\" as const;\nexport const COLOR_TEMPERATURE_WHITE_BALANCE_INTENT_VERSION =\n \"0.1.0\" as const;\n\nexport type WhiteBalanceInputDomain =\n \"relative-pre-wb-camera-linear-rgb\";\n\nexport interface WhiteBalanceChannelGains {\n red: number;\n green: number;\n blue: number;\n}\n\nexport type WhiteBalanceAwbIntent =\n | \"neutral-priority\"\n | \"standard\"\n | \"ambience-preserving\";\n\nexport interface WhiteBalancePresetDefinition {\n presetId: string;\n label: string;\n channelGains: EvidenceBackedFact<WhiteBalanceChannelGains>;\n nominalColorTemperatureKelvin?: number;\n nominalTint?: number;\n limitations?: readonly string[];\n}\n\nexport interface WhiteBalanceAwbPolicy {\n policyId: string;\n intent: WhiteBalanceAwbIntent;\n /**\n * How much of a grey-world neutralizing correction to apply, measured in\n * logarithmic gain space. 1 applies the full correction (neutral priority).\n * Lower values keep more of the observed colour cast.\n */\n correctionStrength: EvidenceBackedFact<number>;\n limitations?: readonly string[];\n}\n\nexport interface WhiteBalanceProfile {\n schemaVersion: typeof WHITE_BALANCE_PROFILE_SCHEMA_VERSION;\n profileId: string;\n profileVersion: string;\n scientificStatus: \"approximation\";\n inputDomain: WhiteBalanceInputDomain;\n presets: readonly WhiteBalancePresetDefinition[];\n awbPolicies: readonly WhiteBalanceAwbPolicy[];\n evidence: readonly EvidenceProvenance[];\n limitations: readonly string[];\n}\n\nexport interface PreWhiteBalanceRgbSample {\n sampleId: string;\n red: number;\n green: number;\n blue: number;\n weight: number;\n clipped: boolean;\n}\n\nexport interface PreWhiteBalanceRgbSampleSet {\n imageStateId: string;\n inputDomain: WhiteBalanceInputDomain;\n samples: readonly PreWhiteBalanceRgbSample[];\n}\n\nexport interface ResolvedWhiteBalanceState {\n version: typeof WHITE_BALANCE_STATE_VERSION;\n stateId: string;\n inputDomain: WhiteBalanceInputDomain;\n source:\n | \"preset\"\n | \"manual-gains\"\n | \"custom-measurement\"\n | \"auto-white-balance\"\n | \"color-temperature\";\n channelGains: WhiteBalanceChannelGains;\n locked: boolean;\n sourceProfile?: {\n profileId: string;\n profileVersion: string;\n };\n presetId?: string;\n awbPolicy?: {\n policyId: string;\n intent: WhiteBalanceAwbIntent;\n correctionStrength: number;\n };\n measurement?: {\n imageStateId: string;\n usableSampleCount: number;\n rejectedClippedSampleCount: number;\n weightedMeanPreWbSignal: {\n red: number;\n green: number;\n blue: number;\n };\n };\n /** Present for `color-temperature` states: the declared CCT/tint and its camera neutral. */\n colorTemperature?: ResolvedColorTemperatureWhiteBalance;\n sourceStateId?: string;\n trueIlluminantMetadataUsed: false;\n sceneIlluminationModified: false;\n rawCaptureDestructivelyModified: false;\n physicalExposureModified: false;\n focusModified: false;\n limitations: readonly string[];\n}\n\nexport interface ColorTemperatureWhiteBalanceIntent {\n version: typeof COLOR_TEMPERATURE_WHITE_BALANCE_INTENT_VERSION;\n intentId: string;\n colorTemperatureKelvin: number;\n tint: number;\n channelGainsResolved: false;\n requiresCameraProfileColorimetry: true;\n sceneIlluminationModified: false;\n}\n\n/** Locus/tint interpretation and camera neutral behind a Kelvin + tint WB state. */\nexport interface ResolvedColorTemperatureWhiteBalance {\n intentId: string;\n colorTemperatureKelvin: number;\n tint: number;\n whiteLocus: WhiteLocus;\n tintInterpretation: \"duv-cie-1960-uv\";\n planckianLocusModel: \"planck-analytic-cmf\" | \"planck-integration\";\n /** CIE 1931 xy of the declared white (CCT + Duv). */\n adoptedWhiteChromaticity: CieXyChromaticity;\n /** Pre-WB camera response to that white (XYZ with Y = 1 through xyzToCameraRgb). */\n cameraNeutralRgb: WhiteBalanceChannelGains;\n}\n\n/** Camera colour model used to turn a declared white into channel gains. */\nexport interface ColorTemperatureWhiteBalanceCameraModel {\n profileId: string;\n profileVersion: string;\n /** Row-major CIE XYZ (white Y = 1) → relative pre-WB camera-linear RGB. */\n xyzToCameraRgb: ColorMatrix3x3;\n}\n\nexport interface ResolveColorTemperatureWhiteBalanceInput {\n stateId: string;\n intent: ColorTemperatureWhiteBalanceIntent;\n /** Locus whose temperature defines the white: Planckian or CIE daylight. */\n whiteLocus: WhiteLocus;\n /** Tint is read as Duv in the CIE 1960 UCS (positive = above the Planckian locus, greenish). */\n tintInterpretation: \"duv-cie-1960-uv\";\n /** Defaults to Planck's law integrated against the engine's analytic CIE 1931 CMFs (`planck-analytic-cmf`). */\n planckianLocus?: PlanckianLocusModel;\n camera: ColorTemperatureWhiteBalanceCameraModel;\n}\n\nexport interface ResolvePresetWhiteBalanceInput {\n stateId: string;\n profile: WhiteBalanceProfile;\n presetId: string;\n}\n\nexport interface ResolveManualWhiteBalanceInput {\n stateId: string;\n channelGains: WhiteBalanceChannelGains;\n}\n\nexport interface CreateColorTemperatureWhiteBalanceIntentInput {\n intentId: string;\n colorTemperatureKelvin: number;\n tint: number;\n}\n\nexport interface ResolveCustomWhiteBalanceInput {\n stateId: string;\n sampleSet: PreWhiteBalanceRgbSampleSet;\n}\n\nexport interface EstimateAutoWhiteBalanceInput {\n stateId: string;\n profile: WhiteBalanceProfile;\n policyId: string;\n sampleSet: PreWhiteBalanceRgbSampleSet;\n}\n\nexport interface CreateLockedWhiteBalanceStateInput {\n stateId: string;\n sourceState: ResolvedWhiteBalanceState;\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(path + \" must be an object.\");\n }\n if (allowedKeys !== null) rejectUnknownFields(value, allowedKeys, path);\n return value as UnknownRecord;\n}\n\nfunction requireNonEmptyString(value: unknown, path: string): string {\n if (typeof value !== \"string\" || value.trim().length === 0) {\n throw new InvalidConfigurationError(\n path + \" must be a non-empty string.\"\n );\n }\n return value.trim();\n}\n\nfunction requireFinite(value: unknown, path: string): number {\n if (typeof value !== \"number\" || !Number.isFinite(value)) {\n throw new InvalidConfigurationError(path + \" must be finite.\");\n }\n return value;\n}\n\nfunction requirePositiveFinite(value: unknown, path: string): number {\n const parsed = requireFinite(value, path);\n if (parsed <= 0) {\n throw new InvalidConfigurationError(\n path + \" must be greater than zero.\"\n );\n }\n return parsed;\n}\n\nfunction requireFraction(value: unknown, path: string): number {\n const parsed = requireFinite(value, path);\n if (parsed < 0 || parsed > 1) {\n throw new InvalidConfigurationError(\n path + \" must be from zero through one.\"\n );\n }\n return parsed;\n}\n\nfunction parseChannelGains(\n value: unknown,\n path: string\n): WhiteBalanceChannelGains {\n const record = requireRecord(value, path, [\"red\", \"green\", \"blue\"]);\n return {\n red: requirePositiveFinite(record.red, path + \".red\"),\n green: requirePositiveFinite(record.green, path + \".green\"),\n blue: requirePositiveFinite(record.blue, path + \".blue\")\n };\n}\n\nfunction parseLimitations(\n value: unknown,\n path: string\n): readonly string[] {\n if (!Array.isArray(value)) {\n throw new InvalidConfigurationError(path + \" must be an array.\");\n }\n const parsed = value.map((entry, index) =>\n requireNonEmptyString(entry, path + \"[\" + index + \"]\")\n );\n if (new Set(parsed).size !== parsed.length) {\n throw new InvalidConfigurationError(\n path + \" must not contain duplicates.\"\n );\n }\n return parsed;\n}\n\nfunction parseOptionalLimitations(\n value: unknown,\n path: string\n): readonly string[] | undefined {\n return value === undefined ? undefined : parseLimitations(value, path);\n}\n\nfunction parsePreset(\n value: unknown,\n path: string\n): WhiteBalancePresetDefinition {\n const record = requireRecord(value, path, [\"channelGains\", \"limitations\", \"presetId\", \"label\", \"nominalColorTemperatureKelvin\", \"nominalTint\"]);\n const gainsFact = requireRecord(record.channelGains, path + \".channelGains\", [\"value\", \"evidence\"]);\n const limitations = parseOptionalLimitations(\n record.limitations,\n path + \".limitations\"\n );\n\n return {\n presetId: requireNonEmptyString(record.presetId, path + \".presetId\"),\n label: requireNonEmptyString(record.label, path + \".label\"),\n channelGains: {\n value: parseChannelGains(\n gainsFact.value,\n path + \".channelGains.value\"\n ),\n evidence: parseEvidenceList(\n gainsFact.evidence,\n path + \".channelGains.evidence\"\n )\n },\n ...(record.nominalColorTemperatureKelvin === undefined\n ? {}\n : {\n nominalColorTemperatureKelvin: requirePositiveFinite(\n record.nominalColorTemperatureKelvin,\n path + \".nominalColorTemperatureKelvin\"\n )\n }),\n ...(record.nominalTint === undefined\n ? {}\n : {\n nominalTint: requireFinite(\n record.nominalTint,\n path + \".nominalTint\"\n )\n }),\n ...(limitations === undefined\n ? {}\n : {\n limitations\n })\n };\n}\n\nfunction parseAwbIntent(\n value: unknown,\n path: string\n): WhiteBalanceAwbIntent {\n if (\n value !== \"neutral-priority\" &&\n value !== \"standard\" &&\n value !== \"ambience-preserving\"\n ) {\n throw new InvalidConfigurationError(path + \" is invalid.\");\n }\n return value;\n}\n\nfunction parseAwbPolicy(\n value: unknown,\n path: string\n): WhiteBalanceAwbPolicy {\n const record = requireRecord(value, path, [\"correctionStrength\", \"limitations\", \"policyId\", \"intent\"]);\n const strengthFact = requireRecord(\n record.correctionStrength,\n path + \".correctionStrength\", [\"value\", \"evidence\"]\n );\n const limitations = parseOptionalLimitations(\n record.limitations,\n path + \".limitations\"\n );\n\n return {\n policyId: requireNonEmptyString(record.policyId, path + \".policyId\"),\n intent: parseAwbIntent(record.intent, path + \".intent\"),\n correctionStrength: {\n value: requireFraction(\n strengthFact.value,\n path + \".correctionStrength.value\"\n ),\n evidence: parseEvidenceList(\n strengthFact.evidence,\n path + \".correctionStrength.evidence\"\n )\n },\n ...(limitations === undefined ? {} : { limitations })\n };\n}\n\n/**\n * Parses generic WB presets and AWB policies.\n *\n * The profile defines preset gains and AWB correction strength. A label is not\n * treated as a universal Kelvin value or as any manufacturer's behaviour.\n */\nexport function parseWhiteBalanceProfile(\n value: unknown\n): WhiteBalanceProfile {\n const record = requireRecord(value, \"whiteBalanceProfile\", [\"schemaVersion\", \"scientificStatus\", \"inputDomain\", \"presets\", \"awbPolicies\", \"profileId\", \"profileVersion\", \"evidence\", \"limitations\"]);\n\n if (record.schemaVersion !== WHITE_BALANCE_PROFILE_SCHEMA_VERSION) {\n throw new InvalidConfigurationError(\n 'whiteBalanceProfile.schemaVersion must be \"' +\n WHITE_BALANCE_PROFILE_SCHEMA_VERSION +\n '\".'\n );\n }\n if (record.scientificStatus !== \"approximation\") {\n throw new InvalidConfigurationError(\n 'whiteBalanceProfile.scientificStatus must be \"approximation\".'\n );\n }\n if (record.inputDomain !== \"relative-pre-wb-camera-linear-rgb\") {\n throw new InvalidConfigurationError(\n 'whiteBalanceProfile.inputDomain must be \"relative-pre-wb-camera-linear-rgb\".'\n );\n }\n if (!Array.isArray(record.presets)) {\n throw new InvalidConfigurationError(\n \"whiteBalanceProfile.presets must be an array.\"\n );\n }\n if (!Array.isArray(record.awbPolicies) || record.awbPolicies.length === 0) {\n throw new InvalidConfigurationError(\n \"whiteBalanceProfile.awbPolicies must be a non-empty array.\"\n );\n }\n\n const presets = record.presets.map((entry, index) =>\n parsePreset(entry, \"whiteBalanceProfile.presets[\" + index + \"]\")\n );\n const policies = record.awbPolicies.map((entry, index) =>\n parseAwbPolicy(entry, \"whiteBalanceProfile.awbPolicies[\" + index + \"]\")\n );\n\n const presetIds = presets.map((entry) => entry.presetId);\n const policyIds = policies.map((entry) => entry.policyId);\n if (new Set(presetIds).size !== presetIds.length) {\n throw new InvalidConfigurationError(\n \"whiteBalanceProfile.presets must not contain duplicate presetId values.\"\n );\n }\n if (new Set(policyIds).size !== policyIds.length) {\n throw new InvalidConfigurationError(\n \"whiteBalanceProfile.awbPolicies must not contain duplicate policyId values.\"\n );\n }\n\n return {\n schemaVersion: WHITE_BALANCE_PROFILE_SCHEMA_VERSION,\n profileId: requireNonEmptyString(\n record.profileId,\n \"whiteBalanceProfile.profileId\"\n ),\n profileVersion: requireNonEmptyString(\n record.profileVersion,\n \"whiteBalanceProfile.profileVersion\"\n ),\n scientificStatus: \"approximation\",\n inputDomain: \"relative-pre-wb-camera-linear-rgb\",\n presets,\n awbPolicies: policies,\n evidence: parseEvidenceList(record.evidence, \"whiteBalanceProfile.evidence\"),\n limitations: parseLimitations(\n record.limitations,\n \"whiteBalanceProfile.limitations\"\n )\n };\n}\n\nfunction requireScientificNonEmptyString(\n value: string,\n path: string\n): string {\n if (typeof value !== \"string\" || value.trim().length === 0) {\n throw new InvalidConfigurationError(\n path + \" must be a non-empty string.\"\n );\n }\n return value.trim();\n}\n\nfunction requireScientificFinite(\n value: number,\n path: string\n): number {\n if (!Number.isFinite(value)) {\n throw new InvalidScientificInputError(path + \" must be finite.\");\n }\n return value;\n}\n\nfunction requireScientificPositiveFinite(\n value: number,\n path: string\n): number {\n const parsed = requireScientificFinite(value, path);\n if (parsed <= 0) {\n throw new InvalidScientificInputError(\n path + \" must be greater than zero.\"\n );\n }\n return parsed;\n}\n\nfunction requireScientificNonNegativeFinite(\n value: number,\n path: string\n): number {\n const parsed = requireScientificFinite(value, path);\n if (parsed < 0) {\n throw new InvalidScientificInputError(\n path + \" must be greater than or equal to zero.\"\n );\n }\n return parsed;\n}\n\nfunction validateResolvedGains(\n gains: WhiteBalanceChannelGains,\n path: string\n): WhiteBalanceChannelGains {\n return {\n red: requireScientificPositiveFinite(gains.red, path + \".red\"),\n green: requireScientificPositiveFinite(gains.green, path + \".green\"),\n blue: requireScientificPositiveFinite(gains.blue, path + \".blue\")\n };\n}\n\nfunction immutableState(\n state: ResolvedWhiteBalanceState\n): ResolvedWhiteBalanceState {\n return Object.freeze({\n ...state,\n channelGains: Object.freeze({ ...state.channelGains }),\n limitations: Object.freeze([...state.limitations]),\n ...(state.sourceProfile === undefined\n ? {}\n : { sourceProfile: Object.freeze({ ...state.sourceProfile }) }),\n ...(state.awbPolicy === undefined\n ? {}\n : { awbPolicy: Object.freeze({ ...state.awbPolicy }) }),\n ...(state.colorTemperature === undefined\n ? {}\n : {\n colorTemperature: Object.freeze({\n ...state.colorTemperature,\n adoptedWhiteChromaticity: Object.freeze({ ...state.colorTemperature.adoptedWhiteChromaticity }),\n cameraNeutralRgb: Object.freeze({ ...state.colorTemperature.cameraNeutralRgb })\n })\n }),\n ...(state.measurement === undefined\n ? {}\n : {\n measurement: Object.freeze({\n ...state.measurement,\n weightedMeanPreWbSignal: Object.freeze({\n ...state.measurement.weightedMeanPreWbSignal\n })\n })\n })\n });\n}\n\nfunction stateBase(\n stateId: string,\n source: ResolvedWhiteBalanceState[\"source\"],\n gains: WhiteBalanceChannelGains,\n limitations: readonly string[]\n): Pick<\n ResolvedWhiteBalanceState,\n | \"version\"\n | \"stateId\"\n | \"inputDomain\"\n | \"source\"\n | \"channelGains\"\n | \"locked\"\n | \"trueIlluminantMetadataUsed\"\n | \"sceneIlluminationModified\"\n | \"rawCaptureDestructivelyModified\"\n | \"physicalExposureModified\"\n | \"focusModified\"\n | \"limitations\"\n> {\n return {\n version: WHITE_BALANCE_STATE_VERSION,\n stateId: requireScientificNonEmptyString(stateId, \"stateId\"),\n inputDomain: \"relative-pre-wb-camera-linear-rgb\",\n source,\n channelGains: validateResolvedGains(gains, \"channelGains\"),\n locked: false,\n trueIlluminantMetadataUsed: false,\n sceneIlluminationModified: false,\n rawCaptureDestructivelyModified: false,\n physicalExposureModified: false,\n focusModified: false,\n limitations: [...limitations]\n };\n}\n\n/** Resolves a WB preset defined by the profile. No universal label-to-Kelvin rule is applied. */\nexport function resolvePresetWhiteBalance(\n input: ResolvePresetWhiteBalanceInput\n): ResolvedWhiteBalanceState {\n requireInputKeys(input, \"resolvePresetWhiteBalance\", [\"stateId\", \"profile\", \"presetId\"]);\n const profile = parseWhiteBalanceProfile(input.profile);\n const presetId = requireScientificNonEmptyString(\n input.presetId,\n \"presetId\"\n );\n const preset = profile.presets.find((entry) => entry.presetId === presetId);\n if (preset === undefined) {\n throw new InvalidScientificInputError(\n \"presetId is not declared by the selected white-balance profile.\"\n );\n }\n\n return immutableState({\n ...stateBase(\n input.stateId,\n \"preset\",\n preset.channelGains.value,\n [\n ...profile.limitations,\n ...(preset.limitations ?? [])\n ]\n ),\n sourceProfile: {\n profileId: profile.profileId,\n profileVersion: profile.profileVersion\n },\n presetId\n });\n}\n\n/** Resolves explicit manual camera-linear channel gains. */\nexport function resolveManualWhiteBalance(\n input: ResolveManualWhiteBalanceInput\n): ResolvedWhiteBalanceState {\n requireInputKeys(input, \"resolveManualWhiteBalance\", [\"stateId\", \"channelGains\"]);\n return immutableState(\n stateBase(\n input.stateId,\n \"manual-gains\",\n input.channelGains,\n [\n \"Manual gains are caller-selected WB intent, not a measured physical illuminant.\"\n ]\n )\n );\n}\n\n/**\n * Records independent color-temperature and tint intent.\n *\n * No channel gains are fabricated here; use\n * `resolveColorTemperatureWhiteBalance()` with an explicit camera colour model to\n * resolve gains.\n */\nexport function createColorTemperatureWhiteBalanceIntent(\n input: CreateColorTemperatureWhiteBalanceIntentInput\n): ColorTemperatureWhiteBalanceIntent {\n requireInputKeys(input, \"createColorTemperatureWhiteBalanceIntent\", [\"intentId\", \"colorTemperatureKelvin\", \"tint\"]);\n return Object.freeze({\n version: COLOR_TEMPERATURE_WHITE_BALANCE_INTENT_VERSION,\n intentId: requireScientificNonEmptyString(input.intentId, \"intentId\"),\n colorTemperatureKelvin: requireScientificPositiveFinite(\n input.colorTemperatureKelvin,\n \"colorTemperatureKelvin\"\n ),\n tint: requireScientificFinite(input.tint, \"tint\"),\n channelGainsResolved: false,\n requiresCameraProfileColorimetry: true,\n sceneIlluminationModified: false\n });\n}\n\n/**\n * Resolves a Kelvin + tint WB intent into camera channel gains, for an explicit camera\n * colour model:\n * - white xy = locus(CCT), offset by Duv = tint along the Planckian-locus normal in CIE 1960 uv;\n * - camera neutral n = M_XYZ→camera · XYZ(white, Y = 1);\n * - gains = (n_G/n_R, 1, n_G/n_B).\n * A neutral surface lit by light of exactly that chromaticity then renders with equal channels.\n * The CCT and tint are the white the photographer declares, not a measured scene illuminant.\n * Accuracy is limited by the camera matrix (exact only under the Luther–Ives condition) and by\n * the locus model.\n */\nexport function resolveColorTemperatureWhiteBalance(\n input: ResolveColorTemperatureWhiteBalanceInput\n): ResolvedWhiteBalanceState {\n return colorTemperatureWhiteBalance(input, calculateChromaticityFromCorrelatedColorTemperature);\n}\n/**\n * Internal (not exported from the package): {@link resolveColorTemperatureWhiteBalance} with the white point from\n * `calculatePortableChromaticityFromCorrelatedColorTemperature`, so the gains have the same bits in every JavaScript\n * engine. The display view uses it for a Kelvin white balance; captures keep {@link resolveColorTemperatureWhiteBalance}.\n */\nexport function resolvePortableColorTemperatureWhiteBalance(input: ResolveColorTemperatureWhiteBalanceInput): ResolvedWhiteBalanceState {\n return colorTemperatureWhiteBalance(input, calculatePortableChromaticityFromCorrelatedColorTemperature);\n}\n// The white point is computed by the function passed in (the portable one only from resolvePortableColorTemperatureWhiteBalance), so\n// a bundle that never resolves the portable white balance does not contain the portable functions.\nfunction colorTemperatureWhiteBalance(input: ResolveColorTemperatureWhiteBalanceInput,\n chromaticityFromCct: typeof calculateChromaticityFromCorrelatedColorTemperature): ResolvedWhiteBalanceState {\n requireInputKeys(input, \"resolveColorTemperatureWhiteBalance\", [\"stateId\", \"intent\", \"whiteLocus\", \"tintInterpretation\", \"planckianLocus\", \"camera\"]);\n const intent = input.intent;\n if (\n typeof intent !== \"object\" ||\n intent === null ||\n intent.version !== COLOR_TEMPERATURE_WHITE_BALANCE_INTENT_VERSION\n ) {\n throw new InvalidConfigurationError(\n \"intent must be a color-temperature WB intent of version \" +\n COLOR_TEMPERATURE_WHITE_BALANCE_INTENT_VERSION +\n \".\"\n );\n }\n const intentId = requireScientificNonEmptyString(intent.intentId, \"intent.intentId\");\n const kelvin = requireScientificPositiveFinite(intent.colorTemperatureKelvin, \"intent.colorTemperatureKelvin\");\n const tint = requireScientificFinite(intent.tint, \"intent.tint\");\n if (input.tintInterpretation !== \"duv-cie-1960-uv\") {\n throw new InvalidConfigurationError('tintInterpretation must be \"duv-cie-1960-uv\".');\n }\n const camera = input.camera;\n if (typeof camera !== \"object\" || camera === null) {\n throw new InvalidConfigurationError(\"camera must be an object.\");\n }\n const profileId = requireScientificNonEmptyString(camera.profileId, \"camera.profileId\");\n const profileVersion = requireScientificNonEmptyString(camera.profileVersion, \"camera.profileVersion\");\n const matrix = parseMatrix3x3(camera.xyzToCameraRgb, \"camera.xyzToCameraRgb\");\n const locus: PlanckianLocusModel = input.planckianLocus ?? { kind: \"planck-analytic-cmf\" };\n const white = chromaticityFromCct({\n correlatedColorTemperatureKelvin: kelvin,\n duv: tint,\n whiteLocus: input.whiteLocus,\n locus\n }).value;\n const xyz = xyzOfChromaticity(white);\n const [red, green, blue] = multiplyMatrixVector(matrix, [xyz.x, xyz.y, xyz.z]);\n if (!(red > 0) || !(green > 0) || !(blue > 0)) {\n throw new InvalidScientificInputError(\n \"The camera response to the declared white must be positive in every channel.\"\n );\n }\n return immutableState({\n ...stateBase(\n input.stateId,\n \"color-temperature\",\n { red: green / red, green: 1, blue: green / blue },\n [\n \"Kelvin/tint gains neutralize the declared white through the supplied camera matrix; they do not identify the scene illuminant.\",\n \"Tint is Duv in CIE 1960 uv; accuracy is bounded by the camera matrix and the locus model.\"\n ]\n ),\n sourceProfile: { profileId, profileVersion },\n colorTemperature: {\n intentId,\n colorTemperatureKelvin: kelvin,\n tint,\n whiteLocus: input.whiteLocus,\n tintInterpretation: \"duv-cie-1960-uv\",\n planckianLocusModel: locus.kind,\n adoptedWhiteChromaticity: { x: white.x, y: white.y },\n cameraNeutralRgb: { red, green, blue }\n }\n });\n}\n\nfunction reduceSampleSet(\n sampleSet: PreWhiteBalanceRgbSampleSet,\n clippedPolicy: \"reject-any\" | \"exclude\"\n): {\n imageStateId: string;\n usableSampleCount: number;\n rejectedClippedSampleCount: number;\n weightedMean: {\n red: number;\n green: number;\n blue: number;\n };\n} {\n requireInputObject(sampleSet, \"sampleSet input\");\n if (sampleSet.inputDomain !== \"relative-pre-wb-camera-linear-rgb\") {\n throw new InvalidConfigurationError(\n 'sampleSet.inputDomain must be \"relative-pre-wb-camera-linear-rgb\".'\n );\n }\n const imageStateId = requireScientificNonEmptyString(\n sampleSet.imageStateId,\n \"sampleSet.imageStateId\"\n );\n if (!Array.isArray(sampleSet.samples) || sampleSet.samples.length === 0) {\n throw new InvalidConfigurationError(\n \"sampleSet.samples must be a non-empty array.\"\n );\n }\n\n let weightSum = 0;\n let redSum = 0;\n let greenSum = 0;\n let blueSum = 0;\n let rejectedClippedSampleCount = 0;\n const ids = new Set<string>();\n\n sampleSet.samples.forEach((sample, index) => {\n const path = \"sampleSet.samples[\" + index + \"]\";\n const sampleId = requireScientificNonEmptyString(\n sample.sampleId,\n path + \".sampleId\"\n );\n if (ids.has(sampleId)) {\n throw new InvalidScientificInputError(\n \"sampleSet.samples must not contain duplicate sampleId values.\"\n );\n }\n ids.add(sampleId);\n\n const red = requireScientificNonNegativeFinite(sample.red, path + \".red\");\n const green = requireScientificNonNegativeFinite(\n sample.green,\n path + \".green\"\n );\n const blue = requireScientificNonNegativeFinite(\n sample.blue,\n path + \".blue\"\n );\n const weight = requireScientificPositiveFinite(\n sample.weight,\n path + \".weight\"\n );\n\n if (sample.clipped) {\n rejectedClippedSampleCount += 1;\n if (clippedPolicy === \"reject-any\") {\n throw new InvalidScientificInputError(\n \"Custom white-balance measurement must not contain clipped samples.\"\n );\n }\n return;\n }\n\n weightSum += weight;\n redSum += red * weight;\n greenSum += green * weight;\n blueSum += blue * weight;\n });\n\n if (weightSum <= 0) {\n throw new InvalidScientificInputError(\n \"White-balance estimation requires at least one usable unclipped sample.\"\n );\n }\n\n const weightedMean = {\n red: redSum / weightSum,\n green: greenSum / weightSum,\n blue: blueSum / weightSum\n };\n\n if (\n weightedMean.red <= 0 ||\n weightedMean.green <= 0 ||\n weightedMean.blue <= 0\n ) {\n throw new InvalidScientificInputError(\n \"White-balance estimation requires positive signal in every camera-linear channel.\"\n );\n }\n\n return {\n imageStateId,\n usableSampleCount:\n sampleSet.samples.length - rejectedClippedSampleCount,\n rejectedClippedSampleCount,\n weightedMean\n };\n}\n\nfunction neutralizingGains(\n mean: {\n red: number;\n green: number;\n blue: number;\n }\n): WhiteBalanceChannelGains {\n return {\n red: mean.green / mean.red,\n green: 1,\n blue: mean.green / mean.blue\n };\n}\n\n/**\n * Resolves a user-declared neutral/gray custom-WB measurement.\n *\n * The engine validates and reduces the selected pre-WB sample, but it does not\n * claim the selected object is spectrally neutral in the real scene.\n */\nexport function resolveCustomWhiteBalance(\n input: ResolveCustomWhiteBalanceInput\n): ResolvedWhiteBalanceState {\n requireInputKeys(input, \"resolveCustomWhiteBalance\", [\"stateId\", \"sampleSet\"]);\n const reduced = reduceSampleSet(input.sampleSet, \"reject-any\");\n\n return immutableState({\n ...stateBase(\n input.stateId,\n \"custom-measurement\",\n neutralizingGains(reduced.weightedMean),\n [\n \"Custom WB assumes the caller-selected measurement target is intended to be neutral.\",\n \"Resolved gains are camera-linear relative corrections, not a recovered physical illuminant spectrum.\"\n ]\n ),\n measurement: {\n imageStateId: reduced.imageStateId,\n usableSampleCount: reduced.usableSampleCount,\n rejectedClippedSampleCount: reduced.rejectedClippedSampleCount,\n weightedMeanPreWbSignal: reduced.weightedMean\n }\n });\n}\n\n/**\n * Estimates one global AWB state from declared pre-WB camera-linear samples.\n *\n * It deliberately does not accept metadata about the true illuminant. A\n * grey-world neutralizing estimate is softened by the profile's\n * correctionStrength, so different generic AWB priorities can keep different\n * amounts of colour cast.\n */\nexport function estimateAutoWhiteBalance(\n input: EstimateAutoWhiteBalanceInput\n): ResolvedWhiteBalanceState {\n requireInputKeys(input, \"estimateAutoWhiteBalance\", [\"stateId\", \"profile\", \"policyId\", \"sampleSet\"]);\n const profile = parseWhiteBalanceProfile(input.profile);\n const policyId = requireScientificNonEmptyString(\n input.policyId,\n \"policyId\"\n );\n const policy = profile.awbPolicies.find(\n (entry) => entry.policyId === policyId\n );\n if (policy === undefined) {\n throw new InvalidScientificInputError(\n \"policyId is not declared by the selected white-balance profile.\"\n );\n }\n\n const reduced = reduceSampleSet(input.sampleSet, \"exclude\");\n const neutral = neutralizingGains(reduced.weightedMean);\n const strength = policy.correctionStrength.value;\n const gains = {\n red: Math.pow(neutral.red, strength),\n green: 1,\n blue: Math.pow(neutral.blue, strength)\n };\n\n return immutableState({\n ...stateBase(\n input.stateId,\n \"auto-white-balance\",\n gains,\n [\n ...profile.limitations,\n ...(policy.limitations ?? []),\n \"AWB is a deterministic gray-world-style global estimate over camera-observable pre-WB signal.\",\n \"One global WB may leave local color casts under mixed illumination.\"\n ]\n ),\n sourceProfile: {\n profileId: profile.profileId,\n profileVersion: profile.profileVersion\n },\n awbPolicy: {\n policyId: policy.policyId,\n intent: policy.intent,\n correctionStrength: strength\n },\n measurement: {\n imageStateId: reduced.imageStateId,\n usableSampleCount: reduced.usableSampleCount,\n rejectedClippedSampleCount: reduced.rejectedClippedSampleCount,\n weightedMeanPreWbSignal: reduced.weightedMean\n }\n });\n}\n\n/**\n * Freezes a resolved WB state under a new stable identity.\n *\n * Locking changes neither the scene nor the gains. Later AWB estimates may\n * differ, but this locked state stays the same.\n */\nexport function createLockedWhiteBalanceState(\n input: CreateLockedWhiteBalanceStateInput\n): ResolvedWhiteBalanceState {\n requireInputKeys(input, \"createLockedWhiteBalanceState\", [\"stateId\", \"sourceState\"]);\n const stateId = requireScientificNonEmptyString(input.stateId, \"stateId\");\n const source = input.sourceState;\n\n return immutableState({\n ...source,\n stateId,\n channelGains: validateResolvedGains(\n source.channelGains,\n \"sourceState.channelGains\"\n ),\n locked: true,\n sourceStateId: requireScientificNonEmptyString(\n source.stateId,\n \"sourceState.stateId\"\n ),\n limitations: [...source.limitations]\n });\n}\n\n\nfunction requireNonNegativeSafeInteger(\n value: unknown,\n path: string\n): number {\n if (\n typeof value !== \"number\" ||\n !Number.isSafeInteger(value) ||\n value < 0\n ) {\n throw new InvalidConfigurationError(\n path + \" must be a non-negative safe integer.\"\n );\n }\n return value;\n}\n\nfunction requirePositiveSafeInteger(\n value: unknown,\n path: string\n): number {\n const parsed =\n requireNonNegativeSafeInteger(\n value,\n path\n );\n if (parsed <= 0) {\n throw new InvalidConfigurationError(\n path + \" must be greater than zero.\"\n );\n }\n return parsed;\n}\n\nfunction parseResolvedWhiteBalanceMeasurement(\n value: unknown,\n path: string\n): NonNullable<\n ResolvedWhiteBalanceState[\"measurement\"]\n> {\n const record =\n requireRecord(value, path, [\"weightedMeanPreWbSignal\", \"imageStateId\", \"usableSampleCount\", \"rejectedClippedSampleCount\"]);\n const mean =\n requireRecord(\n record.weightedMeanPreWbSignal,\n path +\n \".weightedMeanPreWbSignal\", [\"red\", \"green\", \"blue\"]\n );\n\n return {\n imageStateId:\n requireNonEmptyString(\n record.imageStateId,\n path + \".imageStateId\"\n ),\n usableSampleCount:\n requirePositiveSafeInteger(\n record.usableSampleCount,\n path +\n \".usableSampleCount\"\n ),\n rejectedClippedSampleCount:\n requireNonNegativeSafeInteger(\n record\n .rejectedClippedSampleCount,\n path +\n \".rejectedClippedSampleCount\"\n ),\n weightedMeanPreWbSignal: {\n red:\n requirePositiveFinite(\n mean.red,\n path +\n \".weightedMeanPreWbSignal.red\"\n ),\n green:\n requirePositiveFinite(\n mean.green,\n path +\n \".weightedMeanPreWbSignal.green\"\n ),\n blue:\n requirePositiveFinite(\n mean.blue,\n path +\n \".weightedMeanPreWbSignal.blue\"\n )\n }\n };\n}\n\nfunction parseResolvedColorTemperature(\n value: unknown,\n path: string\n): ResolvedColorTemperatureWhiteBalance {\n const record = requireRecord(value, path, [\"whiteLocus\", \"tintInterpretation\", \"planckianLocusModel\", \"adoptedWhiteChromaticity\", \"intentId\", \"colorTemperatureKelvin\", \"tint\", \"cameraNeutralRgb\"]);\n if (record.whiteLocus !== \"planckian\" && record.whiteLocus !== \"cie-daylight\") {\n throw new InvalidConfigurationError(path + \".whiteLocus is invalid.\");\n }\n if (record.tintInterpretation !== \"duv-cie-1960-uv\") {\n throw new InvalidConfigurationError(path + \".tintInterpretation is invalid.\");\n }\n if (\n record.planckianLocusModel !== \"planck-analytic-cmf\" &&\n record.planckianLocusModel !== \"planck-integration\"\n ) {\n throw new InvalidConfigurationError(path + \".planckianLocusModel is invalid.\");\n }\n const white = requireRecord(record.adoptedWhiteChromaticity, path + \".adoptedWhiteChromaticity\", [\"x\", \"y\"]);\n return {\n intentId: requireNonEmptyString(record.intentId, path + \".intentId\"),\n colorTemperatureKelvin: requirePositiveFinite(record.colorTemperatureKelvin, path + \".colorTemperatureKelvin\"),\n tint: requireFinite(record.tint, path + \".tint\"),\n whiteLocus: record.whiteLocus,\n tintInterpretation: \"duv-cie-1960-uv\",\n planckianLocusModel: record.planckianLocusModel,\n adoptedWhiteChromaticity: {\n x: requirePositiveFinite(white.x, path + \".adoptedWhiteChromaticity.x\"),\n y: requirePositiveFinite(white.y, path + \".adoptedWhiteChromaticity.y\")\n },\n cameraNeutralRgb: parseChannelGains(record.cameraNeutralRgb, path + \".cameraNeutralRgb\")\n };\n}\n\n/**\n * Parses a committed, resolved white-balance state from untrusted JSON,\n * without estimating WB again.\n *\n * This is deliberately a state parser, not an AWB estimator. It keeps the\n * resolved gains, policy and measurement identity that a capture committed\n * earlier.\n */\nexport function parseResolvedWhiteBalanceState(\n value: unknown\n): ResolvedWhiteBalanceState {\n const record =\n requireRecord(\n value,\n \"resolvedWhiteBalanceState\", [\"version\", \"inputDomain\", \"source\", \"locked\", \"sourceProfile\", \"awbPolicy\", \"measurement\", \"colorTemperature\", \"presetId\", \"sourceStateId\", \"stateId\", \"channelGains\", \"limitations\", \"trueIlluminantMetadataUsed\", \"sceneIlluminationModified\", \"rawCaptureDestructivelyModified\", \"physicalExposureModified\", \"focusModified\"]\n );\n\n if (\n record.version !==\n WHITE_BALANCE_STATE_VERSION\n ) {\n throw new InvalidConfigurationError(\n 'resolvedWhiteBalanceState.version must be \"' +\n WHITE_BALANCE_STATE_VERSION +\n '\".'\n );\n }\n if (\n record.inputDomain !==\n \"relative-pre-wb-camera-linear-rgb\"\n ) {\n throw new InvalidConfigurationError(\n 'resolvedWhiteBalanceState.inputDomain must be \"relative-pre-wb-camera-linear-rgb\".'\n );\n }\n if (\n record.source !== \"preset\" &&\n record.source !==\n \"manual-gains\" &&\n record.source !==\n \"custom-measurement\" &&\n record.source !==\n \"auto-white-balance\" &&\n record.source !==\n \"color-temperature\"\n ) {\n throw new InvalidConfigurationError(\n \"resolvedWhiteBalanceState.source is invalid.\"\n );\n }\n if (\n typeof record.locked !==\n \"boolean\"\n ) {\n throw new InvalidConfigurationError(\n \"resolvedWhiteBalanceState.locked must be boolean.\"\n );\n }\n\n for (const key of [\n \"trueIlluminantMetadataUsed\",\n \"sceneIlluminationModified\",\n \"rawCaptureDestructivelyModified\",\n \"physicalExposureModified\",\n \"focusModified\"\n ] as const) {\n if (record[key] !== false) {\n throw new InvalidConfigurationError(\n \"resolvedWhiteBalanceState.\" +\n key +\n \" must remain false.\"\n );\n }\n }\n\n const sourceProfile =\n record.sourceProfile === undefined\n ? undefined\n : ((): NonNullable<ResolvedWhiteBalanceState[\"sourceProfile\"]> => {\n const profile =\n requireRecord(\n record.sourceProfile,\n \"resolvedWhiteBalanceState.sourceProfile\", [\"profileId\", \"profileVersion\"]\n );\n return {\n profileId:\n requireNonEmptyString(\n profile.profileId,\n \"resolvedWhiteBalanceState.sourceProfile.profileId\"\n ),\n profileVersion:\n requireNonEmptyString(\n profile.profileVersion,\n \"resolvedWhiteBalanceState.sourceProfile.profileVersion\"\n )\n };\n })();\n\n const awbPolicy =\n record.awbPolicy === undefined\n ? undefined\n : ((): NonNullable<ResolvedWhiteBalanceState[\"awbPolicy\"]> => {\n const policy =\n requireRecord(\n record.awbPolicy,\n \"resolvedWhiteBalanceState.awbPolicy\", [\"policyId\", \"intent\", \"correctionStrength\"]\n );\n return {\n policyId:\n requireNonEmptyString(\n policy.policyId,\n \"resolvedWhiteBalanceState.awbPolicy.policyId\"\n ),\n intent:\n parseAwbIntent(\n policy.intent,\n \"resolvedWhiteBalanceState.awbPolicy.intent\"\n ),\n correctionStrength:\n requireFraction(\n policy.correctionStrength,\n \"resolvedWhiteBalanceState.awbPolicy.correctionStrength\"\n )\n };\n })();\n\n const measurement =\n record.measurement === undefined\n ? undefined\n : parseResolvedWhiteBalanceMeasurement(\n record.measurement,\n \"resolvedWhiteBalanceState.measurement\"\n );\n\n const colorTemperature =\n record.colorTemperature === undefined\n ? undefined\n : parseResolvedColorTemperature(\n record.colorTemperature,\n \"resolvedWhiteBalanceState.colorTemperature\"\n );\n\n const presetId =\n record.presetId === undefined\n ? undefined\n : requireNonEmptyString(\n record.presetId,\n \"resolvedWhiteBalanceState.presetId\"\n );\n\n const sourceStateId =\n record.sourceStateId ===\n undefined\n ? undefined\n : requireNonEmptyString(\n record.sourceStateId,\n \"resolvedWhiteBalanceState.sourceStateId\"\n );\n\n if (\n record.source === \"preset\" &&\n (sourceProfile === undefined ||\n presetId === undefined)\n ) {\n throw new InvalidConfigurationError(\n \"A preset WB state requires sourceProfile and presetId.\"\n );\n }\n\n if (\n record.source ===\n \"custom-measurement\" &&\n measurement === undefined\n ) {\n throw new InvalidConfigurationError(\n \"A custom-measurement WB state requires measurement identity.\"\n );\n }\n\n if (\n record.source ===\n \"auto-white-balance\" &&\n (sourceProfile === undefined ||\n awbPolicy === undefined ||\n measurement === undefined)\n ) {\n throw new InvalidConfigurationError(\n \"An auto-white-balance state requires sourceProfile, awbPolicy, and measurement identity.\"\n );\n }\n\n if (\n (record.source === \"color-temperature\") !==\n (colorTemperature !== undefined) ||\n (record.source === \"color-temperature\" &&\n sourceProfile === undefined)\n ) {\n throw new InvalidConfigurationError(\n \"A color-temperature WB state requires sourceProfile and colorTemperature; other sources must not declare colorTemperature.\"\n );\n }\n\n if (\n record.locked &&\n sourceStateId === undefined\n ) {\n throw new InvalidConfigurationError(\n \"A locked WB state requires sourceStateId.\"\n );\n }\n\n if (\n !record.locked &&\n sourceStateId !== undefined\n ) {\n throw new InvalidConfigurationError(\n \"An unlocked WB state must not declare sourceStateId.\"\n );\n }\n\n return immutableState({\n version:\n WHITE_BALANCE_STATE_VERSION,\n stateId:\n requireNonEmptyString(\n record.stateId,\n \"resolvedWhiteBalanceState.stateId\"\n ),\n inputDomain:\n \"relative-pre-wb-camera-linear-rgb\",\n source: record.source,\n channelGains:\n parseChannelGains(\n record.channelGains,\n \"resolvedWhiteBalanceState.channelGains\"\n ),\n locked: record.locked,\n ...(sourceProfile === undefined\n ? {}\n : {\n sourceProfile\n }),\n ...(presetId === undefined\n ? {}\n : {\n presetId\n }),\n ...(awbPolicy === undefined\n ? {}\n : {\n awbPolicy\n }),\n ...(measurement === undefined\n ? {}\n : {\n measurement\n }),\n ...(colorTemperature === undefined\n ? {}\n : {\n colorTemperature\n }),\n ...(sourceStateId === undefined\n ? {}\n : {\n sourceStateId\n }),\n trueIlluminantMetadataUsed:\n false,\n sceneIlluminationModified:\n false,\n rawCaptureDestructivelyModified:\n false,\n physicalExposureModified:\n false,\n focusModified: false,\n limitations:\n parseLimitations(\n record.limitations,\n \"resolvedWhiteBalanceState.limitations\"\n )\n });\n}\n"]}
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
/** Marks an engine-built evaluator and returns it. */
|
|
2
|
+
export declare function markInternalSceneRadianceEvaluator<T extends object>(evaluator: T): T;
|
|
3
|
+
/** True only for an evaluator marked by the engine. */
|
|
4
|
+
export declare function isInternalSceneRadianceEvaluator(evaluator: unknown): boolean;
|
|
5
|
+
/** True when the value and everything reachable from it are frozen (primitives count as frozen). */
|
|
6
|
+
export declare function isDeeplyFrozen(value: unknown): boolean;
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
// SPDX-License-Identifier: Apache-2.0
|
|
2
|
+
/**
|
|
3
|
+
* Internal (not exported from the package): marks the scene-radiance evaluators that the engine itself builds for
|
|
4
|
+
* `simulateCapture` chart scenes (2.6). Their results are object literals with the schema's exact keys, constant
|
|
5
|
+
* schema/quantity/unit/status fields, the request's identifiers and deep-frozen engine-owned uncertainty, evidence
|
|
6
|
+
* and limitations; the native environment then skips re-parsing those fixed parts (see
|
|
7
|
+
* `parseSceneRadianceEvaluationResultWithValidatedRecords`). Evaluators from callers are never marked and keep the
|
|
8
|
+
* full validation. The mark is on the function object, which only the engine holds.
|
|
9
|
+
*/
|
|
10
|
+
const INTERNAL_EVALUATORS = new WeakSet();
|
|
11
|
+
/** Marks an engine-built evaluator and returns it. */
|
|
12
|
+
export function markInternalSceneRadianceEvaluator(evaluator) {
|
|
13
|
+
INTERNAL_EVALUATORS.add(evaluator);
|
|
14
|
+
return evaluator;
|
|
15
|
+
}
|
|
16
|
+
/** True only for an evaluator marked by the engine. */
|
|
17
|
+
export function isInternalSceneRadianceEvaluator(evaluator) {
|
|
18
|
+
return typeof evaluator === "function" && INTERNAL_EVALUATORS.has(evaluator);
|
|
19
|
+
}
|
|
20
|
+
/** True when the value and everything reachable from it are frozen (primitives count as frozen). */
|
|
21
|
+
export function isDeeplyFrozen(value) {
|
|
22
|
+
if (value === null || typeof value !== "object")
|
|
23
|
+
return typeof value !== "function";
|
|
24
|
+
if (!Object.isFrozen(value))
|
|
25
|
+
return false;
|
|
26
|
+
for (const key of Reflect.ownKeys(value)) {
|
|
27
|
+
const descriptor = Object.getOwnPropertyDescriptor(value, key);
|
|
28
|
+
if (descriptor.get !== undefined || descriptor.set !== undefined || !isDeeplyFrozen(descriptor.value))
|
|
29
|
+
return false;
|
|
30
|
+
}
|
|
31
|
+
return true;
|
|
32
|
+
}
|
|
33
|
+
//# sourceMappingURL=internal-radiance-evaluator.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"internal-radiance-evaluator.js","sourceRoot":"","sources":["../../src/core/internal-radiance-evaluator.ts"],"names":[],"mappings":"AAAA,sCAAsC;AAEtC;;;;;;;GAOG;AACH,MAAM,mBAAmB,GAAG,IAAI,OAAO,EAAU,CAAC;AAElD,sDAAsD;AACtD,MAAM,UAAU,kCAAkC,CAAmB,SAAY;IAC/E,mBAAmB,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC;IACnC,OAAO,SAAS,CAAC;AACnB,CAAC;AAED,uDAAuD;AACvD,MAAM,UAAU,gCAAgC,CAAC,SAAkB;IACjE,OAAO,OAAO,SAAS,KAAK,UAAU,IAAI,mBAAmB,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC;AAC/E,CAAC;AAED,oGAAoG;AACpG,MAAM,UAAU,cAAc,CAAC,KAAc;IAC3C,IAAI,KAAK,KAAK,IAAI,IAAI,OAAO,KAAK,KAAK,QAAQ;QAAE,OAAO,OAAO,KAAK,KAAK,UAAU,CAAC;IACpF,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC;QAAE,OAAO,KAAK,CAAC;IAC1C,KAAK,MAAM,GAAG,IAAI,OAAO,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC;QACzC,MAAM,UAAU,GAAG,MAAM,CAAC,wBAAwB,CAAC,KAAK,EAAE,GAAG,CAAE,CAAC;QAChE,IAAI,UAAU,CAAC,GAAG,KAAK,SAAS,IAAI,UAAU,CAAC,GAAG,KAAK,SAAS,IAAI,CAAC,cAAc,CAAC,UAAU,CAAC,KAAK,CAAC;YAAE,OAAO,KAAK,CAAC;IACtH,CAAC;IACD,OAAO,IAAI,CAAC;AACd,CAAC","sourcesContent":["// SPDX-License-Identifier: Apache-2.0\n\n/**\n * Internal (not exported from the package): marks the scene-radiance evaluators that the engine itself builds for\n * `simulateCapture` chart scenes (2.6). Their results are object literals with the schema's exact keys, constant\n * schema/quantity/unit/status fields, the request's identifiers and deep-frozen engine-owned uncertainty, evidence\n * and limitations; the native environment then skips re-parsing those fixed parts (see\n * `parseSceneRadianceEvaluationResultWithValidatedRecords`). Evaluators from callers are never marked and keep the\n * full validation. The mark is on the function object, which only the engine holds.\n */\nconst INTERNAL_EVALUATORS = new WeakSet<object>();\n\n/** Marks an engine-built evaluator and returns it. */\nexport function markInternalSceneRadianceEvaluator<T extends object>(evaluator: T): T {\n INTERNAL_EVALUATORS.add(evaluator);\n return evaluator;\n}\n\n/** True only for an evaluator marked by the engine. */\nexport function isInternalSceneRadianceEvaluator(evaluator: unknown): boolean {\n return typeof evaluator === \"function\" && INTERNAL_EVALUATORS.has(evaluator);\n}\n\n/** True when the value and everything reachable from it are frozen (primitives count as frozen). */\nexport function isDeeplyFrozen(value: unknown): boolean {\n if (value === null || typeof value !== \"object\") return typeof value !== \"function\";\n if (!Object.isFrozen(value)) return false;\n for (const key of Reflect.ownKeys(value)) {\n const descriptor = Object.getOwnPropertyDescriptor(value, key)!;\n if (descriptor.get !== undefined || descriptor.set !== undefined || !isDeeplyFrozen(descriptor.value)) return false;\n }\n return true;\n}\n"]}
|
|
@@ -13,3 +13,36 @@ export declare function portableHypot(...values: readonly number[]): number;
|
|
|
13
13
|
* that another engine or an earlier release computed with an implementation-approximated function.
|
|
14
14
|
*/
|
|
15
15
|
export declare function equalWithinUlps(a: number, b: number, maximumUlps: number): boolean;
|
|
16
|
+
/** log2 x, bit-identical in every JavaScript engine (within 1 ulp). 0 → −∞; negative or NaN → NaN; +∞ → +∞. */
|
|
17
|
+
export declare function portableLog2(x: number): number;
|
|
18
|
+
/**
|
|
19
|
+
* Natural logarithm, bit-identical in every JavaScript engine (within 1 ulp). 0 → −∞; negative or NaN → NaN; +∞ → +∞.
|
|
20
|
+
* x = m·2^e, m in [√½, √2]; ln x = e·ln 2 + ln F (table, F = k/128, k = round(128·m)) + 2·atanh(s), s = (m − F)/(m + F),
|
|
21
|
+
* with s as a double-double and the three terms added with TwoSum.
|
|
22
|
+
*/
|
|
23
|
+
export declare function portableLog(x: number): number;
|
|
24
|
+
/** 2^x, bit-identical in every JavaScript engine (within 1 ulp). */
|
|
25
|
+
export declare function portableExp2(x: number): number;
|
|
26
|
+
/** e^x, bit-identical in every JavaScript engine (within 1 ulp). */
|
|
27
|
+
export declare function portableExp(x: number): number;
|
|
28
|
+
/**
|
|
29
|
+
* e^x − 1, bit-identical in every JavaScript engine (within 2 ulps): the Taylor series to degree 20 for |x| < 1
|
|
30
|
+
* (truncation below 2^-60 relative), else portableExp(x) − 1.
|
|
31
|
+
*/
|
|
32
|
+
export declare function portableExpm1(x: number): number;
|
|
33
|
+
/**
|
|
34
|
+
* x^y for x ≥ 0 and finite y, bit-identical in every JavaScript engine (within 1 ulp for |y| ≤ 4). x = 0 gives 0 for
|
|
35
|
+
* y > 0, 1 for y = 0 and +∞ for y < 0; negative x or a non-finite argument gives NaN (the callers never pass them).
|
|
36
|
+
*/
|
|
37
|
+
export declare function portablePow(x: number, y: number): number;
|
|
38
|
+
/**
|
|
39
|
+
* Cube root, bit-identical in every JavaScript engine (within 1 ulp; exact for ±0, ±∞ and cubes of powers of two).
|
|
40
|
+
* |x| = m·2^(3q + r) with m in [1, 2) and r in {0, 1, 2}, w = m·2^r: a cubic fit to ∛m (within 1.7·10⁻⁴) times ∛(2^r),
|
|
41
|
+
* one Halley step y ← y(y³ + 2w)/(2y³ + w) (cubic convergence: below 10⁻¹¹), then one Newton step y + (w − y³)/(3y²)
|
|
42
|
+
* with w − y³ formed exactly (TwoProduct), which leaves only the final rounding and errors near 10⁻²².
|
|
43
|
+
*/
|
|
44
|
+
export declare function portableCbrt(x: number): number;
|
|
45
|
+
/** cos(2πu) for finite u (u in turns), bit-identical in every JavaScript engine (within 2 ulps). */
|
|
46
|
+
export declare function portableCosTwoPi(u: number): number;
|
|
47
|
+
/** sin(2πu) for finite u (u in turns), bit-identical in every JavaScript engine (within 2 ulps). */
|
|
48
|
+
export declare function portableSinTwoPi(u: number): number;
|