@yahoo/uds-create-config 5.25.1 → 5.26.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/dist/configs/system.js +2 -0
- package/dist/entities/native/NativeToken.js +4 -1
- package/dist/entities/system/Component.d.ts +35 -2
- package/dist/entities/system/Component.js +224 -9
- package/dist/entities/system/Settings.js +1 -1
- package/dist/entities/system/StyleProperty.js +1 -1
- package/dist/entities/system/component-module.d.ts +17 -1
- package/dist/entities/system/component-module.js +54 -2
- package/dist/entities/system/defineComponent.d.ts +53 -13
- package/dist/entities/system/defineComponent.js +1 -0
- package/dist/entities/system/forward-route-invariants.js +1 -1
- package/dist/entities/system/icon-domain-invariants.js +1 -1
- package/dist/entities/system/linked-token-values.js +9 -2
- package/dist/entities/system/root-layer-invariants.js +1 -1
- package/dist/entities/system/token-values.js +1 -1
- package/dist/framework/Config.d.ts +1 -1
- package/dist/framework/Config.js +1 -1
- package/dist/framework/class-names.d.ts +27 -1
- package/dist/framework/class-names.js +56 -3
- package/dist/framework/component-states.d.ts +40 -0
- package/dist/framework/component-states.js +53 -0
- package/dist/framework/interaction-conditions.d.ts +48 -0
- package/dist/framework/interaction-conditions.js +104 -0
- package/dist/framework/layer-styles.d.ts +5 -1
- package/dist/framework/layer-styles.js +18 -4
- package/dist/framework/projections.js +44 -2
- package/dist/framework/render-spec.js +14 -4
- package/dist/framework/schema-version.d.ts +1 -1
- package/dist/framework/schema-version.js +5 -5
- package/dist/framework/validate-spec.js +14 -0
- package/dist/index.d.ts +5 -3
- package/dist/index.js +6 -4
- package/dist/migrations/20261013154037_component_states.d.ts +19 -0
- package/dist/migrations/20261013154037_component_states.js +74 -0
- package/dist/renderer/componentEntry.d.ts +7 -1
- package/dist/renderer/componentEntry.js +30 -1
- package/dist/renderer/forced-stamp.d.ts +26 -0
- package/dist/renderer/forced-stamp.js +50 -0
- package/dist/renderer/index.d.ts +3 -1
- package/dist/renderer/index.js +3 -1
- package/dist/renderer/use-forced-stamp.d.ts +11 -0
- package/dist/renderer/use-forced-stamp.js +50 -0
- package/dist/spec/specToJsx.d.ts +6 -0
- package/dist/spec/specToJsx.js +5 -0
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +2 -2
|
@@ -1,6 +1,9 @@
|
|
|
1
|
+
import { UDS_FORCE_STATES } from "../framework/component-states.js";
|
|
2
|
+
import { forcedModifierAttributes } from "../framework/class-names.js";
|
|
1
3
|
import { registerComputed } from "./computed.js";
|
|
2
4
|
import { RendererErrorBoundary } from "./RendererErrorBoundary.js";
|
|
3
5
|
import { specContent } from "./spec-content.js";
|
|
6
|
+
import { useForcedModifierStamp } from "./use-forced-stamp.js";
|
|
4
7
|
import React from "react";
|
|
5
8
|
//#region src/renderer/componentEntry.tsx
|
|
6
9
|
/**
|
|
@@ -33,11 +36,12 @@ function definedOnly(options) {
|
|
|
33
36
|
* data, so it never imports this renderer: whoever assembles a registry makes the entry.
|
|
34
37
|
*/
|
|
35
38
|
function makeComponentEntry(options) {
|
|
36
|
-
const { component: Comp, childless, name, computed } = {
|
|
39
|
+
const { component: Comp, childless, name, computed, states } = {
|
|
37
40
|
...options.component.__udsEntry,
|
|
38
41
|
...definedOnly(options)
|
|
39
42
|
};
|
|
40
43
|
const label = name ?? Comp.displayName ?? Comp.name ?? "component";
|
|
44
|
+
const componentPath = name?.startsWith("component:") ? name.slice(10) : label;
|
|
41
45
|
if (computed) registerComputed(computed);
|
|
42
46
|
return function ComponentEntry({ props: elementProps, children, slots }) {
|
|
43
47
|
let props = elementProps ?? {};
|
|
@@ -51,6 +55,18 @@ function makeComponentEntry(options) {
|
|
|
51
55
|
props = filled;
|
|
52
56
|
}
|
|
53
57
|
const { children: propChildren, ...rest } = props;
|
|
58
|
+
if (states?.some((state) => state in rest)) {
|
|
59
|
+
const forced = { ...rest["__udsForceStates"] ?? {} };
|
|
60
|
+
for (const state of states) {
|
|
61
|
+
if (!(state in rest)) continue;
|
|
62
|
+
forced[state] = rest[state];
|
|
63
|
+
delete rest[state];
|
|
64
|
+
}
|
|
65
|
+
rest[UDS_FORCE_STATES] = forced;
|
|
66
|
+
}
|
|
67
|
+
let forcedAttrs = {};
|
|
68
|
+
const pins = rest[UDS_FORCE_STATES];
|
|
69
|
+
if (pins && typeof pins === "object") forcedAttrs = forcedModifierAttributes(pins);
|
|
54
70
|
let rendered;
|
|
55
71
|
if (childless) rendered = React.createElement(Comp, rest);
|
|
56
72
|
else {
|
|
@@ -60,6 +76,10 @@ function makeComponentEntry(options) {
|
|
|
60
76
|
});
|
|
61
77
|
rendered = finalChildren !== void 0 && finalChildren !== null ? React.createElement(Comp, rest, finalChildren) : React.createElement(Comp, rest);
|
|
62
78
|
}
|
|
79
|
+
if (Object.keys(forcedAttrs).length > 0) rendered = React.createElement(ForcedHost, {
|
|
80
|
+
component: componentPath,
|
|
81
|
+
attributes: forcedAttrs
|
|
82
|
+
}, rendered);
|
|
63
83
|
return React.createElement(RendererErrorBoundary, {
|
|
64
84
|
name: label,
|
|
65
85
|
resetKey: elementProps
|
|
@@ -84,5 +104,14 @@ function entryRenderer(entry) {
|
|
|
84
104
|
});
|
|
85
105
|
};
|
|
86
106
|
}
|
|
107
|
+
/** A layout-neutral wrapper that marks the forced component's own elements under it. */
|
|
108
|
+
function ForcedHost({ component, attributes, children }) {
|
|
109
|
+
const host = React.useRef(null);
|
|
110
|
+
useForcedModifierStamp(host, component, attributes);
|
|
111
|
+
return React.createElement("div", {
|
|
112
|
+
ref: host,
|
|
113
|
+
style: { display: "contents" }
|
|
114
|
+
}, children);
|
|
115
|
+
}
|
|
87
116
|
//#endregion
|
|
88
117
|
export { entryRenderer, makeComponentEntry, slotFillValue };
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
//#region src/renderer/forced-stamp.d.ts
|
|
2
|
+
/**
|
|
3
|
+
* Mark a forced component's own elements with its force attributes, inside `container`.
|
|
4
|
+
*
|
|
5
|
+
* The design sheet's force twin matches an element that carries the attribute itself, so a state is
|
|
6
|
+
* forced exactly where this puts it: the component's root, and its other elements tagged with its
|
|
7
|
+
* own `data-uds-component` — except the root of a component nested in it. That root is tagged with
|
|
8
|
+
* the parent's markers (the props it was given land over its own), but it is the nearest tagged
|
|
9
|
+
* ancestor of the nested component's own non-root parts, which is how it's told apart. A nested
|
|
10
|
+
* IconButton then keeps its own hover and focus ring, as the browser would. Returns the undo.
|
|
11
|
+
*
|
|
12
|
+
* Each attribute's value lists the components forced on the element, and this adds `component` to
|
|
13
|
+
* it: the twin matches only its own component's name (`forceStateSelector`), so a component
|
|
14
|
+
* whose root is another's instance — one element for both — doesn't light the inner one's state.
|
|
15
|
+
*/
|
|
16
|
+
declare function stampForcedModifiers({
|
|
17
|
+
container,
|
|
18
|
+
component,
|
|
19
|
+
attributes
|
|
20
|
+
}: {
|
|
21
|
+
container: Element;
|
|
22
|
+
component: string;
|
|
23
|
+
attributes: Readonly<Record<string, string>>;
|
|
24
|
+
}): () => void;
|
|
25
|
+
//#endregion
|
|
26
|
+
export { stampForcedModifiers };
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
//#region src/renderer/forced-stamp.ts
|
|
2
|
+
/**
|
|
3
|
+
* Mark a forced component's own elements with its force attributes, inside `container`.
|
|
4
|
+
*
|
|
5
|
+
* The design sheet's force twin matches an element that carries the attribute itself, so a state is
|
|
6
|
+
* forced exactly where this puts it: the component's root, and its other elements tagged with its
|
|
7
|
+
* own `data-uds-component` — except the root of a component nested in it. That root is tagged with
|
|
8
|
+
* the parent's markers (the props it was given land over its own), but it is the nearest tagged
|
|
9
|
+
* ancestor of the nested component's own non-root parts, which is how it's told apart. A nested
|
|
10
|
+
* IconButton then keeps its own hover and focus ring, as the browser would. Returns the undo.
|
|
11
|
+
*
|
|
12
|
+
* Each attribute's value lists the components forced on the element, and this adds `component` to
|
|
13
|
+
* it: the twin matches only its own component's name (`forceStateSelector`), so a component
|
|
14
|
+
* whose root is another's instance — one element for both — doesn't light the inner one's state.
|
|
15
|
+
*/
|
|
16
|
+
function stampForcedModifiers({ container, component, attributes }) {
|
|
17
|
+
const names = Object.keys(attributes);
|
|
18
|
+
if (names.length === 0) return () => {};
|
|
19
|
+
const tagged = [...container.querySelectorAll("[data-uds-component]")];
|
|
20
|
+
const nestedRoots = /* @__PURE__ */ new Set();
|
|
21
|
+
for (const element of tagged) {
|
|
22
|
+
if (element.getAttribute("data-uds-component") === component) continue;
|
|
23
|
+
if (element.getAttribute("data-uds-layer") === "root") continue;
|
|
24
|
+
const owner = element.parentElement?.closest("[data-uds-component]");
|
|
25
|
+
if (owner && owner.getAttribute("data-uds-component") === component) nestedRoots.add(owner);
|
|
26
|
+
}
|
|
27
|
+
const stamped = [];
|
|
28
|
+
for (const element of tagged) {
|
|
29
|
+
if (element.getAttribute("data-uds-component") !== component) continue;
|
|
30
|
+
if (!(element.getAttribute("data-uds-layer") === "root") && nestedRoots.has(element)) continue;
|
|
31
|
+
for (const name of names) {
|
|
32
|
+
const owners = ownersOf(element, name);
|
|
33
|
+
if (!owners.includes(component)) element.setAttribute(name, [...owners, component].join(" "));
|
|
34
|
+
}
|
|
35
|
+
stamped.push(element);
|
|
36
|
+
}
|
|
37
|
+
return () => {
|
|
38
|
+
for (const element of stamped) for (const name of names) {
|
|
39
|
+
const owners = ownersOf(element, name).filter((owner) => owner !== component);
|
|
40
|
+
if (owners.length > 0) element.setAttribute(name, owners.join(" "));
|
|
41
|
+
else element.removeAttribute(name);
|
|
42
|
+
}
|
|
43
|
+
};
|
|
44
|
+
}
|
|
45
|
+
/** The components a force attribute already names on an element. */
|
|
46
|
+
function ownersOf(element, name) {
|
|
47
|
+
return (element.getAttribute(name) ?? "").split(/\s+/).filter(Boolean);
|
|
48
|
+
}
|
|
49
|
+
//#endregion
|
|
50
|
+
export { stampForcedModifiers };
|
package/dist/renderer/index.d.ts
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { ComponentEntry, ComponentEntryFacts, MakeComponentEntryOptions, entryRenderer, makeComponentEntry, slotFillValue } from "./componentEntry.js";
|
|
2
2
|
import { computedFunctions, registerComputed, withComputedFunctions } from "./computed.js";
|
|
3
|
+
import { stampForcedModifiers } from "./forced-stamp.js";
|
|
3
4
|
import { GlyphEntriesResult, GlyphMembers, glyphRegistryEntries } from "./glyphEntries.js";
|
|
4
5
|
import { FragmentRenderer } from "./primitives/FragmentRenderer.js";
|
|
5
6
|
import { SlotRenderer } from "./primitives/SlotRenderer.js";
|
|
@@ -11,7 +12,8 @@ import { GlyphPropMap, wrapGlyphProps } from "./wrappers/glyph-props.js";
|
|
|
11
12
|
import { VERBATIM_ATTRIBUTES, aliasHtmlTypes } from "./wrappers/html-aliases.js";
|
|
12
13
|
import { RegistryDescriptor, wrapRegistry } from "./wrapRegistry.js";
|
|
13
14
|
import { UdsRenderer, UdsRendererProps } from "./UdsRenderer.js";
|
|
15
|
+
import { useForcedModifierStamp } from "./use-forced-stamp.js";
|
|
14
16
|
import { wrapEventBridge } from "./wrappers/event-bridge.js";
|
|
15
17
|
import { wrapNormalizeHex } from "./wrappers/hex-normalize.js";
|
|
16
18
|
import { wrapInlineStyleProps } from "./wrappers/inline-styles.js";
|
|
17
|
-
export { type ComponentEntry, type ComponentEntryFacts, FragmentRenderer, type Glyph, type GlyphEntriesResult, type GlyphLibrary, type GlyphMembers, type GlyphPropMap, type MakeComponentEntryOptions, REVEALED_LAYER_ATTR, type RegistryDescriptor, RendererErrorBoundary, type ResolvedGlyph, RuntimeComponentFailureContext, type RuntimeComponentFailureReporter, RuntimeComponentRebuildContext, type RuntimeComponentRebuildReporter, type RuntimeComponentScope, type RuntimeComponentStatus, type RuntimeComponentStore, RuntimeComponentStoreContext, SlotRenderer, UdsRenderer, type UdsRendererProps, VERBATIM_ATTRIBUTES, aliasHtmlTypes, computedFunctions, entryRenderer, glyphRegistryEntries, installRuntimeComponentStore, makeComponentEntry, registerComputed, resolveGlyph, runtimeComponent, slotFillValue, specContent, withComputedFunctions, wrapEventBridge, wrapGlyphProps, wrapInlineStyleProps, wrapNormalizeHex, wrapRegistry };
|
|
19
|
+
export { type ComponentEntry, type ComponentEntryFacts, FragmentRenderer, type Glyph, type GlyphEntriesResult, type GlyphLibrary, type GlyphMembers, type GlyphPropMap, type MakeComponentEntryOptions, REVEALED_LAYER_ATTR, type RegistryDescriptor, RendererErrorBoundary, type ResolvedGlyph, RuntimeComponentFailureContext, type RuntimeComponentFailureReporter, RuntimeComponentRebuildContext, type RuntimeComponentRebuildReporter, type RuntimeComponentScope, type RuntimeComponentStatus, type RuntimeComponentStore, RuntimeComponentStoreContext, SlotRenderer, UdsRenderer, type UdsRendererProps, VERBATIM_ATTRIBUTES, aliasHtmlTypes, computedFunctions, entryRenderer, glyphRegistryEntries, installRuntimeComponentStore, makeComponentEntry, registerComputed, resolveGlyph, runtimeComponent, slotFillValue, specContent, stampForcedModifiers, useForcedModifierStamp, withComputedFunctions, wrapEventBridge, wrapGlyphProps, wrapInlineStyleProps, wrapNormalizeHex, wrapRegistry };
|
package/dist/renderer/index.js
CHANGED
|
@@ -1,6 +1,8 @@
|
|
|
1
1
|
import { computedFunctions, registerComputed, withComputedFunctions } from "./computed.js";
|
|
2
2
|
import { RendererErrorBoundary } from "./RendererErrorBoundary.js";
|
|
3
3
|
import { REVEALED_LAYER_ATTR, specContent } from "./spec-content.js";
|
|
4
|
+
import { stampForcedModifiers } from "./forced-stamp.js";
|
|
5
|
+
import { useForcedModifierStamp } from "./use-forced-stamp.js";
|
|
4
6
|
import { entryRenderer, makeComponentEntry, slotFillValue } from "./componentEntry.js";
|
|
5
7
|
import { resolveGlyph } from "./resolveGlyph.js";
|
|
6
8
|
import { glyphRegistryEntries } from "./glyphEntries.js";
|
|
@@ -14,4 +16,4 @@ import { VERBATIM_ATTRIBUTES, aliasHtmlTypes } from "./wrappers/html-aliases.js"
|
|
|
14
16
|
import { wrapInlineStyleProps } from "./wrappers/inline-styles.js";
|
|
15
17
|
import { wrapRegistry } from "./wrapRegistry.js";
|
|
16
18
|
import { UdsRenderer } from "./UdsRenderer.js";
|
|
17
|
-
export { FragmentRenderer, REVEALED_LAYER_ATTR, RendererErrorBoundary, RuntimeComponentFailureContext, RuntimeComponentRebuildContext, RuntimeComponentStoreContext, SlotRenderer, UdsRenderer, VERBATIM_ATTRIBUTES, aliasHtmlTypes, computedFunctions, entryRenderer, glyphRegistryEntries, installRuntimeComponentStore, makeComponentEntry, registerComputed, resolveGlyph, runtimeComponent, slotFillValue, specContent, withComputedFunctions, wrapEventBridge, wrapGlyphProps, wrapInlineStyleProps, wrapNormalizeHex, wrapRegistry };
|
|
19
|
+
export { FragmentRenderer, REVEALED_LAYER_ATTR, RendererErrorBoundary, RuntimeComponentFailureContext, RuntimeComponentRebuildContext, RuntimeComponentStoreContext, SlotRenderer, UdsRenderer, VERBATIM_ATTRIBUTES, aliasHtmlTypes, computedFunctions, entryRenderer, glyphRegistryEntries, installRuntimeComponentStore, makeComponentEntry, registerComputed, resolveGlyph, runtimeComponent, slotFillValue, specContent, stampForcedModifiers, useForcedModifierStamp, withComputedFunctions, wrapEventBridge, wrapGlyphProps, wrapInlineStyleProps, wrapNormalizeHex, wrapRegistry };
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { RefObject } from "react";
|
|
2
|
+
|
|
3
|
+
//#region src/renderer/use-forced-stamp.d.ts
|
|
4
|
+
/**
|
|
5
|
+
* Keep a forced component's own elements under `ref` marked with `attributes` (see
|
|
6
|
+
* {@link stampForcedModifiers}) as its DOM renders and re-renders: marked after every commit, and
|
|
7
|
+
* again when the subtree changes underneath (a lazy layer mounting, a module swapping in).
|
|
8
|
+
*/
|
|
9
|
+
declare function useForcedModifierStamp(ref: RefObject<Element | null>, component: string, attributes: Readonly<Record<string, string>>): void;
|
|
10
|
+
//#endregion
|
|
11
|
+
export { useForcedModifierStamp };
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
import { stampForcedModifiers } from "./forced-stamp.js";
|
|
2
|
+
import { useLayoutEffect, useRef } from "react";
|
|
3
|
+
//#region src/renderer/use-forced-stamp.ts
|
|
4
|
+
/**
|
|
5
|
+
* Keep a forced component's own elements under `ref` marked with `attributes` (see
|
|
6
|
+
* {@link stampForcedModifiers}) as its DOM renders and re-renders: marked after every commit, and
|
|
7
|
+
* again when the subtree changes underneath (a lazy layer mounting, a module swapping in).
|
|
8
|
+
*/
|
|
9
|
+
function useForcedModifierStamp(ref, component, attributes) {
|
|
10
|
+
const key = Object.keys(attributes).sort().join("|");
|
|
11
|
+
const latest = useRef(attributes);
|
|
12
|
+
latest.current = attributes;
|
|
13
|
+
useLayoutEffect(() => {
|
|
14
|
+
const container = ref.current;
|
|
15
|
+
if (!container || key === "") return;
|
|
16
|
+
const attributes = latest.current;
|
|
17
|
+
let undo = stampForcedModifiers({
|
|
18
|
+
container,
|
|
19
|
+
component,
|
|
20
|
+
attributes
|
|
21
|
+
});
|
|
22
|
+
const observer = new MutationObserver(() => {
|
|
23
|
+
observer.disconnect();
|
|
24
|
+
undo();
|
|
25
|
+
undo = stampForcedModifiers({
|
|
26
|
+
container,
|
|
27
|
+
component,
|
|
28
|
+
attributes
|
|
29
|
+
});
|
|
30
|
+
observer.observe(container, {
|
|
31
|
+
childList: true,
|
|
32
|
+
subtree: true
|
|
33
|
+
});
|
|
34
|
+
});
|
|
35
|
+
observer.observe(container, {
|
|
36
|
+
childList: true,
|
|
37
|
+
subtree: true
|
|
38
|
+
});
|
|
39
|
+
return () => {
|
|
40
|
+
observer.disconnect();
|
|
41
|
+
undo();
|
|
42
|
+
};
|
|
43
|
+
}, [
|
|
44
|
+
ref,
|
|
45
|
+
component,
|
|
46
|
+
key
|
|
47
|
+
]);
|
|
48
|
+
}
|
|
49
|
+
//#endregion
|
|
50
|
+
export { useForcedModifierStamp };
|
package/dist/spec/specToJsx.d.ts
CHANGED
|
@@ -32,6 +32,12 @@ interface SpecToJsxOptions {
|
|
|
32
32
|
* package that exports it.
|
|
33
33
|
*/
|
|
34
34
|
glyphMembers?: Readonly<Record<string, readonly string[]>>;
|
|
35
|
+
/**
|
|
36
|
+
* Component type → the states it declares. A design-time instance may pin one (a canvas mock of a
|
|
37
|
+
* filled field); a state is never a prop, so code leaves it out rather than writing
|
|
38
|
+
* `<Input filled />`, which would force the look in production.
|
|
39
|
+
*/
|
|
40
|
+
states?: Readonly<Record<string, readonly string[]>>;
|
|
35
41
|
}
|
|
36
42
|
interface SpecToJsxResult {
|
|
37
43
|
/** Generated JSX source code */
|
package/dist/spec/specToJsx.js
CHANGED
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
import { UDS_FORCE_STATES } from "../framework/component-states.js";
|
|
2
|
+
import "../framework/class-names.js";
|
|
1
3
|
import { glyphJsxForm, glyphMemberOf, jsxIdentifier, parseGlyphType } from "./glyph-jsx.js";
|
|
2
4
|
import { serializeProps } from "@json-render/codegen";
|
|
3
5
|
//#region src/spec/specToJsx.ts
|
|
@@ -108,6 +110,8 @@ function renderElement(key, spec, depth, ctx, ancestors) {
|
|
|
108
110
|
if (ancestors.has(key)) return `${indent}{/* cyclic reference to "${key}" omitted */}`;
|
|
109
111
|
const withSelf = new Set(ancestors).add(key);
|
|
110
112
|
const { children: _children, ...propsWithoutSlots } = element.props ?? {};
|
|
113
|
+
delete propsWithoutSlots[UDS_FORCE_STATES];
|
|
114
|
+
for (const state of ctx.states?.[element.type] ?? []) delete propsWithoutSlots[state];
|
|
111
115
|
const slotKeys = collectSlotKeys(element.slots);
|
|
112
116
|
const slotAttrs = [];
|
|
113
117
|
for (const [propName, fills] of Object.entries(element.slots ?? {})) if (fills.length === 1) {
|
|
@@ -207,6 +211,7 @@ function specToJsx(spec, options) {
|
|
|
207
211
|
glyphModules: options?.glyphModules,
|
|
208
212
|
glyphProps: options?.glyphProps,
|
|
209
213
|
glyphMembers: options?.glyphMembers,
|
|
214
|
+
states: options?.states,
|
|
210
215
|
members: /* @__PURE__ */ new Map()
|
|
211
216
|
};
|
|
212
217
|
const jsxTree = renderElement(spec.root, spec, 0, ctx, /* @__PURE__ */ new Set());
|