import { inject, injectable } from 'inversify'; import { deepClone } from 'ts-toolset/dist/common/object'; import { ServicesIoc, WorkbenchIoc } from '../../../ioc'; import { MapStore, EventBus } from '../../../services'; import { EditEvents, InterfaceEvents, MapStoreKeys } from './common'; import { IEditorOptionEntity, IPropEntity } from '../../../models/base'; import { ICssDataEntity, IHtmlComponentEntity, IHtmlSchemaNode, IStyleRuleEntity } from '../../../models/html'; import { EventEditor, EventPropEntities, EventPropKeys } from '../../parts/editor/eventEditor'; import { IStyleEditor, StyleEditor, StylePropEntities, StylePropGroups } from '../../parts/editor/styleEditor'; import { IPropEditor, PropEditor } from '../../parts/editor/propEditor'; import { EditorHookParam, EditorValue } from '../../parts/editor'; import { HtmlStage } from '../../parts/htmlStage'; export interface IEditIntegrator { readonly propEditor: IPropEditor; readonly styleEditor: IStyleEditor; } @injectable() export class EditIntegrator implements IEditIntegrator { private readonly _componentStore: Map; private readonly _editorOptionStore: Map; constructor( // services @inject(ServicesIoc.Identifier.MapStore) private _mapStore: MapStore, @inject(ServicesIoc.Identifier.EventBus) private _eventBus: EventBus, // parts @inject(WorkbenchIoc.PartsIdentifier.PropEditor) private _propEditor: PropEditor, @inject(WorkbenchIoc.PartsIdentifier.StyleEditor) private _styleEditor: StyleEditor, @inject(WorkbenchIoc.PartsIdentifier.EventEditor) private _eventEditor: EventEditor, @inject(WorkbenchIoc.PartsIdentifier.HtmlStage) private _htmlStage: HtmlStage, ) { this._editorOptionStore = this._mapStore.get(MapStoreKeys.editorOptionStore)!; this._componentStore = this._mapStore.get(MapStoreKeys.componentStore)!; this._eventBus .register(EditEvents.onInitEditData, this._initEditData, { scope: this }) .register(EditEvents.onInitEditorOptions, this._initEditorOptions, { scope: this }) // PropEditor .register(EditEvents.PropEditor.onSetValues, this._propEditorSetValues, { scope: this }) .register(EditEvents.PropEditor.onCallHook, this._propEditorCallHook, { scope: this }) // StyleEditor .register(EditEvents.StyleEditor.onSetValues, this._styleEditorSetValues, { scope: this }) .register(EditEvents.StyleEditor.onCallHook, this._styleEditorCallHook, { scope: this }) .register(EditEvents.StyleEditor.loadClassList, this._loadClassList, { scope: this }) // EventEditor .register(EditEvents.EventEditor.onSetValues, this._eventEditorSetValues, { scope: this }) .register(EditEvents.EventEditor.onCallHook, this._eventEditorCallHook, { scope: this }); } get propEditor() { return this._propEditor; } get styleEditor() { return this._styleEditor; } get eventEditor() { return this._eventEditor; } /** 获取 编辑器项 配置列表 */ private _getEditorOptionlMaterial(props: IPropEntity[], values: any = {}) { return props.map(prop => ({ prop, value: values[prop.key], editorOptionEntity: prop.editorOption ? this._editorOptionStore.get(prop.editorOption.key) : undefined })); } /** 加载只需初始化一次的编辑器,编辑器配置项加载完后才能加载编辑器 */ private _initEditorOptions() { // 初始化 样式编辑器 let styleMaterials = this._getEditorOptionlMaterial(StylePropEntities); styleMaterials.length && this._styleEditor.initial(styleMaterials, { propGroups: StylePropGroups }); // 初始化 事件编辑器 let eventMaterials = this._getEditorOptionlMaterial(EventPropEntities); eventMaterials.length && this._eventEditor.initial(eventMaterials); } /** 初始化选中节点对应的编辑项数据 */ private _initEditData(data: IHtmlSchemaNode, reload: boolean = true) { // 现在框架都是用遇到什么场景用到什么点才临时处理 // 要专门把框架用到的场景全部收集起来形成通用的底层设施形成下一版框架基础 // 场景:数据副本,数据比较判断是否更新渲染(可以通过计算数据比较 规避 频繁操作硬件) // let dataCopy = deepClone(data); this._loadPropEditor(reload, data.key, deepClone(data.propData || {})); this._editStyleEditorValues(deepClone(data.cssData || {})); // this._editEventEditorValues(data); } //#region -- PropEditor /** 更新属性值 */ private _updatePropData(isRender: boolean) { if (this._htmlStage.selectedNode) { let propData: any = this._propEditor.getChangeValues(); this._eventBus.emit(InterfaceEvents.HtmlSchema.updateData, this._htmlStage.selectedNode, { propData }); } } /** 加载属性编辑器数据 */ private _loadPropEditor(reload: boolean, componentKey: string, propData: any) { if (reload) { let component = this._componentStore.get(componentKey) as IHtmlComponentEntity; if (component) { let materials = this._getEditorOptionlMaterial(component.props, propData); materials && this._propEditor.initial(materials, { data: propData, propGroups: component.propGroups }); this._eventBus.emit(EditEvents.PropEditor.onRenderEditor); } } else { this._propEditor.importValues(propData); } } /** 属性编辑器 设置值或组合值 */ private _propEditorSetValues(editorValues: EditorValue[], isRender: boolean = true) { if (this._htmlStage.selectedNode) { editorValues && this._propEditor.setValues(editorValues); this._updatePropData(isRender); } } /** 属性编辑器回调 */ private _propEditorCallHook(editorHookParams: EditorHookParam | EditorHookParam[]) { this._propEditor.callHooks(editorHookParams); } //#endregion //#region -- StyleEditor private _loadClassList(entities: IStyleRuleEntity[]) { this._styleEditor.loadClassList(entities); } private _editStyleEditorValues(data: ICssDataEntity) { this._styleEditor.importValues(data); //this._eventBus.emit(EditEvents.StyleEditor.onRenderEditor); } /** 属性编辑器 设置值或组合值 */ private _styleEditorSetValues(editorValues: EditorValue[], isRender: boolean = true) { if (this._htmlStage.selectedNode) { editorValues && this._styleEditor.setValues(editorValues); //this._updatePropData(isRender); } } /** 属性编辑器回调 */ private _styleEditorCallHook(editorHookParams: EditorHookParam | EditorHookParam[]) { this._styleEditor.callHooks(editorHookParams); } //#endregion //#region -- EventEditor private _updateEventData(isRender: boolean) { if (this._htmlStage.selectedNode) { let eventData: any = this._eventEditor.getChangeValues()[EventPropKeys.events]; this._eventBus.emit(InterfaceEvents.HtmlSchema.updateData, this._htmlStage.selectedNode, { eventData }); } } private _editEventEditorValues(data: IHtmlSchemaNode) { let eventList: any[] = []; let component = this._componentStore.get(data.key) as IHtmlComponentEntity; component && component.events && component.events.length && (eventList = component.events); this._eventEditor.importValues({ [EventPropKeys.events]: data.eventData }, eventList); //this._eventBus.emit(EditEvents.EventEditor.onRenderEditor); } /** 事件编辑器 设置值或组合值 */ private _eventEditorSetValues(editorValues: EditorValue[], isRender: boolean = true) { if (this._htmlStage.selectedNode) { editorValues && this._eventEditor.setValues(editorValues); this._updateEventData(isRender); } } /** 事件编辑器回调 */ private _eventEditorCallHook(editorHookParams: EditorHookParam | EditorHookParam[]) { this._eventEditor.callHooks(editorHookParams); } //#endregion }