mirror of
https://github.com/mathuo/dockview
synced 2025-08-28 21:16:38 +00:00
feat: refactor dockview update logic
This commit is contained in:
parent
3f93b34f73
commit
ccd8e7fdf5
@ -83,7 +83,7 @@ export const Params = (props: {
|
||||
const interval = setInterval(() => {
|
||||
const panel1 = gridApi.getPanel('panel1');
|
||||
|
||||
panel1.update({ params: { ticker: Date.now() } });
|
||||
panel1.update({ params: { params: { ticker: Date.now() } } });
|
||||
}, 1000);
|
||||
return () => {
|
||||
clearInterval(interval);
|
||||
|
@ -0,0 +1,111 @@
|
||||
import {
|
||||
GridviewApi,
|
||||
GridviewReact,
|
||||
GridviewReadyEvent,
|
||||
IGridviewPanelProps,
|
||||
Orientation,
|
||||
PanelCollection,
|
||||
} from 'dockview';
|
||||
import * as React from 'react';
|
||||
import { Meta } from '@storybook/react';
|
||||
|
||||
const components: PanelCollection<IGridviewPanelProps<any>> = {
|
||||
default: (props) => {
|
||||
return (
|
||||
<div style={{ padding: '10px', height: '100%' }}>hello world</div>
|
||||
);
|
||||
},
|
||||
ticker: (props: IGridviewPanelProps<{ ticker: number }>) => {
|
||||
return (
|
||||
<div style={{ padding: '10px', height: '100%' }}>
|
||||
{`The current ticker value is ${props.params.ticker}`}
|
||||
</div>
|
||||
);
|
||||
},
|
||||
};
|
||||
|
||||
export const Params = (props: {
|
||||
onEvent: (name: string) => void;
|
||||
theme: string;
|
||||
hideBorders: boolean;
|
||||
disableAutoResizing: boolean;
|
||||
}) => {
|
||||
const api = React.useRef<GridviewApi>();
|
||||
|
||||
React.useEffect(() => {
|
||||
if (!api.current) {
|
||||
return () => {
|
||||
// noop
|
||||
};
|
||||
}
|
||||
|
||||
const gridApi = api.current;
|
||||
|
||||
const interval = setInterval(() => {
|
||||
const panel1 = gridApi.getPanel('panel1');
|
||||
|
||||
panel1.update({ params: { ticker: Date.now() } });
|
||||
}, 1000);
|
||||
return () => {
|
||||
clearInterval(interval);
|
||||
};
|
||||
}, [api]);
|
||||
|
||||
const onReady = (event: GridviewReadyEvent) => {
|
||||
api.current = event.api;
|
||||
|
||||
event.api.onGridEvent((e) => props.onEvent(e.kind));
|
||||
|
||||
event.api.addPanel({
|
||||
id: 'panel1',
|
||||
component: 'ticker',
|
||||
params: {
|
||||
ticker: 0,
|
||||
},
|
||||
});
|
||||
event.api.addPanel({
|
||||
id: 'panel2',
|
||||
component: 'default',
|
||||
});
|
||||
event.api.addPanel({
|
||||
id: 'panel3',
|
||||
component: 'default',
|
||||
});
|
||||
};
|
||||
|
||||
return (
|
||||
<GridviewReact
|
||||
orientation={Orientation.HORIZONTAL}
|
||||
className={props.theme}
|
||||
onReady={onReady}
|
||||
components={components}
|
||||
hideBorders={props.hideBorders}
|
||||
disableAutoResizing={props.disableAutoResizing}
|
||||
/>
|
||||
);
|
||||
};
|
||||
|
||||
export default {
|
||||
title: 'Library/Gridview/Params',
|
||||
component: Params,
|
||||
decorators: [
|
||||
(Component) => {
|
||||
document.body.style.padding = '0px';
|
||||
return (
|
||||
<div style={{ height: '100vh', fontFamily: 'Arial' }}>
|
||||
<Component />
|
||||
</div>
|
||||
);
|
||||
},
|
||||
],
|
||||
args: { theme: 'dockview-theme-light' },
|
||||
argTypes: {
|
||||
theme: {
|
||||
control: {
|
||||
type: 'select',
|
||||
options: ['dockview-theme-dark', 'dockview-theme-light'],
|
||||
},
|
||||
},
|
||||
onEvent: { action: 'onEvent' },
|
||||
},
|
||||
} as Meta;
|
@ -9,7 +9,7 @@ import {
|
||||
import * as React from 'react';
|
||||
import { Meta } from '@storybook/react';
|
||||
|
||||
const components: PanelCollection = {
|
||||
const components: PanelCollection<ISplitviewPanelProps> = {
|
||||
default: (props: ISplitviewPanelProps<{ color: string }>) => {
|
||||
const resize = () => {
|
||||
props.api.setSize({ size: 300 });
|
||||
|
@ -0,0 +1,109 @@
|
||||
import {
|
||||
ISplitviewPanelProps,
|
||||
Orientation,
|
||||
PanelCollection,
|
||||
SplitviewApi,
|
||||
SplitviewReact,
|
||||
SplitviewReadyEvent,
|
||||
} from 'dockview';
|
||||
import * as React from 'react';
|
||||
import { Meta } from '@storybook/react';
|
||||
|
||||
const components: PanelCollection<ISplitviewPanelProps<any>> = {
|
||||
default: (props) => {
|
||||
return (
|
||||
<div style={{ padding: '10px', height: '100%' }}>hello world</div>
|
||||
);
|
||||
},
|
||||
ticker: (props: ISplitviewPanelProps<{ ticker: number }>) => {
|
||||
return (
|
||||
<div style={{ padding: '10px', height: '100%' }}>
|
||||
{`The current ticker value is ${props.params.ticker}`}
|
||||
</div>
|
||||
);
|
||||
},
|
||||
};
|
||||
|
||||
export const Params = (props: {
|
||||
onEvent: (name: string) => void;
|
||||
theme: string;
|
||||
hideBorders: boolean;
|
||||
disableAutoResizing: boolean;
|
||||
}) => {
|
||||
const api = React.useRef<SplitviewApi>();
|
||||
|
||||
React.useEffect(() => {
|
||||
if (!api.current) {
|
||||
return () => {
|
||||
// noop
|
||||
};
|
||||
}
|
||||
|
||||
const gridApi = api.current;
|
||||
|
||||
const interval = setInterval(() => {
|
||||
const panel1 = gridApi.getPanel('panel1');
|
||||
|
||||
panel1.update({ params: { ticker: Date.now() } });
|
||||
}, 1000);
|
||||
return () => {
|
||||
clearInterval(interval);
|
||||
};
|
||||
}, [api]);
|
||||
|
||||
const onReady = (event: SplitviewReadyEvent) => {
|
||||
api.current = event.api;
|
||||
|
||||
event.api.addPanel({
|
||||
id: 'panel1',
|
||||
component: 'ticker',
|
||||
params: {
|
||||
ticker: 0,
|
||||
},
|
||||
});
|
||||
event.api.addPanel({
|
||||
id: 'panel2',
|
||||
component: 'default',
|
||||
});
|
||||
event.api.addPanel({
|
||||
id: 'panel3',
|
||||
component: 'default',
|
||||
});
|
||||
};
|
||||
|
||||
return (
|
||||
<SplitviewReact
|
||||
orientation={Orientation.HORIZONTAL}
|
||||
className={props.theme}
|
||||
onReady={onReady}
|
||||
components={components}
|
||||
hideBorders={props.hideBorders}
|
||||
disableAutoResizing={props.disableAutoResizing}
|
||||
/>
|
||||
);
|
||||
};
|
||||
|
||||
export default {
|
||||
title: 'Library/Splitview/Params',
|
||||
component: Params,
|
||||
decorators: [
|
||||
(Component) => {
|
||||
document.body.style.padding = '0px';
|
||||
return (
|
||||
<div style={{ height: '100vh', fontFamily: 'Arial' }}>
|
||||
<Component />
|
||||
</div>
|
||||
);
|
||||
},
|
||||
],
|
||||
args: { theme: 'dockview-theme-light' },
|
||||
argTypes: {
|
||||
theme: {
|
||||
control: {
|
||||
type: 'select',
|
||||
options: ['dockview-theme-dark', 'dockview-theme-light'],
|
||||
},
|
||||
},
|
||||
onEvent: { action: 'onEvent' },
|
||||
},
|
||||
} as Meta;
|
@ -58,11 +58,11 @@ export class DockviewPanelApiImpl
|
||||
}
|
||||
|
||||
get title() {
|
||||
return this.panel.params?.title || '';
|
||||
return this.panel.title;
|
||||
}
|
||||
|
||||
get suppressClosable() {
|
||||
return !!this.panel.params?.suppressClosable;
|
||||
return !!this.panel.suppressClosable;
|
||||
}
|
||||
|
||||
get isGroupActive() {
|
||||
|
@ -1,22 +1,19 @@
|
||||
import {
|
||||
DefaultTab,
|
||||
WrappedTab,
|
||||
} from '../../../dockview/components/tab/defaultTab';
|
||||
import { DefaultTab, WrappedTab } from './components/tab/defaultTab';
|
||||
import {
|
||||
GroupPanelPartInitParameters,
|
||||
IActionsRenderer,
|
||||
IContentRenderer,
|
||||
ITabRenderer,
|
||||
} from '../../../groupview/types';
|
||||
import { GroupviewPanel } from '../../../groupview/groupviewPanel';
|
||||
import { IDisposable } from '../../../lifecycle';
|
||||
import { PanelUpdateEvent } from '../../../panel/types';
|
||||
} from '../groupview/types';
|
||||
import { GroupviewPanel } from '../groupview/groupviewPanel';
|
||||
import { IDisposable } from '../lifecycle';
|
||||
import { GroupPanelUpdateEvent } from '../groupview/groupPanel';
|
||||
|
||||
export interface IGroupPanelView extends IDisposable {
|
||||
readonly content: IContentRenderer;
|
||||
readonly tab?: ITabRenderer;
|
||||
readonly actions?: IActionsRenderer;
|
||||
update(event: PanelUpdateEvent): void;
|
||||
update(event: GroupPanelUpdateEvent): void;
|
||||
layout(width: number, height: number): void;
|
||||
init(params: GroupPanelPartInitParameters): void;
|
||||
updateParentGroup(group: GroupviewPanel, isPanelVisible: boolean): void;
|
||||
@ -65,19 +62,19 @@ export class DefaultGroupPanelView implements IGroupPanelView {
|
||||
}
|
||||
|
||||
updateParentGroup(group: GroupviewPanel, isPanelVisible: boolean): void {
|
||||
//
|
||||
// TODO
|
||||
}
|
||||
|
||||
layout(width: number, height: number): void {
|
||||
this.content.layout(width, height);
|
||||
}
|
||||
|
||||
update(event: PanelUpdateEvent): void {
|
||||
update(event: GroupPanelUpdateEvent): void {
|
||||
this.content.update(event);
|
||||
this.tab.update(event);
|
||||
}
|
||||
|
||||
toJSON() {
|
||||
toJSON(): {} {
|
||||
return {
|
||||
content: this.content.toJSON(),
|
||||
tab:
|
@ -5,11 +5,8 @@ import {
|
||||
} from '../gridview/gridview';
|
||||
import { Position } from '../dnd/droptarget';
|
||||
import { tail, sequenceEquals } from '../array';
|
||||
import {
|
||||
GroupPanel,
|
||||
GroupviewPanelState,
|
||||
IGroupPanel,
|
||||
} from '../groupview/groupPanel';
|
||||
import { GroupviewPanelState, IGroupPanel } from '../groupview/groupPanel';
|
||||
import { DockviewGroupPanel } from './dockviewGroupPanel';
|
||||
import {
|
||||
CompositeDisposable,
|
||||
IDisposable,
|
||||
@ -58,7 +55,7 @@ import {
|
||||
GroupPanelViewState,
|
||||
} from '../groupview/groupview';
|
||||
import { GroupviewPanel } from '../groupview/groupviewPanel';
|
||||
import { DefaultGroupPanelView } from '../react/dockview/v2/defaultGroupPanelView';
|
||||
import { DefaultGroupPanelView } from './defaultGroupPanelView';
|
||||
|
||||
const nextGroupId = sequentialNumberGenerator();
|
||||
|
||||
@ -595,7 +592,10 @@ export class DockviewComponent
|
||||
tab: this.createTabComponent(options.id, options.tabComponent),
|
||||
});
|
||||
|
||||
const panel: IGroupPanel = new GroupPanel(options.id, this._api);
|
||||
const panel: IGroupPanel = new DockviewGroupPanel(
|
||||
options.id,
|
||||
this._api
|
||||
);
|
||||
panel.init({
|
||||
view,
|
||||
title: options.title || options.id,
|
||||
@ -704,15 +704,8 @@ export class DockviewComponent
|
||||
): void {
|
||||
let group: GroupviewPanel;
|
||||
|
||||
// if (
|
||||
// this.groups.size === 1 &&
|
||||
// Array.from(this.groups.values())[0].value.size === 0
|
||||
// ) {
|
||||
// group = Array.from(this.groups.values())[0].value;
|
||||
// } else {
|
||||
group! = this.createGroup();
|
||||
this.doAddGroup(group, location);
|
||||
// }
|
||||
|
||||
group.group.openPanel(panel);
|
||||
}
|
||||
@ -815,7 +808,6 @@ export class DockviewComponent
|
||||
`Duplicate group id ${options?.id}. reassigning group id to avoid errors`
|
||||
);
|
||||
id = undefined;
|
||||
// throw new Error(`duplicate group ${options.id}`);
|
||||
}
|
||||
|
||||
if (!id) {
|
||||
|
203
packages/dockview/src/dockview/dockviewGroupPanel.ts
Normal file
203
packages/dockview/src/dockview/dockviewGroupPanel.ts
Normal file
@ -0,0 +1,203 @@
|
||||
import { DockviewApi } from '../api/component.api';
|
||||
import { DockviewPanelApiImpl } from '../api/groupPanelApi';
|
||||
import { Event } from '../events';
|
||||
import {
|
||||
GroupPanelUpdateEvent,
|
||||
GroupviewPanelState,
|
||||
IGroupPanel,
|
||||
IGroupPanelInitParameters,
|
||||
} from '../groupview/groupPanel';
|
||||
import { GroupChangeKind } from '../groupview/groupview';
|
||||
import { GroupviewPanel } from '../groupview/groupviewPanel';
|
||||
import { CompositeDisposable, MutableDisposable } from '../lifecycle';
|
||||
import { Parameters } from '../panel/types';
|
||||
import { IGroupPanelView } from './defaultGroupPanelView';
|
||||
|
||||
export class DockviewGroupPanel
|
||||
extends CompositeDisposable
|
||||
implements IGroupPanel {
|
||||
private readonly mutableDisposable = new MutableDisposable();
|
||||
|
||||
readonly api: DockviewPanelApiImpl;
|
||||
private _group: GroupviewPanel | undefined;
|
||||
private _params?: Parameters;
|
||||
|
||||
readonly onDidStateChange: Event<void>;
|
||||
|
||||
private _view?: IGroupPanelView;
|
||||
|
||||
private _title: string;
|
||||
private _suppressClosable: boolean;
|
||||
|
||||
get title() {
|
||||
return this._title;
|
||||
}
|
||||
|
||||
get suppressClosable() {
|
||||
return this._suppressClosable;
|
||||
}
|
||||
|
||||
get group(): GroupviewPanel | undefined {
|
||||
return this._group;
|
||||
}
|
||||
|
||||
get view() {
|
||||
return this._view;
|
||||
}
|
||||
|
||||
constructor(
|
||||
public readonly id: string,
|
||||
private readonly containerApi: DockviewApi
|
||||
) {
|
||||
super();
|
||||
this._suppressClosable = false;
|
||||
this._title = '';
|
||||
|
||||
this.api = new DockviewPanelApiImpl(this, this._group);
|
||||
this.onDidStateChange = this.api.onDidStateChange;
|
||||
|
||||
this.addDisposables(
|
||||
this.api.onActiveChange(() => {
|
||||
this.containerApi.setActivePanel(this);
|
||||
}),
|
||||
this.api.onDidTitleChange((event) => {
|
||||
const title = event.title;
|
||||
this.update({ params: { title } });
|
||||
})
|
||||
);
|
||||
}
|
||||
|
||||
public init(params: IGroupPanelInitParameters): void {
|
||||
this._params = params.params;
|
||||
this._view = params.view;
|
||||
|
||||
this._title = params.title;
|
||||
this._suppressClosable = params.suppressClosable || false;
|
||||
|
||||
if (params.state) {
|
||||
this.api.setState(params.state);
|
||||
}
|
||||
|
||||
this.view?.init({
|
||||
...params,
|
||||
api: this.api,
|
||||
containerApi: this.containerApi,
|
||||
});
|
||||
}
|
||||
|
||||
focus() {
|
||||
this.api._onFocusEvent.fire();
|
||||
}
|
||||
|
||||
public setDirty(isDirty: boolean) {
|
||||
this.api._onDidDirtyChange.fire(isDirty);
|
||||
}
|
||||
|
||||
public close(): Promise<boolean> {
|
||||
if (this.api.tryClose) {
|
||||
return this.api.tryClose();
|
||||
}
|
||||
|
||||
return Promise.resolve(true);
|
||||
}
|
||||
|
||||
public toJSON(): GroupviewPanelState {
|
||||
const state = this.api.getState();
|
||||
|
||||
return {
|
||||
id: this.id,
|
||||
view: this.view!.toJSON(),
|
||||
params:
|
||||
Object.keys(this._params || {}).length > 0
|
||||
? this._params
|
||||
: undefined,
|
||||
title: this._params?.title as string,
|
||||
suppressClosable: this._params?.suppressClosable,
|
||||
state: state && Object.keys(state).length > 0 ? state : undefined,
|
||||
};
|
||||
}
|
||||
|
||||
public update(event: GroupPanelUpdateEvent): void {
|
||||
const params = event.params as IGroupPanelInitParameters;
|
||||
|
||||
const didTitleChange =
|
||||
typeof params.title === 'string' &&
|
||||
params.title !== this._params?.title;
|
||||
const didSuppressChangableClose =
|
||||
typeof params.suppressClosable === 'boolean' &&
|
||||
params.suppressClosable !== this._params?.suppressClosable;
|
||||
|
||||
this._params = {
|
||||
...(this._params || {}),
|
||||
...event.params.params,
|
||||
};
|
||||
|
||||
if (didTitleChange) {
|
||||
this.api._titleChanged.fire({ title: params.title });
|
||||
}
|
||||
|
||||
if (didSuppressChangableClose) {
|
||||
this.api._suppressClosableChanged.fire({
|
||||
suppressClosable: !!params.suppressClosable,
|
||||
});
|
||||
}
|
||||
|
||||
this.view?.update({
|
||||
params: {
|
||||
params: this._params,
|
||||
title: this.title,
|
||||
suppressClosable: this.suppressClosable,
|
||||
},
|
||||
});
|
||||
}
|
||||
|
||||
public updateParentGroup(group: GroupviewPanel, isGroupActive: boolean) {
|
||||
this._group = group;
|
||||
this.api.group = group;
|
||||
|
||||
this.mutableDisposable.value = this._group.group.onDidGroupChange(
|
||||
(ev) => {
|
||||
if (ev.kind === GroupChangeKind.GROUP_ACTIVE) {
|
||||
const isVisible = !!this._group?.group.isPanelActive(this);
|
||||
this.api._onDidActiveChange.fire({
|
||||
isActive: isGroupActive && isVisible,
|
||||
});
|
||||
this.api._onDidVisibilityChange.fire({
|
||||
isVisible,
|
||||
});
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
const isPanelVisible = this._group.group.isPanelActive(this);
|
||||
|
||||
this.api._onDidActiveChange.fire({
|
||||
isActive: isGroupActive && isPanelVisible,
|
||||
});
|
||||
this.api._onDidVisibilityChange.fire({
|
||||
isVisible: isPanelVisible,
|
||||
});
|
||||
|
||||
this.view?.updateParentGroup(
|
||||
this._group,
|
||||
this._group.group.isPanelActive(this)
|
||||
);
|
||||
}
|
||||
|
||||
public layout(width: number, height: number) {
|
||||
// the obtain the correct dimensions of the content panel we must deduct the tab height
|
||||
this.api._onDidPanelDimensionChange.fire({
|
||||
width,
|
||||
height: height - (this.group?.group.tabHeight || 0),
|
||||
});
|
||||
|
||||
this.view?.layout(width, height);
|
||||
}
|
||||
|
||||
public dispose() {
|
||||
this.api.dispose();
|
||||
this.mutableDisposable.dispose();
|
||||
|
||||
this.view?.dispose();
|
||||
}
|
||||
}
|
@ -97,15 +97,15 @@ export abstract class BasePanelView<T extends PanelApiImpl>
|
||||
this.part = this.getComponent();
|
||||
}
|
||||
|
||||
update(params: PanelUpdateEvent) {
|
||||
update(event: PanelUpdateEvent) {
|
||||
this.params = {
|
||||
...this.params,
|
||||
params: {
|
||||
...this.params?.params,
|
||||
...params.params,
|
||||
...event.params,
|
||||
},
|
||||
};
|
||||
this.part?.update(this.params.params);
|
||||
this.part?.update({ params: this.params.params });
|
||||
}
|
||||
|
||||
toJSON(): BasePanelViewState {
|
||||
|
@ -1,16 +1,15 @@
|
||||
import { DockviewPanelApiImpl, DockviewPanelApi } from '../api/groupPanelApi';
|
||||
import { DockviewPanelApi } from '../api/groupPanelApi';
|
||||
import { Event } from '../events';
|
||||
import {
|
||||
MutableDisposable,
|
||||
CompositeDisposable,
|
||||
IDisposable,
|
||||
} from '../lifecycle';
|
||||
import { IDisposable } from '../lifecycle';
|
||||
import { HeaderPartInitParameters } from './types';
|
||||
import { IPanel, PanelInitParameters, PanelUpdateEvent } from '../panel/types';
|
||||
import { DockviewApi } from '../api/component.api';
|
||||
import {
|
||||
IPanel,
|
||||
PanelInitParameters,
|
||||
PanelUpdateEvent,
|
||||
Parameters,
|
||||
} from '../panel/types';
|
||||
import { GroupviewPanel } from './groupviewPanel';
|
||||
import { GroupChangeKind } from './groupview';
|
||||
import { IGroupPanelView } from '../react/dockview/v2/defaultGroupPanelView';
|
||||
import { IGroupPanelView } from '../dockview/defaultGroupPanelView';
|
||||
|
||||
export interface IGroupPanelInitParameters
|
||||
extends PanelInitParameters,
|
||||
@ -18,193 +17,32 @@ export interface IGroupPanelInitParameters
|
||||
view: IGroupPanelView;
|
||||
}
|
||||
|
||||
export type GroupPanelUpdateEvent = PanelUpdateEvent<{
|
||||
params?: Parameters;
|
||||
title?: string;
|
||||
suppressClosable?: boolean;
|
||||
}>;
|
||||
|
||||
export interface IGroupPanel extends IDisposable, IPanel {
|
||||
readonly view?: IGroupPanelView;
|
||||
readonly group?: GroupviewPanel;
|
||||
readonly api: DockviewPanelApi;
|
||||
readonly params?: IGroupPanelInitParameters;
|
||||
readonly title: string;
|
||||
readonly suppressClosable: boolean;
|
||||
updateParentGroup(group: GroupviewPanel, isGroupActive: boolean): void;
|
||||
setDirty(isDirty: boolean): void;
|
||||
close?(): Promise<boolean>;
|
||||
init(params: IGroupPanelInitParameters): void;
|
||||
onDidStateChange: Event<void>;
|
||||
toJSON(): GroupviewPanelState;
|
||||
update(event: GroupPanelUpdateEvent): void;
|
||||
}
|
||||
|
||||
export interface GroupviewPanelState {
|
||||
id: string;
|
||||
view?: any;
|
||||
params?: { [key: string]: any };
|
||||
title: string;
|
||||
params?: { [key: string]: any };
|
||||
suppressClosable?: boolean;
|
||||
state?: { [key: string]: any };
|
||||
}
|
||||
|
||||
export class GroupPanel extends CompositeDisposable implements IGroupPanel {
|
||||
private readonly mutableDisposable = new MutableDisposable();
|
||||
|
||||
readonly api: DockviewPanelApiImpl;
|
||||
private _group: GroupviewPanel | undefined;
|
||||
private _params?: IGroupPanelInitParameters;
|
||||
|
||||
readonly onDidStateChange: Event<void>;
|
||||
|
||||
private _view?: IGroupPanelView;
|
||||
|
||||
get params() {
|
||||
return this._params;
|
||||
}
|
||||
|
||||
get group(): GroupviewPanel | undefined {
|
||||
return this._group;
|
||||
}
|
||||
|
||||
get view() {
|
||||
return this._view;
|
||||
}
|
||||
|
||||
constructor(
|
||||
public readonly id: string,
|
||||
private readonly containerApi: DockviewApi
|
||||
) {
|
||||
super();
|
||||
this.api = new DockviewPanelApiImpl(this, this._group);
|
||||
this.onDidStateChange = this.api.onDidStateChange;
|
||||
|
||||
this.addDisposables(
|
||||
this.api.onActiveChange(() => {
|
||||
this.containerApi.setActivePanel(this);
|
||||
}),
|
||||
this.api.onDidTitleChange((event) => {
|
||||
const title = event.title;
|
||||
this.update({ params: { title } });
|
||||
})
|
||||
);
|
||||
}
|
||||
|
||||
focus() {
|
||||
this.api._onFocusEvent.fire();
|
||||
}
|
||||
|
||||
public setDirty(isDirty: boolean) {
|
||||
this.api._onDidDirtyChange.fire(isDirty);
|
||||
}
|
||||
|
||||
public close(): Promise<boolean> {
|
||||
if (this.api.tryClose) {
|
||||
return this.api.tryClose();
|
||||
}
|
||||
|
||||
return Promise.resolve(true);
|
||||
}
|
||||
|
||||
public toJSON(): GroupviewPanelState {
|
||||
const params = this._params?.params;
|
||||
const state = this.api.getState();
|
||||
|
||||
return {
|
||||
id: this.id,
|
||||
view: this.view!.toJSON(),
|
||||
params:
|
||||
params && Object.keys(params).length > 0 ? params : undefined,
|
||||
title: this._params?.title as string,
|
||||
suppressClosable: this._params?.suppressClosable,
|
||||
state: state && Object.keys(state).length > 0 ? state : undefined,
|
||||
};
|
||||
}
|
||||
|
||||
public update(params: PanelUpdateEvent<IGroupPanelInitParameters>): void {
|
||||
let didTitleChange = false;
|
||||
let didSuppressChangableClose = false;
|
||||
|
||||
const innerParams = params.params as IGroupPanelInitParameters;
|
||||
|
||||
if (this._params) {
|
||||
didTitleChange = this._params.title !== innerParams.title;
|
||||
didSuppressChangableClose =
|
||||
this._params.suppressClosable !== innerParams.suppressClosable;
|
||||
|
||||
this._params.params = {
|
||||
...(this._params?.params || {}),
|
||||
...params,
|
||||
};
|
||||
}
|
||||
|
||||
if (didTitleChange) {
|
||||
this.api._titleChanged.fire({ title: innerParams.title });
|
||||
}
|
||||
|
||||
if (didSuppressChangableClose) {
|
||||
this.api._suppressClosableChanged.fire({
|
||||
suppressClosable: !!innerParams.suppressClosable,
|
||||
});
|
||||
}
|
||||
|
||||
this.view?.update(params);
|
||||
}
|
||||
|
||||
public init(params: IGroupPanelInitParameters): void {
|
||||
this._params = params;
|
||||
this._view = params.view;
|
||||
|
||||
if (params.state) {
|
||||
this.api.setState(params.state);
|
||||
}
|
||||
|
||||
this.view?.init({
|
||||
...params,
|
||||
api: this.api,
|
||||
containerApi: this.containerApi,
|
||||
});
|
||||
}
|
||||
|
||||
public updateParentGroup(group: GroupviewPanel, isGroupActive: boolean) {
|
||||
this._group = group;
|
||||
this.api.group = group;
|
||||
|
||||
this.mutableDisposable.value = this._group.group.onDidGroupChange(
|
||||
(ev) => {
|
||||
if (ev.kind === GroupChangeKind.GROUP_ACTIVE) {
|
||||
const isVisible = !!this._group?.group.isPanelActive(this);
|
||||
this.api._onDidActiveChange.fire({
|
||||
isActive: isGroupActive && isVisible,
|
||||
});
|
||||
this.api._onDidVisibilityChange.fire({
|
||||
isVisible,
|
||||
});
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
const isPanelVisible = this._group.group.isPanelActive(this);
|
||||
|
||||
this.api._onDidActiveChange.fire({
|
||||
isActive: isGroupActive && isPanelVisible,
|
||||
});
|
||||
this.api._onDidVisibilityChange.fire({
|
||||
isVisible: isPanelVisible,
|
||||
});
|
||||
|
||||
this.view?.updateParentGroup(
|
||||
this._group,
|
||||
this._group.group.isPanelActive(this)
|
||||
);
|
||||
}
|
||||
|
||||
public layout(width: number, height: number) {
|
||||
// the obtain the correct dimensions of the content panel we must deduct the tab height
|
||||
this.api._onDidPanelDimensionChange.fire({
|
||||
width,
|
||||
height: height - (this.group?.group.tabHeight || 0),
|
||||
});
|
||||
|
||||
this.view?.layout(width, height);
|
||||
}
|
||||
|
||||
public dispose() {
|
||||
this.api.dispose();
|
||||
this.mutableDisposable.dispose();
|
||||
|
||||
this.view?.dispose();
|
||||
}
|
||||
}
|
||||
|
@ -1,14 +1,11 @@
|
||||
import { DockviewComponent } from '../dockview/dockviewComponent';
|
||||
import {
|
||||
GroupPanel,
|
||||
GroupviewPanelState,
|
||||
IGroupPanel,
|
||||
} from '../groupview/groupPanel';
|
||||
import { GroupviewPanelState, IGroupPanel } from '../groupview/groupPanel';
|
||||
import { DockviewGroupPanel } from '../dockview/dockviewGroupPanel';
|
||||
import { IPanelDeserializer } from '../dockview/deserializer';
|
||||
import { createComponent } from '../panel/componentFactory';
|
||||
import { DockviewApi } from '../api/component.api';
|
||||
import { DefaultTab } from '../dockview/components/tab/defaultTab';
|
||||
import { DefaultGroupPanelView } from './dockview/v2/defaultGroupPanelView';
|
||||
import { DefaultGroupPanelView } from '../dockview/defaultGroupPanelView';
|
||||
|
||||
export class ReactPanelDeserialzier implements IPanelDeserializer {
|
||||
constructor(private readonly layout: DockviewComponent) {}
|
||||
@ -40,7 +37,10 @@ export class ReactPanelDeserialzier implements IPanelDeserializer {
|
||||
: new DefaultTab(),
|
||||
});
|
||||
|
||||
const panel = new GroupPanel(panelId, new DockviewApi(this.layout));
|
||||
const panel = new DockviewGroupPanel(
|
||||
panelId,
|
||||
new DockviewApi(this.layout)
|
||||
);
|
||||
|
||||
panel.init({
|
||||
view,
|
||||
|
@ -27,12 +27,10 @@ export interface ReactContentPartContext {
|
||||
export class ReactPanelContentPart implements IContentRenderer {
|
||||
private _element: HTMLElement;
|
||||
private part?: ReactPart<IDockviewPanelProps>;
|
||||
private _group: GroupviewPanel | undefined;
|
||||
//
|
||||
private _actionsElement: HTMLElement;
|
||||
private actionsPart?: ReactPart<any>;
|
||||
|
||||
private parameters: GroupPanelContentPartInitParameters | undefined;
|
||||
private _group: GroupviewPanel | undefined;
|
||||
|
||||
// private hostedContainer: HostedContainer;
|
||||
|
||||
@ -72,29 +70,15 @@ export class ReactPanelContentPart implements IContentRenderer {
|
||||
}
|
||||
|
||||
focus() {
|
||||
// this._element.focus();
|
||||
// TODO
|
||||
}
|
||||
|
||||
public init(parameters: GroupPanelContentPartInitParameters): void {
|
||||
this.parameters = parameters;
|
||||
|
||||
// const api = parameters.api;
|
||||
|
||||
// api.onDidVisibilityChange((event) => {
|
||||
// const { isVisible } = event;
|
||||
|
||||
// if (isVisible) {
|
||||
// this.hostedContainer.show();
|
||||
// } else {
|
||||
// this.hostedContainer.hide();
|
||||
// }
|
||||
// });
|
||||
|
||||
const context: ReactContentPartContext = {
|
||||
api: parameters.api,
|
||||
containerApi: parameters.containerApi,
|
||||
actionsPortalElement: this._actionsElement,
|
||||
tabPortalElement: this.parameters.tab,
|
||||
tabPortalElement: parameters.tab,
|
||||
};
|
||||
|
||||
this.part = new ReactPart(
|
||||
@ -116,12 +100,8 @@ export class ReactPanelContentPart implements IContentRenderer {
|
||||
};
|
||||
}
|
||||
|
||||
public update(params: PanelUpdateEvent) {
|
||||
if (this.parameters) {
|
||||
this.parameters.params = params.params;
|
||||
}
|
||||
|
||||
this.part?.update({ params: this.parameters?.params || {} });
|
||||
public update(event: PanelUpdateEvent) {
|
||||
this.part?.update(event.params);
|
||||
}
|
||||
|
||||
public updateParentGroup(
|
||||
|
@ -11,7 +11,6 @@ import { IGroupPanelBaseProps } from './dockview';
|
||||
export class ReactPanelHeaderPart implements ITabRenderer {
|
||||
private _element: HTMLElement;
|
||||
private part?: ReactPart<IGroupPanelBaseProps>;
|
||||
private parameters: GroupPanelPartInitParameters | undefined;
|
||||
|
||||
get element() {
|
||||
return this._element;
|
||||
@ -30,8 +29,6 @@ export class ReactPanelHeaderPart implements ITabRenderer {
|
||||
}
|
||||
|
||||
public init(parameters: GroupPanelPartInitParameters): void {
|
||||
this.parameters = parameters;
|
||||
|
||||
this.part = new ReactPart(
|
||||
this.element,
|
||||
this.reactPortalStore,
|
||||
@ -45,14 +42,7 @@ export class ReactPanelHeaderPart implements ITabRenderer {
|
||||
}
|
||||
|
||||
public update(event: PanelUpdateEvent) {
|
||||
if (this.parameters) {
|
||||
this.parameters.params = {
|
||||
...this.parameters?.params,
|
||||
...event.params,
|
||||
};
|
||||
}
|
||||
|
||||
this.part?.update({ params: this.parameters?.params || {} });
|
||||
this.part?.update(event.params);
|
||||
}
|
||||
|
||||
public toJSON() {
|
||||
|
@ -4,7 +4,7 @@ import {
|
||||
ViewFactoryData,
|
||||
} from '../../../dockview/options';
|
||||
import { ReactPortalStore } from '../../react';
|
||||
import { DefaultGroupPanelView } from './defaultGroupPanelView';
|
||||
import { DefaultGroupPanelView } from '../../../dockview/defaultGroupPanelView';
|
||||
import { ReactContentRenderer } from './reactContentRenderer';
|
||||
|
||||
export class ReactGroupPanelView extends DefaultGroupPanelView {
|
||||
|
Loading…
x
Reference in New Issue
Block a user