@fulate/core 1.0.11 → 1.0.13
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/index.d.ts +2 -1
- package/dist/index.js +116 -58
- package/dist/mutation/change-batch.d.ts +4 -2
- package/dist/node/element.d.ts +20 -6
- package/dist/node/reference-transform.d.ts +2 -0
- package/dist/root/index.d.ts +3 -3
- package/dist/root/input-controller.d.ts +29 -8
- package/dist/root/scene-registry.d.ts +17 -8
- package/package.json +1 -1
package/dist/index.d.ts
CHANGED
|
@@ -8,7 +8,7 @@ export { ChangeImpact, NodeProperties, resolveOrigin, TransformProperties } from
|
|
|
8
8
|
export type { OriginX, OriginY, PropertyChanges, PropertyUpdates, TransformableOptions } from "./node/properties";
|
|
9
9
|
export { Element, ElementProperties } from "./node/element";
|
|
10
10
|
export type { AnyElement, BaseElementOption, ElementJSON, ElementOptionPatch, AnimateOptions, AnimateTarget } from "./node/element";
|
|
11
|
-
export { isReparentTransformIntent, resolveAuthoredGeometryFramePatch, resolveReferenceTransform, resolveReferenceTransformTarget } from "./node/reference-transform";
|
|
11
|
+
export { isReparentTransformIntent, resolveAuthoredGeometryFramePatch, resolveReferenceBoundsTranslation, resolveReferenceTransform, resolveReferenceTransformTarget } from "./node/reference-transform";
|
|
12
12
|
export type { ElementTransformBaseline, ReferenceTransformBaseline, ReferenceTransformFrame, ReferenceTransformResolution, ReferenceTransformTarget, ReparentTransformIntent, TransformIntent } from "./node/reference-transform";
|
|
13
13
|
export { DEFAULT_CONNECTION_PORT_SCHEMA, getElementConnectionPort, getElementConnectionPortPoint, getElementConnectionPortPoints, projectConnectionPortPoint } from "./utils/connection-port";
|
|
14
14
|
export type { ConnectionPortId, ConnectionPortConfiguration, ConnectionPortDefinition, ConnectionPortLabelStyle, ConnectionPortDirection, ConnectionPortLimit, ConnectionPortLimits, ConnectionPortRef, DerivedConnectionPort, EdgeConnectionPortPosition, ResolvedConnectionPort, ResolvedConnectionPortSlot } from "./utils/connection-port";
|
|
@@ -25,6 +25,7 @@ export { FrameStabilizationError, RootFrameRuntime } from "./root/frame-runtime"
|
|
|
25
25
|
export type { RootFrameCompletionWork, RootFrameLayoutOwner, RootFrameParticipant } from "./root/frame-runtime";
|
|
26
26
|
export { SceneRegistry } from "./root/scene-registry";
|
|
27
27
|
export type { NodeKeyObserver, NodeRegistrationObserver, SceneChangeObserver } from "./root/scene-registry";
|
|
28
|
+
export { mergeOwnerPropertyChanges } from "./mutation/change-batch";
|
|
28
29
|
export type { ChangeHistorySink, OwnerPropertyChange, StructureChange } from "./mutation/change-batch";
|
|
29
30
|
export { Layer, LayerProperties, LayerTransform } from "./layer/index";
|
|
30
31
|
export type { LayerFrameWork, LayerOption, LayerOptionPatch } from "./layer/index";
|
package/dist/index.js
CHANGED
|
@@ -3277,6 +3277,11 @@ var Element = class Element extends Node {
|
|
|
3277
3277
|
/** @internal 在全部 owner/tree 安装及 lifecycle 后运行 owner hook。 */
|
|
3278
3278
|
runPropertyCommitHook(commit) {
|
|
3279
3279
|
if (commit.update.changes.size) this.onPropertiesChanged(this.propertyState, commit.update.changes);
|
|
3280
|
+
if (commit.update.source === "configured" && this.onConfiguredPropertiesChanged) {
|
|
3281
|
+
const keys = [];
|
|
3282
|
+
for (const field of commit.update.fields) if (field.sourceChanged) keys.push(field.key);
|
|
3283
|
+
if (keys.length) this.onConfiguredPropertiesChanged(keys);
|
|
3284
|
+
}
|
|
3280
3285
|
}
|
|
3281
3286
|
/** @internal 在 owner hook 后通知依赖实际 Ports commit 的框架消费者。 */
|
|
3282
3287
|
notifyPortsCommit(commit) {
|
|
@@ -3494,22 +3499,13 @@ var Element = class Element extends Node {
|
|
|
3494
3499
|
origin: "builtin"
|
|
3495
3500
|
};
|
|
3496
3501
|
}
|
|
3497
|
-
/** @internal
|
|
3498
|
-
|
|
3499
|
-
if (ports === false) return
|
|
3500
|
-
|
|
3501
|
-
return (this.getDefaultConnectionPortSchema() ?? DEFAULT_CONNECTION_PORT_SCHEMA).map((port) => ({
|
|
3502
|
-
ref: {
|
|
3503
|
-
elementKey: this.key,
|
|
3504
|
-
portId: port.id
|
|
3505
|
-
},
|
|
3506
|
-
kind: "endpoint-binding",
|
|
3507
|
-
localPosition: port.localPosition(this),
|
|
3508
|
-
origin: "builtin"
|
|
3509
|
-
}));
|
|
3502
|
+
/** @internal 只解释显式 Port replacement 的 IDs;patch 是同批最终 owner fields。 */
|
|
3503
|
+
resolveConnectionPortIds(ports, patch) {
|
|
3504
|
+
if (ports === false) return [];
|
|
3505
|
+
return (ports === true ? this.getDefaultConnectionPortSchema(patch) ?? DEFAULT_CONNECTION_PORT_SCHEMA : ports).map(({ id }) => id);
|
|
3510
3506
|
}
|
|
3511
3507
|
/** 返回元素类型自有的默认 Port;`null` 使用通用四边 Ports。 */
|
|
3512
|
-
getDefaultConnectionPortSchema() {
|
|
3508
|
+
getDefaultConnectionPortSchema(_patch) {
|
|
3513
3509
|
return null;
|
|
3514
3510
|
}
|
|
3515
3511
|
/** 返回 custom Ports 的当前 decoration slots。 @internal */
|
|
@@ -3552,11 +3548,18 @@ var Element = class Element extends Node {
|
|
|
3552
3548
|
edgeLength: edge === "top" || edge === "bottom" ? Math.abs(this.width ?? 0) : Math.abs(this.height ?? 0)
|
|
3553
3549
|
};
|
|
3554
3550
|
}
|
|
3555
|
-
/**
|
|
3551
|
+
/**
|
|
3552
|
+
* 将当前配置值填入 caller 提供的 value cells,保留结构化值的原引用。
|
|
3553
|
+
* 读取包含默认值的 configured 结果,不读取 runtime 覆盖;保留 null/undefined。
|
|
3554
|
+
* cells 可复用;借用值不得原地修改并期待自动提交,需要独立值时由 caller 复制。
|
|
3555
|
+
*/
|
|
3556
3556
|
static readConfiguredPropertyValues(owner, targets) {
|
|
3557
3557
|
readConfiguredPropertyValues(owner.propertyState, targets);
|
|
3558
3558
|
}
|
|
3559
|
-
/**
|
|
3559
|
+
/**
|
|
3560
|
+
* 借用当前字段的 configured/default 值,忽略 runtime 覆盖,保留 null/undefined。
|
|
3561
|
+
* 返回结构化原引用,不表示该字段是否曾被显式配置;需要独立值时由 caller 复制。
|
|
3562
|
+
*/
|
|
3560
3563
|
static getConfiguredPropertyValue(owner, key) {
|
|
3561
3564
|
return getConfiguredPropertyValue(owner.propertyState, key);
|
|
3562
3565
|
}
|
|
@@ -3804,19 +3807,31 @@ function resolveBakedAuthoredGeometryTransform(baseline, target) {
|
|
|
3804
3807
|
function resolveAuthoredGeometryFramePatch(baseline, resolution, authoredBounds) {
|
|
3805
3808
|
if (isIdentityMatrix(resolution.authoredLocalDelta)) return resolution.framePatch;
|
|
3806
3809
|
const approximateBounds = transformReferenceBounds(baseline.referenceBounds, resolution.authoredLocalDelta);
|
|
3807
|
-
const originX = resolveOrigin(baseline.frame.originX) + .5;
|
|
3808
|
-
const originY = resolveOrigin(baseline.frame.originY) + .5;
|
|
3809
|
-
const approximateOffsetX = approximateBounds.left + originX * approximateBounds.width;
|
|
3810
|
-
const approximateOffsetY = approximateBounds.top + originY * approximateBounds.height;
|
|
3811
|
-
const authoredOffsetX = authoredBounds.left + originX * authoredBounds.width;
|
|
3812
|
-
const authoredOffsetY = authoredBounds.top + originY * authoredBounds.height;
|
|
3813
|
-
const deltaX = authoredOffsetX - approximateOffsetX;
|
|
3814
|
-
const deltaY = authoredOffsetY - approximateOffsetY;
|
|
3815
|
-
const frameLinear = createFrameLinearMatrix(baseline.frame);
|
|
3816
3810
|
return {
|
|
3817
3811
|
...resolution.framePatch,
|
|
3818
|
-
|
|
3819
|
-
|
|
3812
|
+
...resolveReferenceBoundsTranslation({
|
|
3813
|
+
...baseline.frame,
|
|
3814
|
+
...resolution.framePatch
|
|
3815
|
+
}, approximateBounds, authoredBounds)
|
|
3816
|
+
};
|
|
3817
|
+
}
|
|
3818
|
+
/** @internal reference bounds 改变时修正 origin 位移,保留给定最终 frame 的仿射。 */
|
|
3819
|
+
function resolveReferenceBoundsTranslation(frame, before, after) {
|
|
3820
|
+
const { left = 0, top = 0, angle = 0, skewX = 0, skewY = 0, scaleX = 1, scaleY = 1, originX = "center", originY = "center" } = frame;
|
|
3821
|
+
const x = resolveOrigin(originX) + .5;
|
|
3822
|
+
const y = resolveOrigin(originY) + .5;
|
|
3823
|
+
const deltaX = after.left + x * after.width - before.left - x * before.width;
|
|
3824
|
+
const deltaY = after.top + y * after.height - before.top - y * before.height;
|
|
3825
|
+
const linear = createFrameLinearMatrix({
|
|
3826
|
+
angle,
|
|
3827
|
+
skewX,
|
|
3828
|
+
skewY,
|
|
3829
|
+
scaleX,
|
|
3830
|
+
scaleY
|
|
3831
|
+
});
|
|
3832
|
+
return {
|
|
3833
|
+
left: left - deltaX + linear.a * deltaX + linear.c * deltaY,
|
|
3834
|
+
top: top - deltaY + linear.b * deltaX + linear.d * deltaY
|
|
3820
3835
|
};
|
|
3821
3836
|
}
|
|
3822
3837
|
/** 判断变换意图是否包含跨父级重挂载所需的目标父级矩阵。 */
|
|
@@ -4496,14 +4511,14 @@ var RootInputController = class {
|
|
|
4496
4511
|
isPanning = false;
|
|
4497
4512
|
/** @internal 是否应在连续指针操作期间暂停 hover 重算。 */
|
|
4498
4513
|
hasLockPoint = false;
|
|
4499
|
-
/**
|
|
4500
|
-
|
|
4514
|
+
/** Input 原地更新的唯一 client 坐标。 */
|
|
4515
|
+
pointerPosition = {
|
|
4501
4516
|
x: 0,
|
|
4502
4517
|
y: 0
|
|
4503
4518
|
};
|
|
4504
4519
|
/** 最近一次记录的指针是否位于 Root 容器内。 */
|
|
4505
4520
|
pointerInside = false;
|
|
4506
|
-
/**
|
|
4521
|
+
/** 当前允许接收元素级指针输入的子树根节点。 */
|
|
4507
4522
|
interactionScopes = /* @__PURE__ */ new Set();
|
|
4508
4523
|
/** 一次 Root 激活周期内全部 DOM listener 的统一清理器。 */
|
|
4509
4524
|
abortController = null;
|
|
@@ -4517,7 +4532,11 @@ var RootInputController = class {
|
|
|
4517
4532
|
constructor(root) {
|
|
4518
4533
|
this.root = root;
|
|
4519
4534
|
}
|
|
4520
|
-
/**
|
|
4535
|
+
/** 最近一次 DOM 指针的 clientX/clientY 只读借用;后续输入原地更新同一对象。 */
|
|
4536
|
+
get lastPointerPos() {
|
|
4537
|
+
return this.pointerPosition;
|
|
4538
|
+
}
|
|
4539
|
+
/** Root 当前是否认为指针位于容器内。 */
|
|
4521
4540
|
get isPointerInside() {
|
|
4522
4541
|
return this.pointerInside;
|
|
4523
4542
|
}
|
|
@@ -4563,7 +4582,16 @@ var RootInputController = class {
|
|
|
4563
4582
|
this.deactivate();
|
|
4564
4583
|
this.interactionScopes.clear();
|
|
4565
4584
|
}
|
|
4566
|
-
/**
|
|
4585
|
+
/**
|
|
4586
|
+
* 取消当前指针操作,释放指针捕获与 hover 锁定,并清除连续点击记录。
|
|
4587
|
+
*
|
|
4588
|
+
* 省略 node 时取消当前场景或空格平移操作。传入所属 Root 内的节点时,
|
|
4589
|
+
* 仅取消按下目标为该节点或其后代的场景操作;空白处以 Root 为目标的操作、
|
|
4590
|
+
* 空格平移和其他子树的操作不受影响。
|
|
4591
|
+
*
|
|
4592
|
+
* 场景操作按当前交互范围派发一次 pointercancel,不产生 pointerup 或 click;
|
|
4593
|
+
* 平移操作只释放输入状态,保留已经发生的 Viewport 平移。
|
|
4594
|
+
*/
|
|
4567
4595
|
cancelSession(node) {
|
|
4568
4596
|
if (!node) {
|
|
4569
4597
|
this.cancelPointerSession();
|
|
@@ -4584,7 +4612,17 @@ var RootInputController = class {
|
|
|
4584
4612
|
setPointerInside(inside) {
|
|
4585
4613
|
this.pointerInside = inside;
|
|
4586
4614
|
}
|
|
4587
|
-
/**
|
|
4615
|
+
/**
|
|
4616
|
+
* 允许所属 Root 内的 scope 及其后代接收元素级指针输入,返回注销函数。
|
|
4617
|
+
*
|
|
4618
|
+
* 多个范围取并集;没有范围时恢复普通派发。范围外的命中仍作为事件 target
|
|
4619
|
+
* 派给 Root,但不进入命中元素的指针、点击、悬停或右键处理器。
|
|
4620
|
+
* wheel 仍派给命中元素;范围内事件保留正常冒泡,范围不改变命中查询结果。
|
|
4621
|
+
*
|
|
4622
|
+
* 调用方负责每个 scope 同时只保留一次注册,并在退出交互或停用时注销;
|
|
4623
|
+
* 再次进入时重新注册。注册和注销通过现有帧队列刷新 hover 与 cursor,
|
|
4624
|
+
* 不自动取消进行中的指针操作;需要取消时调用 cancelSession(scope)。
|
|
4625
|
+
*/
|
|
4588
4626
|
registerInteractionScope(scope) {
|
|
4589
4627
|
this.interactionScopes.add(scope);
|
|
4590
4628
|
this.root.scheduleHoverRefresh();
|
|
@@ -4593,7 +4631,7 @@ var RootInputController = class {
|
|
|
4593
4631
|
this.root.scheduleHoverRefresh();
|
|
4594
4632
|
};
|
|
4595
4633
|
}
|
|
4596
|
-
/**
|
|
4634
|
+
/** 判断元素是否属于当前允许交互的子树;无范围限制时为 true,不执行命中或焦点查询。 */
|
|
4597
4635
|
isInteractionTarget(element) {
|
|
4598
4636
|
if (this.interactionScopes.size === 0) return true;
|
|
4599
4637
|
for (let node = element; node; node = node.parent) if (node instanceof Element && this.interactionScopes.has(node)) return true;
|
|
@@ -4613,8 +4651,8 @@ var RootInputController = class {
|
|
|
4613
4651
|
}
|
|
4614
4652
|
/** 保存 DOM client 坐标,供无显式事件的 hover 重算使用。 */
|
|
4615
4653
|
updatePointer(event) {
|
|
4616
|
-
this.
|
|
4617
|
-
this.
|
|
4654
|
+
this.pointerPosition.x = event.clientX;
|
|
4655
|
+
this.pointerPosition.y = event.clientY;
|
|
4618
4656
|
}
|
|
4619
4657
|
/** 将一个 DOM 输入转换为 Fulate world 事件并派给当前场景目标。 */
|
|
4620
4658
|
dispatchDomEvent(event, eventName, target = this.root.currentElement, point = this.root.viewport.getLogicalPosition(event.clientX, event.clientY)) {
|
|
@@ -5565,11 +5603,21 @@ var SceneRegistry = class {
|
|
|
5565
5603
|
sceneChangeObservers = /* @__PURE__ */ new Set();
|
|
5566
5604
|
/** 监听 active registration 的轻量观察器。 */
|
|
5567
5605
|
nodeRegistrationObservers = /* @__PURE__ */ new Set();
|
|
5568
|
-
/**
|
|
5569
|
-
constructor(
|
|
5570
|
-
this.
|
|
5606
|
+
/** @internal 由 Root 创建,拥有当前场景唯一 key 索引。 */
|
|
5607
|
+
constructor(nodes = /* @__PURE__ */ new Map()) {
|
|
5608
|
+
this.nodes = nodes;
|
|
5571
5609
|
}
|
|
5572
|
-
/**
|
|
5610
|
+
/**
|
|
5611
|
+
* 当前 active 节点的只读 live 索引;与内部 Map 为同一引用,不创建快照。
|
|
5612
|
+
* 初始枚举后可订阅增量变化,后续注册/注销会直接更新此视图。
|
|
5613
|
+
*/
|
|
5614
|
+
get keyElements() {
|
|
5615
|
+
return this.nodes;
|
|
5616
|
+
}
|
|
5617
|
+
/**
|
|
5618
|
+
* 订阅后续场景查询/结构变化,返回退订函数;不补发当前状态。
|
|
5619
|
+
* 此通知不代表完整属性变化或帧已稳定;Root 销毁时清除订阅。
|
|
5620
|
+
*/
|
|
5573
5621
|
observeSceneChanges(observer) {
|
|
5574
5622
|
this.sceneChangeObservers.add(observer);
|
|
5575
5623
|
return () => this.sceneChangeObservers.delete(observer);
|
|
@@ -5578,7 +5626,11 @@ var SceneRegistry = class {
|
|
|
5578
5626
|
get hasSceneChangeObservers() {
|
|
5579
5627
|
return this.sceneChangeObservers.size > 0;
|
|
5580
5628
|
}
|
|
5581
|
-
/**
|
|
5629
|
+
/**
|
|
5630
|
+
* 订阅后续节点进入/离开 active 生命周期,返回退订函数;不补发已有节点。
|
|
5631
|
+
* 回调时索引与 active 状态已安装;detach/reinsert 分别通知 false/true。
|
|
5632
|
+
* Root 销毁时清除订阅。
|
|
5633
|
+
*/
|
|
5582
5634
|
observeNodeRegistrations(observer) {
|
|
5583
5635
|
this.nodeRegistrationObservers.add(observer);
|
|
5584
5636
|
return () => this.nodeRegistrationObservers.delete(observer);
|
|
@@ -5621,13 +5673,13 @@ var SceneRegistry = class {
|
|
|
5621
5673
|
const key = node.key;
|
|
5622
5674
|
const existing = this.keyElements.get(key);
|
|
5623
5675
|
if (existing && existing !== node) console.warn(`Duplicate node key: "${key}"`);
|
|
5624
|
-
this.
|
|
5676
|
+
this.nodes.set(key, node);
|
|
5625
5677
|
}
|
|
5626
5678
|
/** @internal 从索引移除停用节点并通知 key 观察器。 */
|
|
5627
5679
|
unregisterNodeKey(node) {
|
|
5628
5680
|
const key = node.key;
|
|
5629
5681
|
if (this.keyElements.get(key) === node) {
|
|
5630
|
-
this.
|
|
5682
|
+
this.nodes.delete(key);
|
|
5631
5683
|
this.notifyNodeKeyObservers(key, node, false);
|
|
5632
5684
|
}
|
|
5633
5685
|
this.notifyNodeRegistrationObservers(node, false);
|
|
@@ -5645,7 +5697,7 @@ var SceneRegistry = class {
|
|
|
5645
5697
|
}
|
|
5646
5698
|
/** @internal 清空 key 索引和全部观察器。 */
|
|
5647
5699
|
clear() {
|
|
5648
|
-
this.
|
|
5700
|
+
this.nodes.clear();
|
|
5649
5701
|
this.nodeKeyObservers.clear();
|
|
5650
5702
|
this.nodeRegistrationObservers.clear();
|
|
5651
5703
|
this.sceneChangeObservers.clear();
|
|
@@ -5745,15 +5797,8 @@ function syncStructureLifecycles(nodes) {
|
|
|
5745
5797
|
}
|
|
5746
5798
|
//#endregion
|
|
5747
5799
|
//#region packages/core/src/mutation/change-batch.ts
|
|
5748
|
-
/**
|
|
5749
|
-
|
|
5750
|
-
*
|
|
5751
|
-
* owner effects 先按对象身份合并最终 patch;所有 fields/raw links 安装完成后才运行
|
|
5752
|
-
* History、lifecycle、hooks、dirty 和一次 scene delivery。本函数不提供 rollback、
|
|
5753
|
-
* retry、receipt 或 rejected 结果。
|
|
5754
|
-
*/
|
|
5755
|
-
function applyChangeBatch(root, ownerEffects, structureEffects = [], history) {
|
|
5756
|
-
if (ownerEffects.length === 0 && structureEffects.length === 0) return;
|
|
5800
|
+
/** @internal 合并 raw owner effects;单个 patch 直接借用,仅合并同 owner 字段时分配。 */
|
|
5801
|
+
function mergeOwnerPropertyChanges(ownerEffects) {
|
|
5757
5802
|
const slots = /* @__PURE__ */ new Map();
|
|
5758
5803
|
let mergedOwners = null;
|
|
5759
5804
|
for (const { owner, patch } of ownerEffects) {
|
|
@@ -5772,6 +5817,18 @@ function applyChangeBatch(root, ownerEffects, structureEffects = [], history) {
|
|
|
5772
5817
|
}
|
|
5773
5818
|
for (const key of Object.keys(patch)) finalPatch[key] = patch[key];
|
|
5774
5819
|
}
|
|
5820
|
+
return slots;
|
|
5821
|
+
}
|
|
5822
|
+
/**
|
|
5823
|
+
* 同步应用一份 trusted change batch。
|
|
5824
|
+
*
|
|
5825
|
+
* owner effects 先按对象身份合并最终 patch;所有 fields/raw links 安装完成后才运行
|
|
5826
|
+
* History、lifecycle、hooks、dirty 和一次 scene delivery。本函数不提供 rollback、
|
|
5827
|
+
* retry、receipt 或 rejected 结果。返回本批次是否实际安装属性或结构变化。
|
|
5828
|
+
*/
|
|
5829
|
+
function applyChangeBatch(root, ownerEffects, structureEffects = [], history) {
|
|
5830
|
+
if (ownerEffects.length === 0 && structureEffects.length === 0) return false;
|
|
5831
|
+
const slots = mergeOwnerPropertyChanges(ownerEffects);
|
|
5775
5832
|
const properties = [];
|
|
5776
5833
|
for (const [owner, patch] of slots) {
|
|
5777
5834
|
const commit = owner.preparePropertyCommit(patch);
|
|
@@ -5782,7 +5839,7 @@ function applyChangeBatch(root, ownerEffects, structureEffects = [], history) {
|
|
|
5782
5839
|
}
|
|
5783
5840
|
const structureBatch = prepareStructureBatch(structureEffects);
|
|
5784
5841
|
const structure = structureBatch.changes;
|
|
5785
|
-
if (properties.length === 0 && structure.length === 0) return;
|
|
5842
|
+
if (properties.length === 0 && structure.length === 0) return false;
|
|
5786
5843
|
const placements = history ? preparePlacementChanges(structure) : null;
|
|
5787
5844
|
for (const { owner, commit } of properties) owner.installPropertyCommit(commit);
|
|
5788
5845
|
const lifecycleRoots = installStructureLinks(structureBatch);
|
|
@@ -5811,6 +5868,7 @@ function applyChangeBatch(root, ownerEffects, structureEffects = [], history) {
|
|
|
5811
5868
|
else if (hoverChanged) root.scheduleHoverRefresh();
|
|
5812
5869
|
if (root.sceneRegistry.hasSceneChangeObservers) root.sceneRegistry.notifySceneChange(void 0, [...properties.map(({ owner }) => owner), ...structure.flatMap(({ owner, changed }) => [owner, ...changed])]);
|
|
5813
5870
|
for (const { owner, commit } of properties) owner.dispatchPortsChange(commit);
|
|
5871
|
+
return true;
|
|
5814
5872
|
}
|
|
5815
5873
|
//#endregion
|
|
5816
5874
|
//#region packages/core/src/root/index.ts
|
|
@@ -5826,9 +5884,9 @@ var Root = class extends Node {
|
|
|
5826
5884
|
skinTextCommitObservers;
|
|
5827
5885
|
/** Root 的平移、缩放、DPR 和坐标换算对象。 */
|
|
5828
5886
|
viewport;
|
|
5829
|
-
/**
|
|
5887
|
+
/** Root 拥有的输入控制器,提供只读查询、交互范围注册和指针操作取消。 */
|
|
5830
5888
|
input;
|
|
5831
|
-
/**
|
|
5889
|
+
/** 当前活动节点的只读索引及增量场景订阅。 */
|
|
5832
5890
|
sceneRegistry;
|
|
5833
5891
|
/** @internal 跨 Layer 帧队列、动画时钟和 nextTick 状态。 */
|
|
5834
5892
|
frameRuntime;
|
|
@@ -6057,7 +6115,7 @@ var Root = class extends Node {
|
|
|
6057
6115
|
* 同 owner 只 finalize/install 一次,全部 fields/raw links 安装后统一发布。
|
|
6058
6116
|
*/
|
|
6059
6117
|
applyChangeBatch(owners, structure = [], history) {
|
|
6060
|
-
applyChangeBatch(this, owners, structure, history);
|
|
6118
|
+
return applyChangeBatch(this, owners, structure, history);
|
|
6061
6119
|
}
|
|
6062
6120
|
/** 按活动场景中的唯一 key 查询节点;key 来自 `node.key`。 */
|
|
6063
6121
|
getByKey(key) {
|
|
@@ -6940,4 +6998,4 @@ var Layer = class Layer extends Element {
|
|
|
6940
6998
|
}
|
|
6941
6999
|
};
|
|
6942
7000
|
//#endregion
|
|
6943
|
-
export { ChangeImpact, CustomEvent, DEFAULT_CONNECTION_PORT_SCHEMA, EVENT_NAMES, Element, ElementProperties, ElementTransform, EventEmitter, FrameStabilizationError, Layer, LayerProperties, LayerTransform, Node, NodeLifecycleEvent, NodeProperties, Root, RootFrameRuntime, RootInputController, SKIN_DEFAULTS, SceneRegistry, Shape, ShapeProperties, ShapeTransform, Skin, TransformProperties, Viewport, createAuthoredLineSubpath, createGeometryQuery, createGeometrySnapshot, createLineSubpath, createPathLocalId, evaluatePathSegmentPoint, getElementConnectionPort, getElementConnectionPortPoint, getElementConnectionPortPoints, isFormControlTarget, isReparentTransformIntent, projectConnectionPortPoint, resolveAuthoredGeometryFramePatch, resolveAuthoredSubpath, resolveOrigin, resolveReferenceTransform, resolveReferenceTransformTarget, splitPathSegment };
|
|
7001
|
+
export { ChangeImpact, CustomEvent, DEFAULT_CONNECTION_PORT_SCHEMA, EVENT_NAMES, Element, ElementProperties, ElementTransform, EventEmitter, FrameStabilizationError, Layer, LayerProperties, LayerTransform, Node, NodeLifecycleEvent, NodeProperties, Root, RootFrameRuntime, RootInputController, SKIN_DEFAULTS, SceneRegistry, Shape, ShapeProperties, ShapeTransform, Skin, TransformProperties, Viewport, createAuthoredLineSubpath, createGeometryQuery, createGeometrySnapshot, createLineSubpath, createPathLocalId, evaluatePathSegmentPoint, getElementConnectionPort, getElementConnectionPortPoint, getElementConnectionPortPoints, isFormControlTarget, isReparentTransformIntent, mergeOwnerPropertyChanges, projectConnectionPortPoint, resolveAuthoredGeometryFramePatch, resolveAuthoredSubpath, resolveOrigin, resolveReferenceBoundsTranslation, resolveReferenceTransform, resolveReferenceTransformTarget, splitPathSegment };
|
|
@@ -18,12 +18,14 @@ export interface ChangeHistorySink {
|
|
|
18
18
|
/** 记录一个节点首次触及批次提供的 before placement。 */
|
|
19
19
|
recordPlacementChange(node: Node, beforeOwner: Node | null, beforeIndex: number): void;
|
|
20
20
|
}
|
|
21
|
+
/** @internal 合并 raw owner effects;单个 patch 直接借用,仅合并同 owner 字段时分配。 */
|
|
22
|
+
export declare function mergeOwnerPropertyChanges(ownerEffects: readonly OwnerPropertyChange[]): Map<Element<import("..").ElementProperties, import("..").BaseElementOption<any>, Partial<Omit<import("..").BaseElementOption<any>, "key" | "children">>>, Readonly<Record<string, unknown>>>;
|
|
21
23
|
/**
|
|
22
24
|
* 同步应用一份 trusted change batch。
|
|
23
25
|
*
|
|
24
26
|
* owner effects 先按对象身份合并最终 patch;所有 fields/raw links 安装完成后才运行
|
|
25
27
|
* History、lifecycle、hooks、dirty 和一次 scene delivery。本函数不提供 rollback、
|
|
26
|
-
* retry、receipt 或 rejected
|
|
28
|
+
* retry、receipt 或 rejected 结果。返回本批次是否实际安装属性或结构变化。
|
|
27
29
|
*/
|
|
28
|
-
export declare function applyChangeBatch(root: Root, ownerEffects: readonly OwnerPropertyChange[], structureEffects?: readonly StructureChange[], history?: ChangeHistorySink):
|
|
30
|
+
export declare function applyChangeBatch(root: Root, ownerEffects: readonly OwnerPropertyChange[], structureEffects?: readonly StructureChange[], history?: ChangeHistorySink): boolean;
|
|
29
31
|
export type { StructureChange } from "./structure-change";
|
package/dist/node/element.d.ts
CHANGED
|
@@ -218,6 +218,13 @@ export declare class Element<P extends ElementProperties = ElementProperties, O
|
|
|
218
218
|
private syncOptionEvents;
|
|
219
219
|
/** 属性提交后的派生类扩展点。 */
|
|
220
220
|
protected onPropertiesChanged(_current: P, _changes: PropertyChanges): void;
|
|
221
|
+
/**
|
|
222
|
+
* 作者配置实际变化后的扩展点,在 effective 属性 hook 之后运行。
|
|
223
|
+
* runtime 遮罩不阻止此通知;runtime-only 更新和相同配置不触发。
|
|
224
|
+
* changedKeys 只包含本次实际改变的 configured 字段;通过 configured reader 读取当前值。
|
|
225
|
+
* direct、batch 和 History replay 使用同一阶段;可在此更新当前数据的 runtime 显示。
|
|
226
|
+
*/
|
|
227
|
+
protected onConfiguredPropertiesChanged?(changedKeys: readonly string[]): void;
|
|
221
228
|
/** 把非 geometry impact 路由到绘制、Layer 顺序和 hover 队列。 */
|
|
222
229
|
private invalidate;
|
|
223
230
|
/** 返回在当前元素 local 坐标系中对 children 生效的裁剪区域。 */
|
|
@@ -239,10 +246,10 @@ export declare class Element<P extends ElementProperties = ElementProperties, O
|
|
|
239
246
|
private resolveCurrentConnectionPortProjection;
|
|
240
247
|
/** 直接解析一个当前 Port,不 materialize 其余 Ports。 */
|
|
241
248
|
getConnectionPort(portId: string): ResolvedConnectionPort | undefined;
|
|
242
|
-
/** @internal
|
|
243
|
-
|
|
249
|
+
/** @internal 只解释显式 Port replacement 的 IDs;patch 是同批最终 owner fields。 */
|
|
250
|
+
resolveConnectionPortIds(ports: ConnectionPortConfiguration, patch?: Readonly<Record<string, unknown>>): readonly string[];
|
|
244
251
|
/** 返回元素类型自有的默认 Port;`null` 使用通用四边 Ports。 */
|
|
245
|
-
protected getDefaultConnectionPortSchema(): readonly DerivedConnectionPort[] | null;
|
|
252
|
+
protected getDefaultConnectionPortSchema(_patch?: Readonly<Record<string, unknown>>): readonly DerivedConnectionPort[] | null;
|
|
246
253
|
/** 返回 custom Ports 的当前 decoration slots。 @internal */
|
|
247
254
|
getResolvedConnectionPortSlots(): readonly ResolvedConnectionPortSlot[];
|
|
248
255
|
/**
|
|
@@ -253,12 +260,19 @@ export declare class Element<P extends ElementProperties = ElementProperties, O
|
|
|
253
260
|
getConnectionPortPosition(edge: Edge, ratio: number): PointView;
|
|
254
261
|
/** @internal 一次产出 custom Port position、法线与 label edge 长度。 */
|
|
255
262
|
getConnectionPortGeometry(edge: Edge, ratio: number): ConnectionPortGeometry;
|
|
256
|
-
/**
|
|
263
|
+
/**
|
|
264
|
+
* 将当前配置值填入 caller 提供的 value cells,保留结构化值的原引用。
|
|
265
|
+
* 读取包含默认值的 configured 结果,不读取 runtime 覆盖;保留 null/undefined。
|
|
266
|
+
* cells 可复用;借用值不得原地修改并期待自动提交,需要独立值时由 caller 复制。
|
|
267
|
+
*/
|
|
257
268
|
static readConfiguredPropertyValues(owner: Element, targets: ReadonlyMap<string, {
|
|
258
269
|
value: unknown;
|
|
259
270
|
}>): void;
|
|
260
|
-
/**
|
|
261
|
-
|
|
271
|
+
/**
|
|
272
|
+
* 借用当前字段的 configured/default 值,忽略 runtime 覆盖,保留 null/undefined。
|
|
273
|
+
* 返回结构化原引用,不表示该字段是否曾被显式配置;需要独立值时由 caller 复制。
|
|
274
|
+
*/
|
|
275
|
+
static getConfiguredPropertyValue(owner: Element, key: string): unknown;
|
|
262
276
|
/**
|
|
263
277
|
* 提交需要持久化的配置属性补丁。
|
|
264
278
|
* @param options 要修改的属性;省略时不修改,字段为 `undefined` 时恢复默认值。
|
|
@@ -61,6 +61,8 @@ export interface ReferenceTransformResolution {
|
|
|
61
61
|
* 新几何后把真实 bounds 交回这里,保持 frame world matrix 与目标一致。
|
|
62
62
|
*/
|
|
63
63
|
export declare function resolveAuthoredGeometryFramePatch(baseline: Readonly<Pick<ReferenceTransformBaseline, "referenceBounds" | "frame">>, resolution: Readonly<ReferenceTransformResolution>, authoredBounds: Readonly<Rect>): Readonly<ElementOptionPatch>;
|
|
64
|
+
/** @internal reference bounds 改变时修正 origin 位移,保留给定最终 frame 的仿射。 */
|
|
65
|
+
export declare function resolveReferenceBoundsTranslation(frame: Readonly<ElementOptionPatch>, before: Readonly<Rect>, after: Readonly<Rect>): Readonly<Pick<ElementOptionPatch, "left" | "top">>;
|
|
64
66
|
/** 判断变换意图是否包含跨父级重挂载所需的目标父级矩阵。 */
|
|
65
67
|
export declare function isReparentTransformIntent(intent: Readonly<TransformIntent | ReparentTransformIntent>): intent is Readonly<ReparentTransformIntent>;
|
|
66
68
|
/**
|
package/dist/root/index.d.ts
CHANGED
|
@@ -30,9 +30,9 @@ export declare class Root extends Node<NodeProperties, Layer> {
|
|
|
30
30
|
private skinTextCommitObservers?;
|
|
31
31
|
/** Root 的平移、缩放、DPR 和坐标换算对象。 */
|
|
32
32
|
readonly viewport: Viewport;
|
|
33
|
-
/**
|
|
33
|
+
/** Root 拥有的输入控制器,提供只读查询、交互范围注册和指针操作取消。 */
|
|
34
34
|
readonly input: RootInputController;
|
|
35
|
-
/**
|
|
35
|
+
/** 当前活动节点的只读索引及增量场景订阅。 */
|
|
36
36
|
readonly sceneRegistry: SceneRegistry;
|
|
37
37
|
/** @internal 跨 Layer 帧队列、动画时钟和 nextTick 状态。 */
|
|
38
38
|
readonly frameRuntime: RootFrameRuntime;
|
|
@@ -133,7 +133,7 @@ export declare class Root extends Node<NodeProperties, Layer> {
|
|
|
133
133
|
* 同步应用领域已经决定的 owner/structure effects。
|
|
134
134
|
* 同 owner 只 finalize/install 一次,全部 fields/raw links 安装后统一发布。
|
|
135
135
|
*/
|
|
136
|
-
applyChangeBatch(owners: readonly OwnerPropertyChange[], structure?: readonly StructureChange[], history?: ChangeHistorySink):
|
|
136
|
+
applyChangeBatch(owners: readonly OwnerPropertyChange[], structure?: readonly StructureChange[], history?: ChangeHistorySink): boolean;
|
|
137
137
|
/** 按活动场景中的唯一 key 查询节点;key 来自 `node.key`。 */
|
|
138
138
|
getByKey(key: string): Node | undefined;
|
|
139
139
|
/**
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { Element } from "../node/element";
|
|
2
2
|
import type { Node as SceneNode } from "../node/node";
|
|
3
3
|
import type { Root } from "./index";
|
|
4
|
-
import type {
|
|
4
|
+
import type { PointView } from "@fulate/share";
|
|
5
5
|
/** 判断键盘事件目标是否应保留浏览器原生空格输入。 */
|
|
6
6
|
export declare function isFormControlTarget(target: EventTarget | null): boolean;
|
|
7
7
|
/** Root 拥有的 DOM 输入监听、指针会话和交互范围控制器。 */
|
|
@@ -13,11 +13,11 @@ export declare class RootInputController {
|
|
|
13
13
|
isPanning: boolean;
|
|
14
14
|
/** @internal 是否应在连续指针操作期间暂停 hover 重算。 */
|
|
15
15
|
hasLockPoint: boolean;
|
|
16
|
-
/**
|
|
17
|
-
|
|
16
|
+
/** Input 原地更新的唯一 client 坐标。 */
|
|
17
|
+
private readonly pointerPosition;
|
|
18
18
|
/** 最近一次记录的指针是否位于 Root 容器内。 */
|
|
19
19
|
private pointerInside;
|
|
20
|
-
/**
|
|
20
|
+
/** 当前允许接收元素级指针输入的子树根节点。 */
|
|
21
21
|
private readonly interactionScopes;
|
|
22
22
|
/** 一次 Root 激活周期内全部 DOM listener 的统一清理器。 */
|
|
23
23
|
private abortController;
|
|
@@ -29,7 +29,9 @@ export declare class RootInputController {
|
|
|
29
29
|
private lastClick;
|
|
30
30
|
/** @internal 由 Root 构造;单独实例化不会接入 Root 生命周期。 */
|
|
31
31
|
constructor(root: Root);
|
|
32
|
-
/**
|
|
32
|
+
/** 最近一次 DOM 指针的 clientX/clientY 只读借用;后续输入原地更新同一对象。 */
|
|
33
|
+
get lastPointerPos(): PointView;
|
|
34
|
+
/** Root 当前是否认为指针位于容器内。 */
|
|
33
35
|
get isPointerInside(): boolean;
|
|
34
36
|
/** @internal 安装当前 Root 的键盘、指针、滚轮和焦点监听。 */
|
|
35
37
|
activate(): void;
|
|
@@ -37,13 +39,32 @@ export declare class RootInputController {
|
|
|
37
39
|
deactivate(): void;
|
|
38
40
|
/** @internal 停用控制器并释放全部 interaction scope。 */
|
|
39
41
|
dispose(): void;
|
|
40
|
-
/**
|
|
42
|
+
/**
|
|
43
|
+
* 取消当前指针操作,释放指针捕获与 hover 锁定,并清除连续点击记录。
|
|
44
|
+
*
|
|
45
|
+
* 省略 node 时取消当前场景或空格平移操作。传入所属 Root 内的节点时,
|
|
46
|
+
* 仅取消按下目标为该节点或其后代的场景操作;空白处以 Root 为目标的操作、
|
|
47
|
+
* 空格平移和其他子树的操作不受影响。
|
|
48
|
+
*
|
|
49
|
+
* 场景操作按当前交互范围派发一次 pointercancel,不产生 pointerup 或 click;
|
|
50
|
+
* 平移操作只释放输入状态,保留已经发生的 Viewport 平移。
|
|
51
|
+
*/
|
|
41
52
|
cancelSession(node?: SceneNode): void;
|
|
42
53
|
/** @internal 更新容器内外状态。 */
|
|
43
54
|
setPointerInside(inside: boolean): void;
|
|
44
|
-
/**
|
|
55
|
+
/**
|
|
56
|
+
* 允许所属 Root 内的 scope 及其后代接收元素级指针输入,返回注销函数。
|
|
57
|
+
*
|
|
58
|
+
* 多个范围取并集;没有范围时恢复普通派发。范围外的命中仍作为事件 target
|
|
59
|
+
* 派给 Root,但不进入命中元素的指针、点击、悬停或右键处理器。
|
|
60
|
+
* wheel 仍派给命中元素;范围内事件保留正常冒泡,范围不改变命中查询结果。
|
|
61
|
+
*
|
|
62
|
+
* 调用方负责每个 scope 同时只保留一次注册,并在退出交互或停用时注销;
|
|
63
|
+
* 再次进入时重新注册。注册和注销通过现有帧队列刷新 hover 与 cursor,
|
|
64
|
+
* 不自动取消进行中的指针操作;需要取消时调用 cancelSession(scope)。
|
|
65
|
+
*/
|
|
45
66
|
registerInteractionScope(scope: Element): () => void;
|
|
46
|
-
/**
|
|
67
|
+
/** 判断元素是否属于当前允许交互的子树;无范围限制时为 true,不执行命中或焦点查询。 */
|
|
47
68
|
isInteractionTarget(element: Element): boolean;
|
|
48
69
|
/** Root 容器所属的 Document。 */
|
|
49
70
|
private get ownerDocument();
|
|
@@ -7,23 +7,32 @@ export type NodeRegistrationObserver = (node: Node, registered: boolean) => void
|
|
|
7
7
|
export type SceneChangeObserver = (node?: Node, affected?: readonly Node[]) => void;
|
|
8
8
|
/** 管理活动场景的节点 key 索引和轻量变化观察器。 */
|
|
9
9
|
export declare class SceneRegistry {
|
|
10
|
-
|
|
11
|
-
readonly keyElements: Map<string, Node<import("..").NodeProperties, Node<any, any>>>;
|
|
10
|
+
private readonly nodes;
|
|
12
11
|
/** 按 key 保存观察注册和注销的回调。 */
|
|
13
12
|
private readonly nodeKeyObservers;
|
|
14
13
|
/** 监听结构、geometry 和命中策略变化的回调。 */
|
|
15
14
|
private readonly sceneChangeObservers;
|
|
16
15
|
/** 监听 active registration 的轻量观察器。 */
|
|
17
16
|
private readonly nodeRegistrationObservers;
|
|
18
|
-
/**
|
|
19
|
-
constructor(
|
|
20
|
-
/**
|
|
21
|
-
|
|
22
|
-
|
|
17
|
+
/** @internal 由 Root 创建,拥有当前场景唯一 key 索引。 */
|
|
18
|
+
constructor(nodes?: Map<string, Node<import("..").NodeProperties, Node<any, any>>>);
|
|
19
|
+
/**
|
|
20
|
+
* 当前 active 节点的只读 live 索引;与内部 Map 为同一引用,不创建快照。
|
|
21
|
+
* 初始枚举后可订阅增量变化,后续注册/注销会直接更新此视图。
|
|
22
|
+
*/
|
|
23
|
+
get keyElements(): ReadonlyMap<string, Node>;
|
|
24
|
+
/**
|
|
25
|
+
* 订阅后续场景查询/结构变化,返回退订函数;不补发当前状态。
|
|
26
|
+
* 此通知不代表完整属性变化或帧已稳定;Root 销毁时清除订阅。
|
|
27
|
+
*/
|
|
23
28
|
observeSceneChanges(observer: SceneChangeObserver): () => boolean;
|
|
24
29
|
/** @internal 当前是否存在真实 scene change consumer。 */
|
|
25
30
|
get hasSceneChangeObservers(): boolean;
|
|
26
|
-
/**
|
|
31
|
+
/**
|
|
32
|
+
* 订阅后续节点进入/离开 active 生命周期,返回退订函数;不补发已有节点。
|
|
33
|
+
* 回调时索引与 active 状态已安装;detach/reinsert 分别通知 false/true。
|
|
34
|
+
* Root 销毁时清除订阅。
|
|
35
|
+
*/
|
|
27
36
|
observeNodeRegistrations(observer: NodeRegistrationObserver): () => boolean;
|
|
28
37
|
/** @internal 通知场景观察器;node 省略时表示整批变化。 */
|
|
29
38
|
notifySceneChange(node?: Node, affected?: readonly Node[]): void;
|