@tutti-os/workbench-surface 0.0.207 → 0.0.209
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/README.md +6 -0
- package/dist/index.d.ts +5 -3
- package/dist/index.js +247 -59
- package/dist/index.js.map +1 -1
- package/package.json +5 -5
package/README.md
CHANGED
|
@@ -149,6 +149,12 @@ Layout rules:
|
|
|
149
149
|
- fullscreen nodes respect top, left, and right safe area, but ignore bottom
|
|
150
150
|
safe area so immersive content can reach the bottom edge of the workbench
|
|
151
151
|
surface
|
|
152
|
+
- persisted snapshots record the surface and layout constraints that produced
|
|
153
|
+
their frames; initial restore maps node frames, fullscreen restore frames,
|
|
154
|
+
space frames, and reusable closed-window frames into the current safe layout
|
|
155
|
+
- legacy snapshots without a layout basis remain readable; fullscreen geometry
|
|
156
|
+
is recomputed and hidden restore frames are clamped before they become
|
|
157
|
+
floating windows
|
|
152
158
|
|
|
153
159
|
The package ships a baseline host layout default so new integrations do not
|
|
154
160
|
start with windows tucked under shared chrome. Today that default uses:
|
package/dist/index.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { WorkbenchFrame as WorkbenchFrame$1, WorkbenchSnapshotDisplayModeV1, WorkbenchSnapshot, WorkbenchSnapshotNode } from '@tutti-os/workbench-snapshot';
|
|
1
|
+
import { WorkbenchFrame as WorkbenchFrame$1, WorkbenchSnapshotDisplayModeV1, WorkbenchSnapshot, WorkbenchSnapshotNode, WorkbenchSnapshotLayoutBasisV1 } from '@tutti-os/workbench-snapshot';
|
|
2
2
|
import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
3
3
|
import { HTMLAttributes, ReactNode, CSSProperties } from 'react';
|
|
4
4
|
import { I18nRuntime } from '@tutti-os/ui-i18n-runtime';
|
|
@@ -234,6 +234,7 @@ interface WorkbenchController<TData = unknown> extends WorkbenchStore<TData> {
|
|
|
234
234
|
|
|
235
235
|
declare function createWorkbenchController<TData = unknown>(initialState?: Partial<WorkbenchState<TData>>, options?: {
|
|
236
236
|
debugDiagnostics?: WorkbenchDebugDiagnostics;
|
|
237
|
+
onSurfaceSizeMeasured?: () => void;
|
|
237
238
|
}): WorkbenchController<TData>;
|
|
238
239
|
|
|
239
240
|
type WorkbenchMissionControlMode = "activate" | "layout";
|
|
@@ -916,7 +917,8 @@ interface CreateWorkbenchSnapshotFromStateOptions {
|
|
|
916
917
|
declare function createWorkbenchNode<TData = unknown>(input: CreateWorkbenchNodeInput<TData>): WorkbenchNode<TData>;
|
|
917
918
|
declare function createWorkbenchNodeFromSnapshot<TData = unknown>(snapshotNode: WorkbenchSnapshotNode): WorkbenchNode<TData>;
|
|
918
919
|
declare function createWorkbenchStateFromSnapshot<TData = unknown>(snapshot: WorkbenchSnapshot): Pick<WorkbenchState<TData>, "nodeStack" | "nodes">;
|
|
919
|
-
declare function createWorkbenchSnapshotFromState<TData = unknown>(state: Pick<WorkbenchState<TData>, "nodeStack" | "nodes">, options?: CreateWorkbenchSnapshotFromStateOptions): WorkbenchSnapshot;
|
|
920
|
+
declare function createWorkbenchSnapshotFromState<TData = unknown>(state: Pick<WorkbenchState<TData>, "nodeStack" | "nodes"> & Partial<Pick<WorkbenchState<TData>, "layoutConstraints" | "surfaceSize">>, options?: CreateWorkbenchSnapshotFromStateOptions): WorkbenchSnapshot;
|
|
921
|
+
declare function createWorkbenchSnapshotLayoutBasis(state: Partial<Pick<WorkbenchState, "layoutConstraints" | "surfaceSize">>): WorkbenchSnapshotLayoutBasisV1 | undefined;
|
|
920
922
|
|
|
921
923
|
interface WorkbenchHostNodeIdentityInput {
|
|
922
924
|
instanceId: string;
|
|
@@ -980,4 +982,4 @@ interface CreateMultiInstanceDockEntryOptionsInput {
|
|
|
980
982
|
declare function createMultiInstanceDockEntryOptions(launchPayload?: unknown, input?: CreateMultiInstanceDockEntryOptionsInput): Pick<WorkbenchHostDockEntry, "allowNewWindowInDockPopup" | "instanceMode" | "launchBehavior" | "launchPayload" | "newWindowLaunchPayload">;
|
|
981
983
|
declare function resolveWorkbenchDockCountBadge(activeNodeCount: number): WorkbenchHostDockEntry["badge"];
|
|
982
984
|
|
|
983
|
-
export { type CreateWorkbenchNodeInput, type CreateWorkbenchSnapshotFromStateOptions, type ResolvedWorkbenchHostDockEntry, type WorkbenchContribution, type WorkbenchController, type WorkbenchDebugDiagnostics, type WorkbenchDisplayMode, WorkbenchDockComponentPreviewFrame, type WorkbenchDockComponentPreviewFrameProps, type WorkbenchDockContext, type WorkbenchDockPlacement, type WorkbenchDockPreviewCache, type WorkbenchDockPreviewCacheKey, type WorkbenchDockPreviewCacheKeyResolver, type WorkbenchDockPreviewContent, type WorkbenchFrame, type WorkbenchFullscreenHeaderMode, WorkbenchHost, type WorkbenchHostActivation, type WorkbenchHostActivationTarget, type WorkbenchHostChromeRenderContext, type WorkbenchHostCloseDialogRequest, type WorkbenchHostCloseDialogScope, type WorkbenchHostCloseDialogVariant, type WorkbenchHostCloseEffect, type WorkbenchHostClosePreparationContext, type WorkbenchHostClosePreparer, type WorkbenchHostDockClickResolution, type WorkbenchHostDockEntry, type WorkbenchHostDockEntryAction, type WorkbenchHostDockEntryBadge, type WorkbenchHostDockEntryDynamicState, type WorkbenchHostDockEntryLaunchBehavior, type WorkbenchHostDockEntryPresentationOverride, type WorkbenchHostDockEntryPresentationOverrides, type WorkbenchHostDockEntryState, type WorkbenchHostDockEntryStateKind, type WorkbenchHostDockEntryStateSource, type WorkbenchHostDockEntryVisibility, type WorkbenchHostDockNodeState, type WorkbenchHostDockPopupItemDescriptor, type WorkbenchHostDockPopupItemInput, type WorkbenchHostExternalStateLookupInput, type WorkbenchHostExternalStateSource, type WorkbenchHostHandle, type WorkbenchHostLaunchFramePolicy, type WorkbenchHostLaunchInput, type WorkbenchHostLaunchReason, type WorkbenchHostLaunchRequest, type WorkbenchHostLaunchResult, type WorkbenchHostMissionControlMode, type WorkbenchHostMissionControlProps, type WorkbenchHostMultiInstanceStrategy, type WorkbenchHostNodeBodyContext, type WorkbenchHostNodeCloseDecision, type WorkbenchHostNodeCloseRequest, type WorkbenchHostNodeData, type WorkbenchHostNodeDefinition, type WorkbenchHostNodeHeaderContext, type WorkbenchHostNodeHeaderFrameRenderKey, type WorkbenchHostNodeHeaderWindowActions, type WorkbenchHostNodeIdentityInput, type WorkbenchHostNodeInstanceStrategy, type WorkbenchHostNodeMinimizedDockCapability, type WorkbenchHostNodeWindowCapabilities, type WorkbenchHostProjectedNode, type WorkbenchHostProjectedNodeSubject, type WorkbenchHostProps, type WorkbenchHostSingleInstanceStrategy, type WorkbenchHostSnapshotRepository, type WorkbenchHostWindowCloseEffectContext, type WorkbenchLayoutConstraints, type WorkbenchLayoutConstraintsInput, type WorkbenchLayoutPreset, type WorkbenchMissionControlAdapter, type WorkbenchMissionControlMode, type WorkbenchMissionControlSnapshot, type WorkbenchNode, type WorkbenchNodeRenderFrame, type WorkbenchNodeSizeConstraints, type WorkbenchQuickLayoutTarget, type WorkbenchRenderNode, type WorkbenchRenderNodeContext, type WorkbenchRenderWindowActions, type WorkbenchRenderWindowHeader, type WorkbenchResolveFullscreenHeaderMode, type WorkbenchResolveWindowChromeMode, type WorkbenchResolveWindowChromeModeContext, type WorkbenchResolveWindowHeaderPresentation, type WorkbenchSafeArea, type WorkbenchSize, type WorkbenchState, WorkbenchSurface, type WorkbenchSurfacePresentation, type WorkbenchSurfaceProps, type WorkbenchSurfaceWallpaper, type WorkbenchSurfaceWallpaperFit, type WorkbenchWindowActionContext, WorkbenchWindowChromeI18nRuntime, type WorkbenchWindowChromeMode, type WorkbenchWindowHeaderContext, type WorkbenchWindowHeaderPresentation, type WorkbenchWindowManagementConfig, canCreateNewWindow, canCreateNewWindowInDockPopup, createDockNewWindowLaunchPayload, createMultiInstanceDockEntryOptions, createWorkbenchController, createWorkbenchHostLaunchedNodeId, createWorkbenchHostProjectedNodeId, createWorkbenchNode, createWorkbenchNodeFromSnapshot, createWorkbenchSnapshotFromState, createWorkbenchStateFromSnapshot, getWorkbenchLayoutFrame, isEditableShortcutTarget, matchWorkbenchDockEntryNode, resolveWorkbenchDockCountBadge, resolveWorkbenchDockEntries, resolveWorkbenchDockEntryClick, resolveWorkbenchHostPrepareClose, selectFocusedWorkbenchNode, useWorkbenchSelector, workbenchFocusInputActivationType };
|
|
985
|
+
export { type CreateWorkbenchNodeInput, type CreateWorkbenchSnapshotFromStateOptions, type ResolvedWorkbenchHostDockEntry, type WorkbenchContribution, type WorkbenchController, type WorkbenchDebugDiagnostics, type WorkbenchDisplayMode, WorkbenchDockComponentPreviewFrame, type WorkbenchDockComponentPreviewFrameProps, type WorkbenchDockContext, type WorkbenchDockPlacement, type WorkbenchDockPreviewCache, type WorkbenchDockPreviewCacheKey, type WorkbenchDockPreviewCacheKeyResolver, type WorkbenchDockPreviewContent, type WorkbenchFrame, type WorkbenchFullscreenHeaderMode, WorkbenchHost, type WorkbenchHostActivation, type WorkbenchHostActivationTarget, type WorkbenchHostChromeRenderContext, type WorkbenchHostCloseDialogRequest, type WorkbenchHostCloseDialogScope, type WorkbenchHostCloseDialogVariant, type WorkbenchHostCloseEffect, type WorkbenchHostClosePreparationContext, type WorkbenchHostClosePreparer, type WorkbenchHostDockClickResolution, type WorkbenchHostDockEntry, type WorkbenchHostDockEntryAction, type WorkbenchHostDockEntryBadge, type WorkbenchHostDockEntryDynamicState, type WorkbenchHostDockEntryLaunchBehavior, type WorkbenchHostDockEntryPresentationOverride, type WorkbenchHostDockEntryPresentationOverrides, type WorkbenchHostDockEntryState, type WorkbenchHostDockEntryStateKind, type WorkbenchHostDockEntryStateSource, type WorkbenchHostDockEntryVisibility, type WorkbenchHostDockNodeState, type WorkbenchHostDockPopupItemDescriptor, type WorkbenchHostDockPopupItemInput, type WorkbenchHostExternalStateLookupInput, type WorkbenchHostExternalStateSource, type WorkbenchHostHandle, type WorkbenchHostLaunchFramePolicy, type WorkbenchHostLaunchInput, type WorkbenchHostLaunchReason, type WorkbenchHostLaunchRequest, type WorkbenchHostLaunchResult, type WorkbenchHostMissionControlMode, type WorkbenchHostMissionControlProps, type WorkbenchHostMultiInstanceStrategy, type WorkbenchHostNodeBodyContext, type WorkbenchHostNodeCloseDecision, type WorkbenchHostNodeCloseRequest, type WorkbenchHostNodeData, type WorkbenchHostNodeDefinition, type WorkbenchHostNodeHeaderContext, type WorkbenchHostNodeHeaderFrameRenderKey, type WorkbenchHostNodeHeaderWindowActions, type WorkbenchHostNodeIdentityInput, type WorkbenchHostNodeInstanceStrategy, type WorkbenchHostNodeMinimizedDockCapability, type WorkbenchHostNodeWindowCapabilities, type WorkbenchHostProjectedNode, type WorkbenchHostProjectedNodeSubject, type WorkbenchHostProps, type WorkbenchHostSingleInstanceStrategy, type WorkbenchHostSnapshotRepository, type WorkbenchHostWindowCloseEffectContext, type WorkbenchLayoutConstraints, type WorkbenchLayoutConstraintsInput, type WorkbenchLayoutPreset, type WorkbenchMissionControlAdapter, type WorkbenchMissionControlMode, type WorkbenchMissionControlSnapshot, type WorkbenchNode, type WorkbenchNodeRenderFrame, type WorkbenchNodeSizeConstraints, type WorkbenchQuickLayoutTarget, type WorkbenchRenderNode, type WorkbenchRenderNodeContext, type WorkbenchRenderWindowActions, type WorkbenchRenderWindowHeader, type WorkbenchResolveFullscreenHeaderMode, type WorkbenchResolveWindowChromeMode, type WorkbenchResolveWindowChromeModeContext, type WorkbenchResolveWindowHeaderPresentation, type WorkbenchSafeArea, type WorkbenchSize, type WorkbenchState, WorkbenchSurface, type WorkbenchSurfacePresentation, type WorkbenchSurfaceProps, type WorkbenchSurfaceWallpaper, type WorkbenchSurfaceWallpaperFit, type WorkbenchWindowActionContext, WorkbenchWindowChromeI18nRuntime, type WorkbenchWindowChromeMode, type WorkbenchWindowHeaderContext, type WorkbenchWindowHeaderPresentation, type WorkbenchWindowManagementConfig, canCreateNewWindow, canCreateNewWindowInDockPopup, createDockNewWindowLaunchPayload, createMultiInstanceDockEntryOptions, createWorkbenchController, createWorkbenchHostLaunchedNodeId, createWorkbenchHostProjectedNodeId, createWorkbenchNode, createWorkbenchNodeFromSnapshot, createWorkbenchSnapshotFromState, createWorkbenchSnapshotLayoutBasis, createWorkbenchStateFromSnapshot, getWorkbenchLayoutFrame, isEditableShortcutTarget, matchWorkbenchDockEntryNode, resolveWorkbenchDockCountBadge, resolveWorkbenchDockEntries, resolveWorkbenchDockEntryClick, resolveWorkbenchHostPrepareClose, selectFocusedWorkbenchNode, useWorkbenchSelector, workbenchFocusInputActivationType };
|
package/dist/index.js
CHANGED
|
@@ -776,7 +776,12 @@ function reduceWorkbenchState(state, action) {
|
|
|
776
776
|
return {
|
|
777
777
|
...node,
|
|
778
778
|
displayMode: "floating",
|
|
779
|
-
frame:
|
|
779
|
+
frame: clampWorkbenchRect(
|
|
780
|
+
node.restoreFrame ?? node.frame,
|
|
781
|
+
state.surfaceSize,
|
|
782
|
+
state.layoutConstraints,
|
|
783
|
+
node.sizeConstraints
|
|
784
|
+
),
|
|
780
785
|
restoreFrame: null
|
|
781
786
|
};
|
|
782
787
|
});
|
|
@@ -1427,14 +1432,21 @@ function createWorkbenchStore(initialState = {}, options = {}) {
|
|
|
1427
1432
|
dispatch(action) {
|
|
1428
1433
|
const nextState = reduceWorkbenchState(state, action);
|
|
1429
1434
|
if (nextState === state) {
|
|
1435
|
+
notifySurfaceSizeMeasured(action, options);
|
|
1430
1436
|
return;
|
|
1431
1437
|
}
|
|
1432
1438
|
logWorkbenchFrameChanges(action, state, nextState, options);
|
|
1433
1439
|
state = nextState;
|
|
1434
1440
|
subscriptions.notify();
|
|
1441
|
+
notifySurfaceSizeMeasured(action, options);
|
|
1435
1442
|
}
|
|
1436
1443
|
};
|
|
1437
1444
|
}
|
|
1445
|
+
function notifySurfaceSizeMeasured(action, options) {
|
|
1446
|
+
if (action.type === "setSurfaceSize") {
|
|
1447
|
+
options.onSurfaceSizeMeasured?.();
|
|
1448
|
+
}
|
|
1449
|
+
}
|
|
1438
1450
|
function logWorkbenchFrameChanges(action, previousState, nextState, options) {
|
|
1439
1451
|
if (!options.debugDiagnostics?.isEnabled()) {
|
|
1440
1452
|
return;
|
|
@@ -6016,9 +6028,25 @@ function createWorkbenchSnapshotFromState(state, options = {}) {
|
|
|
6016
6028
|
activeNodeId: state.nodeStack.at(-1) ?? null,
|
|
6017
6029
|
spaces: options.spaces,
|
|
6018
6030
|
activeSpaceId: options.activeSpaceId,
|
|
6031
|
+
layoutBasis: createWorkbenchSnapshotLayoutBasis(state),
|
|
6019
6032
|
metadata: options.metadata
|
|
6020
6033
|
});
|
|
6021
6034
|
}
|
|
6035
|
+
function createWorkbenchSnapshotLayoutBasis(state) {
|
|
6036
|
+
if (!state.surfaceSize || !state.layoutConstraints || !isPositiveFinite(state.surfaceSize.width) || !isPositiveFinite(state.surfaceSize.height)) {
|
|
6037
|
+
return void 0;
|
|
6038
|
+
}
|
|
6039
|
+
return {
|
|
6040
|
+
surfaceSize: { ...state.surfaceSize },
|
|
6041
|
+
layoutConstraints: {
|
|
6042
|
+
...state.layoutConstraints,
|
|
6043
|
+
safeArea: { ...state.layoutConstraints.safeArea }
|
|
6044
|
+
}
|
|
6045
|
+
};
|
|
6046
|
+
}
|
|
6047
|
+
function isPositiveFinite(value) {
|
|
6048
|
+
return Number.isFinite(value) && value > 0;
|
|
6049
|
+
}
|
|
6022
6050
|
|
|
6023
6051
|
// src/core/placement.ts
|
|
6024
6052
|
var WORKBENCH_WINDOW_CASCADE_OFFSET = 28;
|
|
@@ -6417,50 +6445,6 @@ function resolveCompactWorkbenchPreferredFrame(input) {
|
|
|
6417
6445
|
input.sizeConstraints
|
|
6418
6446
|
);
|
|
6419
6447
|
}
|
|
6420
|
-
function compactRestoredWorkbenchHostNodes(input) {
|
|
6421
|
-
if (!shouldUseCompactWorkbenchFrame(input.surfaceSize)) {
|
|
6422
|
-
return [...input.nodes];
|
|
6423
|
-
}
|
|
6424
|
-
return input.nodes.map((node) => {
|
|
6425
|
-
const sizeConstraints = node.sizeConstraints ?? input.nodeDefinitionByType.get(node.data.typeId)?.sizeConstraints ?? null;
|
|
6426
|
-
if (node.displayMode === "fullscreen") {
|
|
6427
|
-
return {
|
|
6428
|
-
...node,
|
|
6429
|
-
frame: getWorkbenchFullscreenRect(
|
|
6430
|
-
input.surfaceSize,
|
|
6431
|
-
input.constraints,
|
|
6432
|
-
sizeConstraints
|
|
6433
|
-
)
|
|
6434
|
-
};
|
|
6435
|
-
}
|
|
6436
|
-
const defaultFrame = input.nodeDefinitionByType.get(node.data.typeId)?.frame ?? node.frame;
|
|
6437
|
-
const compactWidth = Math.round(
|
|
6438
|
-
defaultFrame.width * COMPACT_LAUNCH_FRAME_SCALE
|
|
6439
|
-
);
|
|
6440
|
-
const compactHeight = Math.round(
|
|
6441
|
-
defaultFrame.height * COMPACT_LAUNCH_FRAME_SCALE
|
|
6442
|
-
);
|
|
6443
|
-
const width = Math.min(node.frame.width, compactWidth);
|
|
6444
|
-
const height = Math.min(node.frame.height, compactHeight);
|
|
6445
|
-
const sizeChanged = width !== node.frame.width || height !== node.frame.height;
|
|
6446
|
-
const layoutFrame = getWorkbenchLayoutFrame(
|
|
6447
|
-
input.surfaceSize,
|
|
6448
|
-
input.constraints
|
|
6449
|
-
);
|
|
6450
|
-
const frame = clampWorkbenchRect(
|
|
6451
|
-
sizeChanged ? {
|
|
6452
|
-
height,
|
|
6453
|
-
width,
|
|
6454
|
-
x: Math.round(layoutFrame.x + (layoutFrame.width - width) / 2),
|
|
6455
|
-
y: Math.round(layoutFrame.y + (layoutFrame.height - height) / 2)
|
|
6456
|
-
} : node.frame,
|
|
6457
|
-
input.surfaceSize,
|
|
6458
|
-
input.constraints,
|
|
6459
|
-
sizeConstraints
|
|
6460
|
-
);
|
|
6461
|
-
return rectsEqual(node.frame, frame) ? node : { ...node, frame };
|
|
6462
|
-
});
|
|
6463
|
-
}
|
|
6464
6448
|
function shouldUseCompactWorkbenchFrame(surfaceSize) {
|
|
6465
6449
|
return surfaceSize.width < COMPACT_LAUNCH_WIDTH_THRESHOLD;
|
|
6466
6450
|
}
|
|
@@ -6469,6 +6453,7 @@ function createProjectedNodeID(typeId, instanceId) {
|
|
|
6469
6453
|
}
|
|
6470
6454
|
function persistedWorkbenchState(state, nodeDefinitionByType) {
|
|
6471
6455
|
return {
|
|
6456
|
+
layoutConstraints: state.layoutConstraints,
|
|
6472
6457
|
nodeStack: state.nodeStack,
|
|
6473
6458
|
nodes: state.nodes.filter((node) => {
|
|
6474
6459
|
return nodeDefinitionByType.get(node.data.typeId)?.window?.persists !== false;
|
|
@@ -6482,7 +6467,8 @@ function persistedWorkbenchState(state, nodeDefinitionByType) {
|
|
|
6482
6467
|
...node.data.isProjected === true ? { isProjected: true } : {},
|
|
6483
6468
|
typeId: node.data.typeId
|
|
6484
6469
|
}
|
|
6485
|
-
}))
|
|
6470
|
+
})),
|
|
6471
|
+
surfaceSize: state.surfaceSize
|
|
6486
6472
|
};
|
|
6487
6473
|
}
|
|
6488
6474
|
function stateFromSnapshotOrDefinitions(snapshot, nodeDefinitions, projectedNodes = []) {
|
|
@@ -6771,6 +6757,174 @@ function projectedSubjectsEqual(left, right) {
|
|
|
6771
6757
|
return left?.id === right?.id && left?.type === right?.type;
|
|
6772
6758
|
}
|
|
6773
6759
|
|
|
6760
|
+
// src/core/snapshotLayout.ts
|
|
6761
|
+
function restoreWorkbenchFrameToLayout(input) {
|
|
6762
|
+
const sourceLayoutBasis = input.sourceLayoutBasis;
|
|
6763
|
+
if (!sourceLayoutBasis) {
|
|
6764
|
+
return normalizeRestoredFrame(
|
|
6765
|
+
clampWorkbenchRect(
|
|
6766
|
+
input.frame,
|
|
6767
|
+
input.targetSurfaceSize,
|
|
6768
|
+
input.targetLayoutConstraints,
|
|
6769
|
+
input.sizeConstraints
|
|
6770
|
+
)
|
|
6771
|
+
);
|
|
6772
|
+
}
|
|
6773
|
+
const sourceLayoutRect = getWorkbenchSafeLayoutRect(
|
|
6774
|
+
sourceLayoutBasis.surfaceSize,
|
|
6775
|
+
sourceLayoutBasis.layoutConstraints
|
|
6776
|
+
);
|
|
6777
|
+
const targetLayoutRect = getWorkbenchSafeLayoutRect(
|
|
6778
|
+
input.targetSurfaceSize,
|
|
6779
|
+
input.targetLayoutConstraints
|
|
6780
|
+
);
|
|
6781
|
+
const normalizedFrame = normalizeWorkbenchFrameToRect(
|
|
6782
|
+
input.frame,
|
|
6783
|
+
sourceLayoutRect
|
|
6784
|
+
);
|
|
6785
|
+
const restoredFrame = denormalizeWorkbenchFrameFromRect(
|
|
6786
|
+
normalizedFrame,
|
|
6787
|
+
targetLayoutRect
|
|
6788
|
+
);
|
|
6789
|
+
return normalizeRestoredFrame(
|
|
6790
|
+
clampWorkbenchRect(
|
|
6791
|
+
restoredFrame,
|
|
6792
|
+
input.targetSurfaceSize,
|
|
6793
|
+
input.targetLayoutConstraints,
|
|
6794
|
+
input.sizeConstraints
|
|
6795
|
+
)
|
|
6796
|
+
);
|
|
6797
|
+
}
|
|
6798
|
+
function normalizeRestoredFrame(frame) {
|
|
6799
|
+
return {
|
|
6800
|
+
x: normalizeCoordinate(frame.x),
|
|
6801
|
+
y: normalizeCoordinate(frame.y),
|
|
6802
|
+
width: normalizeCoordinate(frame.width),
|
|
6803
|
+
height: normalizeCoordinate(frame.height)
|
|
6804
|
+
};
|
|
6805
|
+
}
|
|
6806
|
+
function normalizeCoordinate(value) {
|
|
6807
|
+
const normalized = Number(value.toFixed(3));
|
|
6808
|
+
return Object.is(normalized, -0) ? 0 : normalized;
|
|
6809
|
+
}
|
|
6810
|
+
|
|
6811
|
+
// src/host/snapshotLayout.ts
|
|
6812
|
+
function restoreWorkbenchHostNodesToSurface(input) {
|
|
6813
|
+
const persistedNodeById = new Map(
|
|
6814
|
+
input.persistedNodes?.map((node) => [node.id, node])
|
|
6815
|
+
);
|
|
6816
|
+
return input.nodes.map((node) => {
|
|
6817
|
+
const persistedNode = persistedNodeById.get(node.id);
|
|
6818
|
+
const sourceNode = persistedNode ? {
|
|
6819
|
+
...node,
|
|
6820
|
+
frame: persistedNode.frame,
|
|
6821
|
+
restoreFrame: persistedNode.restoreFrame ?? null
|
|
6822
|
+
} : node;
|
|
6823
|
+
return restoreNodeToSurface(sourceNode, input);
|
|
6824
|
+
});
|
|
6825
|
+
}
|
|
6826
|
+
function restoreWorkbenchHostSpacesToSurface(input) {
|
|
6827
|
+
return input.spaces?.map((space) => {
|
|
6828
|
+
if (!space.frame) {
|
|
6829
|
+
return space;
|
|
6830
|
+
}
|
|
6831
|
+
const frame = restoreWorkbenchFrameToLayout({
|
|
6832
|
+
frame: space.frame,
|
|
6833
|
+
sourceLayoutBasis: input.layoutBasis,
|
|
6834
|
+
targetLayoutConstraints: input.constraints,
|
|
6835
|
+
targetSurfaceSize: input.surfaceSize
|
|
6836
|
+
});
|
|
6837
|
+
return rectsEqual(space.frame, frame) ? space : { ...space, frame };
|
|
6838
|
+
});
|
|
6839
|
+
}
|
|
6840
|
+
function restoreClosedDockWindowFrameEntriesToSurface(input) {
|
|
6841
|
+
const restoredEntries = /* @__PURE__ */ new Map();
|
|
6842
|
+
for (const entry of input.entries) {
|
|
6843
|
+
const definition = input.nodeDefinitionByType.get(entry.typeId);
|
|
6844
|
+
const restoredEntry = {
|
|
6845
|
+
...entry,
|
|
6846
|
+
frame: restoreWorkbenchFrameToLayout({
|
|
6847
|
+
frame: entry.frame,
|
|
6848
|
+
sourceLayoutBasis: input.layoutBasis,
|
|
6849
|
+
targetLayoutConstraints: input.constraints,
|
|
6850
|
+
targetSurfaceSize: input.surfaceSize,
|
|
6851
|
+
sizeConstraints: definition?.sizeConstraints
|
|
6852
|
+
})
|
|
6853
|
+
};
|
|
6854
|
+
restoredEntries.set(
|
|
6855
|
+
closedDockWindowFrameEntryKey(restoredEntry),
|
|
6856
|
+
restoredEntry
|
|
6857
|
+
);
|
|
6858
|
+
}
|
|
6859
|
+
return restoredEntries;
|
|
6860
|
+
}
|
|
6861
|
+
function restoreNodeToSurface(node, input) {
|
|
6862
|
+
const sizeConstraints = node.sizeConstraints ?? input.nodeDefinitionByType.get(node.data.typeId)?.sizeConstraints ?? null;
|
|
6863
|
+
const restoreFrame = node.restoreFrame ? restoreWorkbenchFrameToLayout({
|
|
6864
|
+
frame: node.restoreFrame,
|
|
6865
|
+
sourceLayoutBasis: input.layoutBasis,
|
|
6866
|
+
targetLayoutConstraints: input.constraints,
|
|
6867
|
+
targetSurfaceSize: input.surfaceSize,
|
|
6868
|
+
sizeConstraints
|
|
6869
|
+
}) : null;
|
|
6870
|
+
if (node.displayMode === "fullscreen") {
|
|
6871
|
+
const frame2 = getWorkbenchFullscreenRect(
|
|
6872
|
+
input.surfaceSize,
|
|
6873
|
+
input.constraints,
|
|
6874
|
+
sizeConstraints
|
|
6875
|
+
);
|
|
6876
|
+
return rectsEqual(node.frame, frame2) && nullableRectsEqual(node.restoreFrame, restoreFrame) ? node : { ...node, frame: frame2, restoreFrame };
|
|
6877
|
+
}
|
|
6878
|
+
if (input.layoutBasis) {
|
|
6879
|
+
const frame2 = restoreWorkbenchFrameToLayout({
|
|
6880
|
+
frame: node.frame,
|
|
6881
|
+
sourceLayoutBasis: input.layoutBasis,
|
|
6882
|
+
targetLayoutConstraints: input.constraints,
|
|
6883
|
+
targetSurfaceSize: input.surfaceSize,
|
|
6884
|
+
sizeConstraints
|
|
6885
|
+
});
|
|
6886
|
+
return rectsEqual(node.frame, frame2) && nullableRectsEqual(node.restoreFrame, restoreFrame) ? node : { ...node, frame: frame2, restoreFrame };
|
|
6887
|
+
}
|
|
6888
|
+
if (input.surfaceSize.width >= COMPACT_LAUNCH_WIDTH_THRESHOLD) {
|
|
6889
|
+
const frame2 = clampWorkbenchRect(
|
|
6890
|
+
node.frame,
|
|
6891
|
+
input.surfaceSize,
|
|
6892
|
+
input.constraints,
|
|
6893
|
+
sizeConstraints
|
|
6894
|
+
);
|
|
6895
|
+
return rectsEqual(node.frame, frame2) && nullableRectsEqual(node.restoreFrame, restoreFrame) ? node : { ...node, frame: frame2, restoreFrame };
|
|
6896
|
+
}
|
|
6897
|
+
const defaultFrame = input.nodeDefinitionByType.get(node.data.typeId)?.frame ?? node.frame;
|
|
6898
|
+
const compactWidth = Math.round(
|
|
6899
|
+
defaultFrame.width * COMPACT_LAUNCH_FRAME_SCALE
|
|
6900
|
+
);
|
|
6901
|
+
const compactHeight = Math.round(
|
|
6902
|
+
defaultFrame.height * COMPACT_LAUNCH_FRAME_SCALE
|
|
6903
|
+
);
|
|
6904
|
+
const width = Math.min(node.frame.width, compactWidth);
|
|
6905
|
+
const height = Math.min(node.frame.height, compactHeight);
|
|
6906
|
+
const sizeChanged = width !== node.frame.width || height !== node.frame.height;
|
|
6907
|
+
const layoutFrame = getWorkbenchLayoutFrame(
|
|
6908
|
+
input.surfaceSize,
|
|
6909
|
+
input.constraints
|
|
6910
|
+
);
|
|
6911
|
+
const frame = clampWorkbenchRect(
|
|
6912
|
+
sizeChanged ? {
|
|
6913
|
+
height,
|
|
6914
|
+
width,
|
|
6915
|
+
x: Math.round(layoutFrame.x + (layoutFrame.width - width) / 2),
|
|
6916
|
+
y: Math.round(layoutFrame.y + (layoutFrame.height - height) / 2)
|
|
6917
|
+
} : node.frame,
|
|
6918
|
+
input.surfaceSize,
|
|
6919
|
+
input.constraints,
|
|
6920
|
+
sizeConstraints
|
|
6921
|
+
);
|
|
6922
|
+
return rectsEqual(node.frame, frame) && nullableRectsEqual(node.restoreFrame, restoreFrame) ? node : { ...node, frame, restoreFrame };
|
|
6923
|
+
}
|
|
6924
|
+
function nullableRectsEqual(left, right) {
|
|
6925
|
+
return left === right || left !== null && right !== null && rectsEqual(left, right);
|
|
6926
|
+
}
|
|
6927
|
+
|
|
6774
6928
|
// src/host/externalState.ts
|
|
6775
6929
|
import { useCallback as useCallback9, useMemo as useMemo7, useSyncExternalStore } from "react";
|
|
6776
6930
|
var noopSubscribe = () => () => {
|
|
@@ -6863,6 +7017,7 @@ function sanitizeWorkbenchHostSnapshot(snapshot) {
|
|
|
6863
7017
|
activeNodeId: normalized.activeNodeId,
|
|
6864
7018
|
spaces: normalized.spaces?.map(sanitizeSpace),
|
|
6865
7019
|
activeSpaceId: normalized.activeSpaceId,
|
|
7020
|
+
layoutBasis: normalized.layoutBasis,
|
|
6866
7021
|
metadata: sanitizeMetadata(normalized.metadata)
|
|
6867
7022
|
});
|
|
6868
7023
|
}
|
|
@@ -6940,7 +7095,7 @@ var WorkbenchHostSessionController = class {
|
|
|
6940
7095
|
loadPromise = null;
|
|
6941
7096
|
nodeLeases = /* @__PURE__ */ new Map();
|
|
6942
7097
|
nextActivationSequence = 1;
|
|
6943
|
-
|
|
7098
|
+
hasAppliedInitialRestoredLayout = false;
|
|
6944
7099
|
hasReceivedSurfaceSize = false;
|
|
6945
7100
|
observedSurfaceSize = null;
|
|
6946
7101
|
pendingProjectedNodeReconciliation = false;
|
|
@@ -6973,17 +7128,23 @@ var WorkbenchHostSessionController = class {
|
|
|
6973
7128
|
this.nodeDefinitions,
|
|
6974
7129
|
this.projectedNodes
|
|
6975
7130
|
),
|
|
6976
|
-
{
|
|
7131
|
+
{
|
|
7132
|
+
debugDiagnostics: input.debugDiagnostics,
|
|
7133
|
+
onSurfaceSizeMeasured: () => {
|
|
7134
|
+
this.hasReceivedSurfaceSize = true;
|
|
7135
|
+
this.applyInitialRestoredLayout();
|
|
7136
|
+
}
|
|
7137
|
+
}
|
|
6977
7138
|
);
|
|
6978
7139
|
this.observedSurfaceSize = this.controller.getSnapshot().surfaceSize;
|
|
6979
7140
|
this.leaseUnsubscribe = this.controller.subscribe(() => {
|
|
6980
7141
|
this.noteSurfaceSizeChange();
|
|
6981
7142
|
this.reconcileNodeLeases();
|
|
6982
|
-
this.
|
|
7143
|
+
this.applyInitialRestoredLayout();
|
|
6983
7144
|
});
|
|
6984
7145
|
this.isSnapshotLoaded = this.loadedSnapshot !== null;
|
|
6985
7146
|
if (this.isSnapshotLoaded) {
|
|
6986
|
-
this.
|
|
7147
|
+
this.applyInitialRestoredLayout();
|
|
6987
7148
|
this.subscribeToPersistence();
|
|
6988
7149
|
}
|
|
6989
7150
|
}
|
|
@@ -7182,6 +7343,7 @@ var WorkbenchHostSessionController = class {
|
|
|
7182
7343
|
return this.loadPromise;
|
|
7183
7344
|
}
|
|
7184
7345
|
async loadInitialSnapshot(generation) {
|
|
7346
|
+
this.hasAppliedInitialRestoredLayout = false;
|
|
7185
7347
|
this.unsubscribe?.();
|
|
7186
7348
|
this.unsubscribe = null;
|
|
7187
7349
|
this.disposeExternalStatePersistenceSubscriptions();
|
|
@@ -7225,7 +7387,7 @@ var WorkbenchHostSessionController = class {
|
|
|
7225
7387
|
}
|
|
7226
7388
|
this.reconcileNodeLeases();
|
|
7227
7389
|
this.isSnapshotLoaded = true;
|
|
7228
|
-
this.
|
|
7390
|
+
this.applyInitialRestoredLayout();
|
|
7229
7391
|
this.subscribeToPersistence();
|
|
7230
7392
|
this.markReady();
|
|
7231
7393
|
}
|
|
@@ -7499,7 +7661,7 @@ var WorkbenchHostSessionController = class {
|
|
|
7499
7661
|
}
|
|
7500
7662
|
resetHydrationBarrier() {
|
|
7501
7663
|
this.isHydratingInitialSnapshot = true;
|
|
7502
|
-
this.
|
|
7664
|
+
this.hasAppliedInitialRestoredLayout = false;
|
|
7503
7665
|
this.readyPromise = new Promise((resolve) => {
|
|
7504
7666
|
this.resolveReady = resolve;
|
|
7505
7667
|
});
|
|
@@ -7511,22 +7673,47 @@ var WorkbenchHostSessionController = class {
|
|
|
7511
7673
|
}
|
|
7512
7674
|
this.observedSurfaceSize = currentSurfaceSize;
|
|
7513
7675
|
}
|
|
7514
|
-
|
|
7515
|
-
if (this.
|
|
7676
|
+
applyInitialRestoredLayout() {
|
|
7677
|
+
if (this.hasAppliedInitialRestoredLayout || !this.isSnapshotLoaded || !this.hasReceivedSurfaceSize) {
|
|
7516
7678
|
return;
|
|
7517
7679
|
}
|
|
7518
7680
|
const snapshot = this.controller.getSnapshot();
|
|
7519
|
-
const
|
|
7681
|
+
const sourceLayoutBasis = this.loadedSnapshot?.layoutBasis;
|
|
7682
|
+
const restoredNodes = restoreWorkbenchHostNodesToSurface({
|
|
7520
7683
|
constraints: snapshot.layoutConstraints,
|
|
7684
|
+
layoutBasis: sourceLayoutBasis,
|
|
7521
7685
|
nodeDefinitionByType: this.nodeDefinitionByType,
|
|
7522
7686
|
nodes: snapshot.nodes,
|
|
7687
|
+
persistedNodes: this.loadedSnapshot?.nodes,
|
|
7523
7688
|
surfaceSize: snapshot.surfaceSize
|
|
7524
7689
|
});
|
|
7525
|
-
this.
|
|
7526
|
-
|
|
7527
|
-
|
|
7690
|
+
this.closedDockWindowFrameEntries = restoreClosedDockWindowFrameEntriesToSurface({
|
|
7691
|
+
constraints: snapshot.layoutConstraints,
|
|
7692
|
+
entries: this.closedDockWindowFrameEntries.values(),
|
|
7693
|
+
layoutBasis: sourceLayoutBasis,
|
|
7694
|
+
nodeDefinitionByType: this.nodeDefinitionByType,
|
|
7695
|
+
surfaceSize: snapshot.surfaceSize
|
|
7696
|
+
});
|
|
7697
|
+
if (this.loadedSnapshot) {
|
|
7698
|
+
this.loadedSnapshot = {
|
|
7699
|
+
...this.loadedSnapshot,
|
|
7700
|
+
layoutBasis: createWorkbenchSnapshotLayoutBasis(snapshot),
|
|
7701
|
+
metadata: writeClosedDockWindowFrameEntries(
|
|
7702
|
+
this.loadedSnapshot.metadata,
|
|
7703
|
+
this.closedDockWindowFrameEntries.values()
|
|
7704
|
+
),
|
|
7705
|
+
spaces: restoreWorkbenchHostSpacesToSurface({
|
|
7706
|
+
constraints: snapshot.layoutConstraints,
|
|
7707
|
+
layoutBasis: sourceLayoutBasis,
|
|
7708
|
+
spaces: this.loadedSnapshot.spaces,
|
|
7709
|
+
surfaceSize: snapshot.surfaceSize
|
|
7710
|
+
})
|
|
7711
|
+
};
|
|
7712
|
+
}
|
|
7713
|
+
this.hasAppliedInitialRestoredLayout = true;
|
|
7714
|
+
if (!shallowArrayEqual(snapshot.nodes, restoredNodes)) {
|
|
7715
|
+
this.controller.commands.replaceNodes(restoredNodes);
|
|
7528
7716
|
}
|
|
7529
|
-
this.controller.commands.replaceNodes(compactedNodes);
|
|
7530
7717
|
}
|
|
7531
7718
|
queueProjectedNodeReconciliation() {
|
|
7532
7719
|
if (this.pendingProjectedNodeReconciliation) {
|
|
@@ -14428,6 +14615,7 @@ export {
|
|
|
14428
14615
|
createWorkbenchNode,
|
|
14429
14616
|
createWorkbenchNodeFromSnapshot,
|
|
14430
14617
|
createWorkbenchSnapshotFromState,
|
|
14618
|
+
createWorkbenchSnapshotLayoutBasis,
|
|
14431
14619
|
createWorkbenchStateFromSnapshot,
|
|
14432
14620
|
createWorkbenchWindowChromeI18nRuntime,
|
|
14433
14621
|
getWorkbenchLayoutFrame,
|