mirror of
https://github.com/alibaba/lowcode-engine.git
synced 2026-01-18 21:38:14 +00:00
增加对钉住状态的本地存储
Link: https://code.aone.alibaba-inc.com/ali-lowcode/ali-lowcode-engine/codereview/6694701 * feat: 大纲树面板提供钉住状态记忆
This commit is contained in:
parent
a6d4747e20
commit
c2f7d9196e
@ -25,7 +25,8 @@
|
|||||||
"power-di": "^2.2.4",
|
"power-di": "^2.2.4",
|
||||||
"react": "^16",
|
"react": "^16",
|
||||||
"react-dom": "^16.7.0",
|
"react-dom": "^16.7.0",
|
||||||
"store": "^2.0.12"
|
"store": "^2.0.12",
|
||||||
|
"zen-logger": "^1.1.0"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@alib/build-scripts": "^0.1.18",
|
"@alib/build-scripts": "^0.1.18",
|
||||||
|
|||||||
@ -13,6 +13,7 @@ import {
|
|||||||
} from '@ali/lowcode-types';
|
} from '@ali/lowcode-types';
|
||||||
import { globalLocale } from './intl';
|
import { globalLocale } from './intl';
|
||||||
import * as utils from './utils';
|
import * as utils from './utils';
|
||||||
|
import Preference from './utils/preference';
|
||||||
import { obx } from './utils';
|
import { obx } from './utils';
|
||||||
import { AssetsJson, AssetLoader } from '@ali/lowcode-utils';
|
import { AssetsJson, AssetLoader } from '@ali/lowcode-utils';
|
||||||
|
|
||||||
@ -33,6 +34,7 @@ export declare interface Editor extends StrictEventEmitter<EventEmitter, GlobalE
|
|||||||
prependListener(event: string | symbol, listener: (...args: any[]) => void): this;
|
prependListener(event: string | symbol, listener: (...args: any[]) => void): this;
|
||||||
prependOnceListener(event: string | symbol, listener: (...args: any[]) => void): this;
|
prependOnceListener(event: string | symbol, listener: (...args: any[]) => void): this;
|
||||||
eventNames(): Array<string | symbol>;
|
eventNames(): Array<string | symbol>;
|
||||||
|
getPreference(): Preference;
|
||||||
}
|
}
|
||||||
|
|
||||||
export class Editor extends (EventEmitter as any) implements IEditor {
|
export class Editor extends (EventEmitter as any) implements IEditor {
|
||||||
@ -46,6 +48,12 @@ export class Editor extends (EventEmitter as any) implements IEditor {
|
|||||||
}
|
}
|
||||||
|
|
||||||
readonly utils = utils;
|
readonly utils = utils;
|
||||||
|
/**
|
||||||
|
* used to store preferences
|
||||||
|
*
|
||||||
|
* @memberof Editor
|
||||||
|
*/
|
||||||
|
readonly preference = new Preference();
|
||||||
|
|
||||||
private hooks: HookConfig[] = [];
|
private hooks: HookConfig[] = [];
|
||||||
|
|
||||||
@ -176,6 +184,10 @@ export class Editor extends (EventEmitter as any) implements IEditor {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
getPreference() {
|
||||||
|
return this.preference;
|
||||||
|
}
|
||||||
|
|
||||||
initHooks = (hooks: HookConfig[]) => {
|
initHooks = (hooks: HookConfig[]) => {
|
||||||
this.hooks = hooks.map((hook) => ({
|
this.hooks = hooks.map((hook) => ({
|
||||||
...hook,
|
...hook,
|
||||||
|
|||||||
@ -4,3 +4,4 @@ export * from './obx';
|
|||||||
export * from './request';
|
export * from './request';
|
||||||
export * from './focus-tracker';
|
export * from './focus-tracker';
|
||||||
export * from './control';
|
export * from './control';
|
||||||
|
export * from './preference';
|
||||||
|
|||||||
7
packages/editor-core/src/utils/logger.ts
Normal file
7
packages/editor-core/src/utils/logger.ts
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
import Logger, { Level } from 'zen-logger';
|
||||||
|
|
||||||
|
export { Logger };
|
||||||
|
|
||||||
|
export function getLogger(config: { level: Level, bizName: string }): Logger {
|
||||||
|
return new Logger(config);
|
||||||
|
}
|
||||||
58
packages/editor-core/src/utils/preference.ts
Normal file
58
packages/editor-core/src/utils/preference.ts
Normal file
@ -0,0 +1,58 @@
|
|||||||
|
import store from 'store';
|
||||||
|
import { getLogger } from './logger';
|
||||||
|
|
||||||
|
const logger = getLogger({ level: 'log', bizName: 'Preference' });
|
||||||
|
const STORAGE_KEY_PREFIX = 'ale';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* used to store user preferences, such as pinned status of a pannel.
|
||||||
|
* save to local storage.
|
||||||
|
*
|
||||||
|
* @class PreferenceStore
|
||||||
|
*/
|
||||||
|
export default class Preference {
|
||||||
|
getStorageKey(key: string, module?: string): string {
|
||||||
|
const moduleKey = module || '__inner__';
|
||||||
|
return `${STORAGE_KEY_PREFIX}_${moduleKey}.${key}`;
|
||||||
|
}
|
||||||
|
|
||||||
|
set(key: string, value:any, module?: string) {
|
||||||
|
if (!key || typeof key !== 'string' || key.length === 0) {
|
||||||
|
logger.error('Invalid key when setting preference', key);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const storageKey = this.getStorageKey(key, module);
|
||||||
|
logger.log('storageKey:', storageKey, 'set with value:', value);
|
||||||
|
store.set(storageKey, value);
|
||||||
|
}
|
||||||
|
|
||||||
|
get(key: string, module: string) : any {
|
||||||
|
if (!key || typeof key !== 'string' || key.length === 0) {
|
||||||
|
logger.error('Invalid key when getting from preference', key);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
const storageKey = this.getStorageKey(key, module);
|
||||||
|
const result = store.get(storageKey);
|
||||||
|
logger.log('storageKey:', storageKey, 'get with result:', result);
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* check if local storage contain certain key
|
||||||
|
*
|
||||||
|
* @param {string} key
|
||||||
|
* @param {string} module
|
||||||
|
* @returns {boolean}
|
||||||
|
* @memberof Preference
|
||||||
|
*/
|
||||||
|
contains(key: string, module: string) : boolean {
|
||||||
|
if (!key || typeof key !== 'string' || key.length === 0) {
|
||||||
|
logger.error('Invalid key when getting from preference', key);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
const storageKey = this.getStorageKey(key, module);
|
||||||
|
const result = store.get(storageKey);
|
||||||
|
|
||||||
|
return !(result === undefined || result === null);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@ -18,15 +18,8 @@ export default class PanelOperationRow extends Component<{ panel: Panel }> {
|
|||||||
if (!current) {
|
if (!current) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (panel?.parent?.name === 'leftFloatArea') {
|
|
||||||
panel.skeleton.leftFloatArea.remove(current);
|
panel.skeleton.toggleFloatStatus(panel);
|
||||||
panel.skeleton.leftFixedArea.add(current);
|
|
||||||
panel.skeleton.leftFixedArea.container.active(current);
|
|
||||||
} else {
|
|
||||||
panel.skeleton.leftFixedArea.remove(current);
|
|
||||||
panel.skeleton.leftFloatArea.add(current);
|
|
||||||
panel.skeleton.leftFloatArea.container.active(current);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
render() {
|
render() {
|
||||||
|
|||||||
@ -1,4 +1,4 @@
|
|||||||
import { Editor } from '@ali/lowcode-editor-core';
|
import { Editor, action, makeObservable } from '@ali/lowcode-editor-core';
|
||||||
import {
|
import {
|
||||||
DockConfig,
|
DockConfig,
|
||||||
PanelConfig,
|
PanelConfig,
|
||||||
@ -59,6 +59,7 @@ export class Skeleton {
|
|||||||
readonly stages: Area<StageConfig, Stage>;
|
readonly stages: Area<StageConfig, Stage>;
|
||||||
|
|
||||||
constructor(readonly editor: Editor) {
|
constructor(readonly editor: Editor) {
|
||||||
|
makeObservable(this);
|
||||||
this.leftArea = new Area(
|
this.leftArea = new Area(
|
||||||
this,
|
this,
|
||||||
'leftArea',
|
'leftArea',
|
||||||
@ -157,6 +158,47 @@ export class Skeleton {
|
|||||||
});
|
});
|
||||||
|
|
||||||
this.setupPlugins();
|
this.setupPlugins();
|
||||||
|
this.setupEvents();
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* setup events
|
||||||
|
*
|
||||||
|
* @memberof Skeleton
|
||||||
|
*/
|
||||||
|
setupEvents() {
|
||||||
|
// adjust pinned status when panel shown
|
||||||
|
this.editor.on('skeleton.panel.show', (panelName, panel) => {
|
||||||
|
const panelNameKey = `${panelName}-pinned-status-isFloat`;
|
||||||
|
const isInFloatAreaPreferenceExists = this.editor?.getPreference()?.contains(panelNameKey, 'skeleton');
|
||||||
|
if (isInFloatAreaPreferenceExists) {
|
||||||
|
const isInFloatAreaFromPreference = this.editor?.getPreference()?.get(panelNameKey, 'skeleton');
|
||||||
|
const currentIsInFloatArea = panel?.isInFloatArea();
|
||||||
|
if (isInFloatAreaFromPreference !== currentIsInFloatArea) {
|
||||||
|
this.toggleFloatStatus(panel);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* set isFloat status for panel
|
||||||
|
*
|
||||||
|
* @param {*} panel
|
||||||
|
* @memberof Skeleton
|
||||||
|
*/
|
||||||
|
@action
|
||||||
|
toggleFloatStatus(panel: Panel) {
|
||||||
|
const isFloat = panel?.parent?.name === 'leftFloatArea';
|
||||||
|
if (isFloat) {
|
||||||
|
this.leftFloatArea.remove(panel);
|
||||||
|
this.leftFixedArea.add(panel);
|
||||||
|
this.leftFixedArea.container.active(panel);
|
||||||
|
} else {
|
||||||
|
this.leftFixedArea.remove(panel);
|
||||||
|
this.leftFloatArea.add(panel);
|
||||||
|
this.leftFloatArea.container.active(panel);
|
||||||
|
}
|
||||||
|
this.editor?.getPreference()?.set(`${panel.name}-pinned-status-isFloat`, !isFloat, 'skeleton');
|
||||||
}
|
}
|
||||||
|
|
||||||
buildFromConfig(config?: EditorConfig, components: PluginClassSet = {}) {
|
buildFromConfig(config?: EditorConfig, components: PluginClassSet = {}) {
|
||||||
|
|||||||
@ -154,6 +154,15 @@ export default class Panel implements IWidget {
|
|||||||
getContent() {
|
getContent() {
|
||||||
return this.content;
|
return this.content;
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* check is current panel is in float area or not
|
||||||
|
*
|
||||||
|
* @returns {boolean}
|
||||||
|
* @memberof Panel
|
||||||
|
*/
|
||||||
|
isInFloatArea(): boolean {
|
||||||
|
return this.parent?.name === 'leftFloatArea';
|
||||||
|
}
|
||||||
|
|
||||||
setActive(flag: boolean) {
|
setActive(flag: boolean) {
|
||||||
if (flag === this._actived) {
|
if (flag === this._actived) {
|
||||||
@ -161,9 +170,9 @@ export default class Panel implements IWidget {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (flag) {
|
if (flag) {
|
||||||
if (this.parent.name === 'leftFloatArea') {
|
if (this.isInFloatArea()) {
|
||||||
this.skeleton.leftFixedArea.container.unactiveAll();
|
this.skeleton.leftFixedArea.container.unactiveAll();
|
||||||
} else if (this.parent.name === 'leftFixedArea') {
|
} else {
|
||||||
this.skeleton.leftFloatArea.container.unactiveAll();
|
this.skeleton.leftFloatArea.container.unactiveAll();
|
||||||
}
|
}
|
||||||
this._actived = true;
|
this._actived = true;
|
||||||
|
|||||||
@ -152,13 +152,21 @@ plugins.register((ctx: ILowCodePluginContext) => {
|
|||||||
},
|
},
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// by default in float area;
|
||||||
|
let isInFloatArea = true;
|
||||||
|
const hasPreferenceForOutline = editor?.getPreference()?.contains('outline-pane-pinned-status-isFloat', 'skeleton');
|
||||||
|
if (hasPreferenceForOutline) {
|
||||||
|
isInFloatArea = editor?.getPreference()?.get('outline-pane-pinned-status-isFloat', 'skeleton');
|
||||||
|
}
|
||||||
|
|
||||||
skeleton.add({
|
skeleton.add({
|
||||||
area: 'leftArea',
|
area: 'leftArea',
|
||||||
name: 'outlinePane',
|
name: 'outlinePane',
|
||||||
type: 'PanelDock',
|
type: 'PanelDock',
|
||||||
content: Outline,
|
content: Outline,
|
||||||
panelProps: {
|
panelProps: {
|
||||||
area: 'leftFloatArea',
|
area: isInFloatArea ? 'leftFloatArea' : 'leftFixedArea',
|
||||||
keepVisibleWhileDragging: true,
|
keepVisibleWhileDragging: true,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user