@flowgram.ai/panel-manager-plugin 1.0.2 → 1.0.6

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/esm/index.js CHANGED
@@ -12,200 +12,37 @@ var __decorateClass = (decorators, target, key, kind) => {
12
12
  // src/create-panel-manager-plugin.ts
13
13
  import { definePluginCreator } from "@flowgram.ai/core";
14
14
 
15
- // src/services/panel-config.ts
16
- var PanelManagerConfig = Symbol("PanelManagerConfig");
17
- var defineConfig = (config) => {
18
- const defaultConfig = {
19
- right: {
20
- max: 1
21
- },
22
- bottom: {
23
- max: 1
24
- },
25
- factories: [],
26
- getPopupContainer: (ctx) => ctx.playground.node.parentNode,
27
- autoResize: true
28
- };
29
- return {
30
- ...defaultConfig,
31
- ...config
32
- };
33
- };
34
-
35
- // src/services/panel-manager.ts
36
- import { injectable, inject } from "inversify";
37
-
38
- // src/services/float-panel.ts
39
- import { Emitter } from "@flowgram.ai/utils";
40
- var PANEL_SIZE_DEFAULT = 400;
41
- var FloatPanel = class {
42
- constructor(config) {
43
- this.config = config;
44
- this.elements = [];
45
- this.onUpdateEmitter = new Emitter();
46
- this.sizeMap = /* @__PURE__ */ new Map();
47
- this.onUpdate = this.onUpdateEmitter.event;
48
- this.currentFactoryKey = "";
49
- }
50
- updateSize(newSize) {
51
- this.sizeMap.set(this.currentFactoryKey, newSize);
52
- this.onUpdateEmitter.fire();
53
- }
54
- get currentSize() {
55
- return this.sizeMap.get(this.currentFactoryKey) || PANEL_SIZE_DEFAULT;
56
- }
57
- open(factory, options) {
58
- const el = factory.render(options?.props);
59
- const idx = this.elements.findIndex((e) => e.key === factory.key);
60
- this.currentFactoryKey = factory.key;
61
- if (!this.sizeMap.has(factory.key)) {
62
- this.sizeMap.set(factory.key, factory.defaultSize || PANEL_SIZE_DEFAULT);
63
- }
64
- if (idx >= 0) {
65
- this.elements[idx] = { el, key: factory.key, style: factory.style };
66
- } else {
67
- this.elements.push({ el, key: factory.key, style: factory.style });
68
- if (this.elements.length > this.config.max) {
69
- this.elements.shift();
70
- }
71
- }
72
- this.onUpdateEmitter.fire();
73
- }
74
- get visible() {
75
- return this.elements.length > 0;
76
- }
77
- close(key) {
78
- if (!key) {
79
- this.elements = [];
80
- } else {
81
- this.elements = this.elements.filter((e) => e.key !== key);
82
- }
83
- this.onUpdateEmitter.fire();
84
- }
85
- dispose() {
86
- this.elements = [];
87
- this.onUpdateEmitter.dispose();
88
- }
89
- };
15
+ // src/services/panel-factory.ts
16
+ import { createStore } from "zustand/vanilla";
17
+ import { nanoid } from "nanoid";
18
+ import { inject, injectable as injectable2 } from "inversify";
90
19
 
91
- // src/services/panel-manager.ts
92
- var PanelManager = class {
20
+ // src/services/panel-restore.ts
21
+ import { injectable } from "inversify";
22
+ var PanelRestore = Symbol("PanelRestore");
23
+ var PanelRestoreImpl = class {
93
24
  constructor() {
94
- this.panelRegistry = /* @__PURE__ */ new Map();
25
+ this.map = /* @__PURE__ */ new Map();
95
26
  }
96
- init() {
97
- this.config.factories.forEach((factory) => this.register(factory));
98
- this.right = new FloatPanel(this.config.right);
99
- this.bottom = new FloatPanel(this.config.bottom);
100
- }
101
- register(factory) {
102
- this.panelRegistry.set(factory.key, factory);
103
- }
104
- open(key, area = "right", options) {
105
- const factory = this.panelRegistry.get(key);
106
- if (!factory) {
107
- return;
108
- }
109
- const panel = this.getPanel(area);
110
- panel.open(factory, options);
111
- }
112
- close(key) {
113
- this.right.close(key);
114
- this.bottom.close(key);
27
+ store(k, v) {
28
+ this.map.set(k, v);
115
29
  }
116
- getPanel(area) {
117
- return area === "right" ? this.right : this.bottom;
118
- }
119
- dispose() {
120
- this.right.dispose();
121
- this.bottom.dispose();
30
+ restore(k) {
31
+ return this.map.get(k);
122
32
  }
123
33
  };
124
- __decorateClass([
125
- inject(PanelManagerConfig)
126
- ], PanelManager.prototype, "config", 2);
127
- PanelManager = __decorateClass([
34
+ PanelRestoreImpl = __decorateClass([
128
35
  injectable()
129
- ], PanelManager);
130
-
131
- // src/services/panel-layer.ts
132
- import ReactDOM from "react-dom";
133
- import { createElement } from "react";
134
- import { injectable as injectable2, inject as inject2 } from "inversify";
135
- import { domUtils, Disposable } from "@flowgram.ai/utils";
136
- import { Layer, PluginContext } from "@flowgram.ai/core";
137
-
138
- // src/components/panel-layer/float-panel.tsx
139
- import { useEffect, useRef as useRef2, startTransition, useState as useState2, useCallback } from "react";
140
-
141
- // src/hooks/use-panel-manager.ts
142
- import { useService } from "@flowgram.ai/core";
143
- var usePanelManager = () => useService(PanelManager);
144
-
145
- // src/components/panel-layer/css.ts
146
- var globalCSS = `
147
- .gedit-flow-panel-layer * {
148
- box-sizing: border-box;
149
- }
150
- `;
151
- var panelLayer = {
152
- pointerEvents: "none",
153
- position: "absolute",
154
- top: 0,
155
- left: 0,
156
- display: "flex",
157
- columnGap: "4px",
158
- width: "100%",
159
- height: "100%",
160
- padding: "4px",
161
- boxSizing: "border-box",
162
- overflow: "hidden"
163
- };
164
- var leftArea = {
165
- width: "100%",
166
- minWidth: 0,
167
- flexGrow: 0,
168
- flexShrink: 1,
169
- display: "flex",
170
- flexDirection: "column",
171
- rowGap: "4px"
172
- };
173
- var rightArea = {
174
- height: "100%",
175
- flexGrow: 1,
176
- flexShrink: 0,
177
- minWidth: 0,
178
- display: "flex",
179
- columnGap: "4px"
180
- };
181
- var mainArea = {
182
- position: "relative",
183
- overflow: "hidden",
184
- flexGrow: 0,
185
- flexShrink: 1,
186
- width: "100%",
187
- height: "100%"
188
- };
189
- var bottomArea = {
190
- flexGrow: 1,
191
- flexShrink: 0,
192
- width: "100%",
193
- minHeight: 0
194
- };
195
- var floatPanelWrap = {
196
- pointerEvents: "auto",
197
- height: "100%",
198
- width: "100%",
199
- overflow: "auto"
200
- };
36
+ ], PanelRestoreImpl);
201
37
 
202
38
  // src/components/resize-bar/index.tsx
203
39
  import { useRef, useState } from "react";
204
40
  import { jsx } from "react/jsx-runtime";
205
- var ResizeBar = ({ onResize, size, isVertical }) => {
41
+ var ResizeBar = ({ onResize, size, direction }) => {
206
42
  const currentPoint = useRef(null);
207
43
  const [isDragging, setIsDragging] = useState(false);
208
44
  const [isHovered, setIsHovered] = useState(false);
45
+ const isVertical = direction === "vertical";
209
46
  return /* @__PURE__ */ jsx(
210
47
  "div",
211
48
  {
@@ -269,53 +106,487 @@ var ResizeBar = ({ onResize, size, isVertical }) => {
269
106
  );
270
107
  };
271
108
 
272
- // src/components/panel-layer/float-panel.tsx
273
- import { jsx as jsx2, jsxs } from "react/jsx-runtime";
274
- var FloatPanel2 = ({ area }) => {
275
- const [, setVersion] = useState2(0);
276
- const panelManager = usePanelManager();
277
- const panel = useRef2(panelManager.getPanel(area));
278
- const render = () => panel.current.elements.map((i) => /* @__PURE__ */ jsx2("div", { className: "float-panel-wrap", style: { ...floatPanelWrap, ...i.style }, children: i.el }, i.key));
279
- const node = useRef2(render());
109
+ // src/services/panel-config.ts
110
+ var PanelManagerConfig = Symbol("PanelManagerConfig");
111
+ var defineConfig = (config) => {
112
+ const defaultConfig = {
113
+ right: {
114
+ max: 1
115
+ },
116
+ bottom: {
117
+ max: 1
118
+ },
119
+ dockedRight: {
120
+ max: 1
121
+ },
122
+ dockedBottom: {
123
+ max: 1
124
+ },
125
+ factories: [],
126
+ autoResize: true,
127
+ layerProps: {},
128
+ resizeBarRender: ResizeBar,
129
+ getPopupContainer: (ctx) => ctx.playground.node.parentNode
130
+ };
131
+ return {
132
+ ...defaultConfig,
133
+ ...config
134
+ };
135
+ };
136
+
137
+ // src/utils.ts
138
+ var merge = (...objs) => {
139
+ const result = {};
140
+ for (const obj of objs) {
141
+ if (!obj || typeof obj !== "object") continue;
142
+ for (const key of Object.keys(obj)) {
143
+ const value = obj[key];
144
+ if (result[key] === void 0) {
145
+ result[key] = value;
146
+ }
147
+ }
148
+ }
149
+ return result;
150
+ };
151
+
152
+ // src/services/panel-factory.ts
153
+ var PanelEntityFactory = Symbol("PanelEntityFactory");
154
+ var PanelEntityFactoryConstant = Symbol("PanelEntityFactoryConstant");
155
+ var PanelEntityConfigConstant = Symbol("PanelEntityConfigConstant");
156
+ var PANEL_SIZE_DEFAULT = 400;
157
+ var PanelEntity = class {
158
+ constructor() {
159
+ this.initialized = false;
160
+ /** 实例唯一标识 */
161
+ this.id = nanoid();
162
+ /** 渲染缓存 */
163
+ this.node = null;
164
+ }
165
+ get area() {
166
+ return this.config.area;
167
+ }
168
+ get mode() {
169
+ return this.config.area.startsWith("docked") ? "docked" : "floating";
170
+ }
171
+ get key() {
172
+ return this.factory.key;
173
+ }
174
+ get renderer() {
175
+ if (!this.node) {
176
+ this.node = this.factory.render(this.config.props);
177
+ }
178
+ return this.node;
179
+ }
180
+ get fullscreen() {
181
+ return this.store.getState().fullscreen;
182
+ }
183
+ set fullscreen(next) {
184
+ this.store.setState({ fullscreen: next });
185
+ }
186
+ get resizable() {
187
+ if (this.fullscreen) {
188
+ return false;
189
+ }
190
+ return this.factory.resize !== void 0 ? this.factory.resize : this.globalConfig.autoResize;
191
+ }
192
+ get keepDOM() {
193
+ return this.factory.keepDOM;
194
+ }
195
+ get visible() {
196
+ return this.store.getState().visible;
197
+ }
198
+ set visible(next) {
199
+ this.store.setState({ visible: next });
200
+ }
201
+ get layer() {
202
+ return document.querySelector(
203
+ this.mode ? ".gedit-flow-panel-layer-wrap-docked" : ".gedit-flow-panel-layer-wrap-floating"
204
+ );
205
+ }
206
+ init() {
207
+ if (this.initialized) {
208
+ return;
209
+ }
210
+ this.initialized = true;
211
+ const cache = this.restore.restore(this.key);
212
+ const initialState = merge(
213
+ {
214
+ size: this.config.defaultSize,
215
+ fullscreen: this.config.fullscreen
216
+ },
217
+ cache ? cache : {},
218
+ {
219
+ size: this.factory.defaultSize || PANEL_SIZE_DEFAULT,
220
+ fullscreen: this.factory.fullscreen || false,
221
+ ...this.factory.keepDOM ? { visible: true } : {}
222
+ }
223
+ );
224
+ this.store = createStore(() => initialState);
225
+ }
226
+ mergeState() {
227
+ }
228
+ dispose() {
229
+ this.restore.store(this.key, this.store.getState());
230
+ }
231
+ };
232
+ __decorateClass([
233
+ inject(PanelRestore)
234
+ ], PanelEntity.prototype, "restore", 2);
235
+ __decorateClass([
236
+ inject(PanelEntityFactoryConstant)
237
+ ], PanelEntity.prototype, "factory", 2);
238
+ __decorateClass([
239
+ inject(PanelEntityConfigConstant)
240
+ ], PanelEntity.prototype, "config", 2);
241
+ __decorateClass([
242
+ inject(PanelManagerConfig)
243
+ ], PanelEntity.prototype, "globalConfig", 2);
244
+ PanelEntity = __decorateClass([
245
+ injectable2()
246
+ ], PanelEntity);
247
+
248
+ // src/services/panel-manager.ts
249
+ import { injectable as injectable3, inject as inject2 } from "inversify";
250
+ import { Emitter } from "@flowgram.ai/utils";
251
+ var PanelManager = class {
252
+ constructor() {
253
+ this.panelRegistry = /* @__PURE__ */ new Map();
254
+ this.panels = /* @__PURE__ */ new Map();
255
+ this.onPanelsChangeEvent = new Emitter();
256
+ this.onPanelsChange = this.onPanelsChangeEvent.event;
257
+ }
258
+ init() {
259
+ this.config.factories.forEach((factory) => this.register(factory));
260
+ }
261
+ /** registry panel factory */
262
+ register(factory) {
263
+ this.panelRegistry.set(factory.key, factory);
264
+ }
265
+ /** open panel */
266
+ open(key, area = "right", options) {
267
+ const factory = this.panelRegistry.get(key);
268
+ if (!factory) {
269
+ return;
270
+ }
271
+ const sameKeyPanels = this.getPanels(area).filter((p) => p.key === key);
272
+ if (!factory.allowDuplicates && sameKeyPanels.length) {
273
+ !factory.keepDOM && sameKeyPanels.forEach((p) => this.remove(p.id));
274
+ }
275
+ if (factory.keepDOM && sameKeyPanels.length) {
276
+ sameKeyPanels[0].visible = true;
277
+ return;
278
+ }
279
+ const panel = this.createPanel({
280
+ factory,
281
+ config: {
282
+ area,
283
+ ...options
284
+ }
285
+ });
286
+ this.panels.set(panel.id, panel);
287
+ this.trim(area);
288
+ this.onPanelsChangeEvent.fire();
289
+ }
290
+ /** close panel */
291
+ close(key) {
292
+ const panels = this.getPanels();
293
+ const closedPanels = key ? panels.filter((p) => p.key === key) : panels;
294
+ closedPanels.forEach((panel) => {
295
+ if (panel.keepDOM) {
296
+ panel.visible = false;
297
+ return;
298
+ }
299
+ this.remove(panel.id);
300
+ });
301
+ this.onPanelsChangeEvent.fire();
302
+ }
303
+ trim(area) {
304
+ const panels = this.getPanels(area).filter((p) => !p.keepDOM);
305
+ const areaConfig = this.getAreaConfig(area);
306
+ while (panels.length > areaConfig.max) {
307
+ const removed = panels.shift();
308
+ if (removed) {
309
+ this.remove(removed.id);
310
+ }
311
+ }
312
+ }
313
+ remove(id) {
314
+ const panel = this.panels.get(id);
315
+ if (panel) {
316
+ panel.dispose();
317
+ this.panels.delete(id);
318
+ }
319
+ }
320
+ getPanels(area) {
321
+ const panels = [];
322
+ this.panels.forEach((panel) => {
323
+ if (!area || panel.area === area) {
324
+ panels.push(panel);
325
+ }
326
+ });
327
+ return panels;
328
+ }
329
+ getAreaConfig(area) {
330
+ switch (area) {
331
+ case "docked-bottom":
332
+ return this.config.dockedBottom;
333
+ case "docked-right":
334
+ return this.config.dockedRight;
335
+ case "bottom":
336
+ return this.config.bottom;
337
+ case "right":
338
+ default:
339
+ return this.config.right;
340
+ }
341
+ }
342
+ dispose() {
343
+ this.onPanelsChangeEvent.dispose();
344
+ }
345
+ };
346
+ __decorateClass([
347
+ inject2(PanelManagerConfig)
348
+ ], PanelManager.prototype, "config", 2);
349
+ __decorateClass([
350
+ inject2(PanelEntityFactory)
351
+ ], PanelManager.prototype, "createPanel", 2);
352
+ PanelManager = __decorateClass([
353
+ injectable3()
354
+ ], PanelManager);
355
+
356
+ // src/services/panel-layer.ts
357
+ import ReactDOM from "react-dom";
358
+ import { createElement } from "react";
359
+ import { injectable as injectable4, inject as inject3 } from "inversify";
360
+ import { domUtils, Disposable } from "@flowgram.ai/utils";
361
+ import { Layer, PluginContext } from "@flowgram.ai/core";
362
+
363
+ // src/components/panel-layer/panel-layer.tsx
364
+ import clsx2 from "clsx";
365
+
366
+ // src/hooks/use-global-css.ts
367
+ import { useEffect } from "react";
368
+ var useGlobalCSS = ({ cssText, id, cleanup }) => {
280
369
  useEffect(() => {
281
- const dispose = panel.current.onUpdate(() => {
370
+ if (typeof document === "undefined") return;
371
+ if (document.getElementById(id)) return;
372
+ const style = document.createElement("style");
373
+ style.id = id;
374
+ style.textContent = cssText;
375
+ document.head.appendChild(style);
376
+ return () => {
377
+ const existing = document.getElementById(id);
378
+ if (existing && cleanup) existing.remove();
379
+ };
380
+ }, [id]);
381
+ };
382
+
383
+ // src/components/panel-layer/panel.tsx
384
+ import { useEffect as useEffect2, startTransition, useState as useState2, useRef as useRef2 } from "react";
385
+ import { clsx } from "clsx";
386
+
387
+ // src/hooks/use-panel-manager.ts
388
+ import { useService } from "@flowgram.ai/core";
389
+ var usePanelManager = () => useService(PanelManager);
390
+
391
+ // src/hooks/use-panel.ts
392
+ import { useContext } from "react";
393
+ import { useStoreWithEqualityFn } from "zustand/traditional";
394
+ import { shallow } from "zustand/shallow";
395
+
396
+ // src/contexts.ts
397
+ import { createContext } from "react";
398
+ var PanelContext = createContext({});
399
+
400
+ // src/hooks/use-panel.ts
401
+ var usePanel = () => useContext(PanelContext);
402
+ var usePanelStore = (selector) => {
403
+ const panel = usePanel();
404
+ return useStoreWithEqualityFn(panel.store, selector, shallow);
405
+ };
406
+
407
+ // src/components/panel-layer/panel.tsx
408
+ import { Fragment, jsx as jsx2, jsxs } from "react/jsx-runtime";
409
+ var PanelItem = ({ panel }) => {
410
+ const panelManager = usePanelManager();
411
+ const ref = useRef2(null);
412
+ const isHorizontal = ["right", "docked-right"].includes(panel.area);
413
+ const { size, fullscreen, visible } = usePanelStore((s) => ({ size: s.size, fullscreen: s.fullscreen, visible: s.visible }));
414
+ const [layerSize, setLayerSize] = useState2(size);
415
+ const [displayStyle, setDisplayStyle] = useState2({});
416
+ const currentSize = fullscreen ? layerSize : size;
417
+ const sizeStyle = isHorizontal ? { width: currentSize } : { height: currentSize };
418
+ const handleResize = (next) => {
419
+ let nextSize = next;
420
+ if (typeof panel.factory.maxSize === "number" && nextSize > panel.factory.maxSize) {
421
+ nextSize = panel.factory.maxSize;
422
+ } else if (typeof panel.factory.minSize === "number" && nextSize < panel.factory.minSize) {
423
+ nextSize = panel.factory.minSize;
424
+ }
425
+ panel.store.setState({ size: nextSize });
426
+ };
427
+ useEffect2(() => {
428
+ if (ref.current && !fullscreen) {
429
+ const { width, height } = ref.current.getBoundingClientRect();
430
+ const realSize = isHorizontal ? width : height;
431
+ panel.store.setState({ size: realSize });
432
+ }
433
+ }, [fullscreen]);
434
+ useEffect2(() => {
435
+ if (!fullscreen) {
436
+ return;
437
+ }
438
+ const layer = panel.layer;
439
+ if (!layer) {
440
+ return;
441
+ }
442
+ const observer = new ResizeObserver(([entry]) => {
443
+ const { width, height } = entry.contentRect;
444
+ setLayerSize(isHorizontal ? width : height);
445
+ });
446
+ observer.observe(layer);
447
+ return () => observer.disconnect();
448
+ }, [fullscreen]);
449
+ useEffect2(() => {
450
+ if (panel.keepDOM) {
451
+ setDisplayStyle({ display: visible ? "block" : "none" });
452
+ }
453
+ }, [visible]);
454
+ return /* @__PURE__ */ jsxs(
455
+ "div",
456
+ {
457
+ className: clsx(
458
+ "gedit-flow-panel-wrap",
459
+ isHorizontal ? "panel-horizontal" : "panel-vertical"
460
+ ),
461
+ ref,
462
+ style: { ...displayStyle, ...panel.factory.style, ...panel.config.style, ...sizeStyle },
463
+ children: [
464
+ panel.resizable && panelManager.config.resizeBarRender({
465
+ size,
466
+ direction: isHorizontal ? "vertical" : "horizontal",
467
+ onResize: handleResize
468
+ }),
469
+ panel.renderer
470
+ ]
471
+ },
472
+ panel.id
473
+ );
474
+ };
475
+ var PanelArea = ({ area }) => {
476
+ const panelManager = usePanelManager();
477
+ const [panels, setPanels] = useState2(panelManager.getPanels(area));
478
+ useEffect2(() => {
479
+ const dispose = panelManager.onPanelsChange(() => {
282
480
  startTransition(() => {
283
- node.current = render();
284
- setVersion((v) => v + 1);
481
+ setPanels(panelManager.getPanels(area));
285
482
  });
286
483
  });
287
484
  return () => dispose.dispose();
288
- }, [panel]);
289
- const onResize = useCallback((newSize) => panel.current.updateSize(newSize), []);
290
- const size = panel.current.currentSize;
291
- const sizeStyle = area === "right" ? { width: size, height: "100%" } : { height: size, width: "100%" };
292
- return /* @__PURE__ */ jsxs(
485
+ }, []);
486
+ return /* @__PURE__ */ jsx2(Fragment, { children: panels.map((panel) => /* @__PURE__ */ jsx2(PanelContext.Provider, { value: panel, children: /* @__PURE__ */ jsx2(PanelItem, { panel }) }, panel.id)) });
487
+ };
488
+
489
+ // src/components/panel-layer/css.ts
490
+ var globalCSS = `
491
+ .gedit-flow-panel-layer-wrap * {
492
+ box-sizing: border-box;
493
+ }
494
+ .gedit-flow-panel-layer-wrap {
495
+ position: absolute;
496
+ top: 0;
497
+ left: 0;
498
+ display: flex;
499
+ width: 100%;
500
+ height: 100%;
501
+ overflow: hidden;
502
+ }
503
+ .gedit-flow-panel-layer-wrap-docked {
504
+
505
+ }
506
+ .gedit-flow-panel-layer-wrap-floating {
507
+ pointer-events: none;
508
+ }
509
+
510
+ .gedit-flow-panel-left-area {
511
+ width: 100%;
512
+ min-width: 0;
513
+ flex-grow: 0;
514
+ flex-shrink: 1;
515
+ display: flex;
516
+ flex-direction: column;
517
+ }
518
+ .gedit-flow-panel-right-area {
519
+ height: 100%;
520
+ flex-grow: 1;
521
+ flex-shrink: 0;
522
+ min-width: 0;
523
+ display: flex;
524
+ max-width: 100%;
525
+ }
526
+
527
+ .gedit-flow-panel-main-area {
528
+ position: relative;
529
+ overflow: hidden;
530
+ flex-grow: 0;
531
+ flex-shrink: 1;
532
+ width: 100%;
533
+ height: 100%;
534
+ }
535
+ .gedit-flow-panel-bottom-area {
536
+ flex-grow: 1;
537
+ flex-shrink: 0;
538
+ width: 100%;
539
+ min-height: 0;
540
+ }
541
+ .gedit-flow-panel-wrap {
542
+ pointer-events: auto;
543
+ overflow: auto;
544
+ position: relative;
545
+ }
546
+ .gedit-flow-panel-wrap.panel-horizontal {
547
+ height: 100%;
548
+ }
549
+ .gedit-flow-panel-wrap.panel-vertical {
550
+ width: 100%;
551
+ }
552
+ `;
553
+
554
+ // src/components/panel-layer/panel-layer.tsx
555
+ import { jsx as jsx3, jsxs as jsxs2 } from "react/jsx-runtime";
556
+ var PanelLayer = ({
557
+ mode = "floating",
558
+ className,
559
+ style,
560
+ children
561
+ }) => {
562
+ useGlobalCSS({
563
+ cssText: globalCSS,
564
+ id: "flow-panel-layer-css"
565
+ });
566
+ return /* @__PURE__ */ jsxs2(
293
567
  "div",
294
568
  {
295
- className: "gedit-flow-panel",
296
- style: {
297
- position: "relative",
298
- display: panel.current.visible ? "block" : "none",
299
- ...sizeStyle
300
- },
569
+ className: clsx2(
570
+ "gedit-flow-panel-layer-wrap",
571
+ mode === "docked" && "gedit-flow-panel-layer-wrap-docked",
572
+ mode === "floating" && "gedit-flow-panel-layer-wrap-floating",
573
+ className
574
+ ),
575
+ style,
301
576
  children: [
302
- panelManager.config.autoResize && panel.current.elements.length > 0 && /* @__PURE__ */ jsx2(ResizeBar, { size, isVertical: area === "right", onResize }),
303
- node.current
577
+ /* @__PURE__ */ jsxs2("div", { className: "gedit-flow-panel-left-area", children: [
578
+ /* @__PURE__ */ jsx3("div", { className: "gedit-flow-panel-main-area", children }),
579
+ /* @__PURE__ */ jsx3("div", { className: "gedit-flow-panel-bottom-area", children: /* @__PURE__ */ jsx3(PanelArea, { area: mode === "docked" ? "docked-bottom" : "bottom" }) })
580
+ ] }),
581
+ /* @__PURE__ */ jsx3("div", { className: "gedit-flow-panel-right-area", children: /* @__PURE__ */ jsx3(PanelArea, { area: mode === "docked" ? "docked-right" : "right" }) })
304
582
  ]
305
583
  }
306
584
  );
307
585
  };
308
586
 
309
- // src/components/panel-layer/panel-layer.tsx
310
- import { jsx as jsx3, jsxs as jsxs2 } from "react/jsx-runtime";
311
- var PanelLayer = ({ children }) => /* @__PURE__ */ jsxs2("div", { style: panelLayer, children: [
312
- /* @__PURE__ */ jsx3("style", { dangerouslySetInnerHTML: { __html: globalCSS } }),
313
- /* @__PURE__ */ jsxs2("div", { className: "gedit-flow-panel-left-area", style: leftArea, children: [
314
- /* @__PURE__ */ jsx3("div", { className: "gedit-flow-panel-main-area", style: mainArea, children }),
315
- /* @__PURE__ */ jsx3("div", { className: "gedit-flow-panel-bottom-area", style: bottomArea, children: /* @__PURE__ */ jsx3(FloatPanel2, { area: "bottom" }) })
316
- ] }),
317
- /* @__PURE__ */ jsx3("div", { className: "gedit-flow-panel-right-area", style: rightArea, children: /* @__PURE__ */ jsx3(FloatPanel2, { area: "right" }) })
318
- ] });
587
+ // src/components/panel-layer/docked-panel-layer.tsx
588
+ import { jsx as jsx4 } from "react/jsx-runtime";
589
+ var DockedPanelLayer = (props) => /* @__PURE__ */ jsx4(PanelLayer, { mode: "docked", ...props });
319
590
 
320
591
  // src/services/panel-layer.ts
321
592
  var PanelLayer2 = class extends Layer {
@@ -344,37 +615,55 @@ var PanelLayer2 = class extends Layer {
344
615
  }
345
616
  render() {
346
617
  if (!this.layout) {
347
- this.layout = createElement(PanelLayer);
618
+ const { children, ...layoutProps } = this.panelConfig.layerProps;
619
+ this.layout = createElement(PanelLayer, layoutProps, children);
348
620
  }
349
621
  return ReactDOM.createPortal(this.layout, this.panelRoot);
350
622
  }
351
623
  };
352
624
  __decorateClass([
353
- inject2(PanelManagerConfig)
625
+ inject3(PanelManagerConfig)
354
626
  ], PanelLayer2.prototype, "panelConfig", 2);
355
627
  __decorateClass([
356
- inject2(PluginContext)
628
+ inject3(PluginContext)
357
629
  ], PanelLayer2.prototype, "pluginContext", 2);
358
630
  PanelLayer2 = __decorateClass([
359
- injectable2()
631
+ injectable4()
360
632
  ], PanelLayer2);
361
633
 
362
634
  // src/create-panel-manager-plugin.ts
363
635
  var createPanelManagerPlugin = definePluginCreator({
364
636
  onBind: ({ bind }, opt) => {
365
637
  bind(PanelManager).to(PanelManager).inSingletonScope();
638
+ bind(PanelRestore).to(PanelRestoreImpl).inSingletonScope();
366
639
  bind(PanelManagerConfig).toConstantValue(defineConfig(opt));
640
+ bind(PanelEntityFactory).toFactory(
641
+ (context) => ({
642
+ factory,
643
+ config
644
+ }) => {
645
+ const container = context.container.createChild();
646
+ container.bind(PanelEntityFactoryConstant).toConstantValue(factory);
647
+ container.bind(PanelEntityConfigConstant).toConstantValue(config);
648
+ const panel = container.resolve(PanelEntity);
649
+ panel.init();
650
+ return panel;
651
+ }
652
+ );
367
653
  },
368
- onInit(ctx, opt) {
654
+ onInit(ctx) {
369
655
  ctx.playground.registerLayer(PanelLayer2);
370
656
  const panelManager = ctx.container.get(PanelManager);
371
657
  panelManager.init();
372
658
  }
373
659
  });
374
660
  export {
661
+ DockedPanelLayer,
375
662
  PanelManager,
663
+ PanelRestore,
376
664
  ResizeBar,
377
665
  createPanelManagerPlugin,
666
+ usePanel,
378
667
  usePanelManager
379
668
  };
380
669
  //# sourceMappingURL=index.js.map