import { Arr, Fun, Merger } from '@ephox/katamari'; import type { AlloySpec } from '../api/component/SpecTypes'; import type { CompositeSketchDetail, CompositeSketchSpec } from '../api/ui/Sketcher'; import * as UiSubstitutes from '../spec/UiSubstitutes'; import type { Substitutions } from './AlloyParts'; import * as PartType from './PartType'; const combine = (detail: D, data: PartType.BasePartDetail, partSpec: S, partValidated?: Record): S & { uid: string } => // Extremely confusing names and types :( Merger.deepMerge( data.defaults(detail, partSpec, partValidated), partSpec, { uid: detail.partUids[data.name] }, data.overrides(detail, partSpec, partValidated) ); const subs = (owner: string, detail: D, parts: PartType.PartTypeAdt[]): Substitutions => { const internals: Record = { }; const externals: Record AlloySpec> = { }; Arr.each(parts, (part) => { part.fold( // Internal (data) => { internals[data.pname] = UiSubstitutes.single(true, (detail, partSpec, partValidated) => data.factory.sketch( combine(detail, data, partSpec, partValidated) )); }, // External (data) => { const partSpec = detail.parts[data.name]; externals[data.name] = Fun.constant( data.factory.sketch( combine(detail, data, partSpec[PartType.original()]), partSpec ) // This is missing partValidated ); // no placeholders }, // Optional (data) => { internals[data.pname] = UiSubstitutes.single(false, (detail, partSpec, partValidated) => data.factory.sketch( combine(detail, data, partSpec, partValidated) )); }, // Group (data) => { internals[data.pname] = UiSubstitutes.multiple(true, (detail, _partSpec, _partValidated) => { const units: Array> = (detail as any)[data.name]; return Arr.map(units, (u) => // Group multiples do not take the uid because there is more than one. data.factory.sketch( Merger.deepMerge( data.defaults(detail, u, _partValidated), u, data.overrides(detail, u) ) ) ); }); } ); }); return { internals: Fun.constant(internals), externals: Fun.constant(externals) }; }; export { subs };