From 0aafafe6eaa100ba2a3e514cba299af63ae9acb2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=8A=9B=E7=9A=93?= Date: Wed, 23 Sep 2020 21:38:58 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20i18n=20=E7=BB=91=E5=AE=9A=E5=8F=98?= =?UTF-8?q?=E9=87=8F=E5=90=8E=E6=B6=88=E5=A4=B1=20fix:=20block=20=E5=8C=BA?= =?UTF-8?q?=E5=9D=97=E7=BB=84=E4=BB=B6=E6=97=A0=E6=B3=95=E6=98=BE=E7=A4=BA?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/deep-value-parser.ts | 5 +- packages/editor-preset-vision/src/editor.ts | 3 +- .../editor-preset-vision/src/utils/index.ts | 3 + packages/react-renderer/src/renderer/base.tsx | 2 +- .../react-simulator-renderer/.eslintrc.js | 21 +- .../react-simulator-renderer/src/renderer.ts | 180 ++++++++++-------- 6 files changed, 118 insertions(+), 96 deletions(-) create mode 100644 packages/editor-preset-vision/src/utils/index.ts diff --git a/packages/editor-preset-vision/src/deep-value-parser.ts b/packages/editor-preset-vision/src/deep-value-parser.ts index 17a309807..5d15d9c0a 100644 --- a/packages/editor-preset-vision/src/deep-value-parser.ts +++ b/packages/editor-preset-vision/src/deep-value-parser.ts @@ -3,10 +3,7 @@ import { isJSSlot, isI18nData, isJSExpression } from '@ali/lowcode-types'; import { isPlainObject } from '@ali/lowcode-utils'; import i18nUtil from './i18n-util'; import { editor } from './editor'; - -function isVariable(obj: any) { - return obj && obj.type === 'variable'; -} +import { isVariable } from './utils'; // FIXME: 表达式使用 mock 值,未来live 模式直接使用原始值 // TODO: designType diff --git a/packages/editor-preset-vision/src/editor.ts b/packages/editor-preset-vision/src/editor.ts index aeb65899c..ba718b31b 100644 --- a/packages/editor-preset-vision/src/editor.ts +++ b/packages/editor-preset-vision/src/editor.ts @@ -124,7 +124,8 @@ designer.addPropsReducer((props, node) => { newProps[item.name] = v; } // 兼容 props 中的属性为 i18n 类型,但是仅提供了一个值 - if (isUseI18NSetter(node.componentMeta.prototype, item.name) && !isI18NObject(ov)) { + if (isUseI18NSetter(node.componentMeta.prototype, item.name) && + !isI18NObject(ov) && !isVariable(ov)) { newProps[item.name] = v; } } catch (e) { diff --git a/packages/editor-preset-vision/src/utils/index.ts b/packages/editor-preset-vision/src/utils/index.ts new file mode 100644 index 000000000..c07d6ad04 --- /dev/null +++ b/packages/editor-preset-vision/src/utils/index.ts @@ -0,0 +1,3 @@ +export function isVariable(obj: any) { + return obj && obj.type === 'variable'; +} diff --git a/packages/react-renderer/src/renderer/base.tsx b/packages/react-renderer/src/renderer/base.tsx index ea685d9d8..8efa3ef79 100644 --- a/packages/react-renderer/src/renderer/base.tsx +++ b/packages/react-renderer/src/renderer/base.tsx @@ -363,7 +363,7 @@ export default class BaseRender extends PureComponent { } let child = null; - if (!isFileSchema(schema) && !!_children) { + if (/*!isFileSchema(schema) && */!!_children) { child = this.__createVirtualDom( isJSExpression(_children) ? parseExpression(_children, self) : _children, self, diff --git a/packages/react-simulator-renderer/.eslintrc.js b/packages/react-simulator-renderer/.eslintrc.js index c6815abf7..31d2e19c3 100644 --- a/packages/react-simulator-renderer/.eslintrc.js +++ b/packages/react-simulator-renderer/.eslintrc.js @@ -1,15 +1,16 @@ module.exports = { extends: 'eslint-config-ali/typescript/react', rules: { - 'react/no-multi-comp': 1, - 'no-unused-expressions': 1, - 'implicit-arrow-linebreak': 1, - 'no-nested-ternary': 1, - 'no-mixed-operators': 1, - '@typescript-eslint/no-parameter-properties': 1, - '@typescript-eslint/ban-types': 1, - 'no-shadow': 1, - 'no-prototype-builtins': 1, - 'array-callback-return': 1, + 'react/no-multi-comp': 0, + 'no-unused-expressions': 0, + 'implicit-arrow-linebreak': 0, + 'no-nested-ternary': 0, + 'no-mixed-operators': 0, + '@typescript-eslint/no-parameter-properties': 0, + '@typescript-eslint/ban-types': 0, + 'no-shadow': 0, + 'no-prototype-builtins': 0, + 'array-callback-return': 0, + '@typescript-eslint/member-ordering': 0 } } \ No newline at end of file diff --git a/packages/react-simulator-renderer/src/renderer.ts b/packages/react-simulator-renderer/src/renderer.ts index 73df54a95..10ee936d2 100644 --- a/packages/react-simulator-renderer/src/renderer.ts +++ b/packages/react-simulator-renderer/src/renderer.ts @@ -1,4 +1,4 @@ -import React, { createElement, ReactInstance, ComponentType, ReactElement, FunctionComponent } from 'react'; +import React, { createElement, ReactInstance } from 'react'; import { render as reactRender } from 'react-dom'; import { host } from './host'; import SimulatorRendererView from './renderer-view'; @@ -255,15 +255,18 @@ export class SimulatorRendererContainer implements BuiltinSimulatorRenderer { } @obx private _layout: any = null; + @computed get layout(): any { // TODO: parse layout Component return this._layout; } + set layout(value: any) { this._layout = value; } private _libraryMap: { [key: string]: string } = {}; + private buildComponents() { // TODO: remove this.createComponent this._components = buildComponents(this._libraryMap, this._componentsMap, this.createComponent.bind(this)); @@ -273,6 +276,7 @@ export class SimulatorRendererContainer implements BuiltinSimulatorRenderer { }; } @obx.ref private _components: any = {}; + @computed get components(): object { // 根据 device 选择不同组件,进行响应式 // 更好的做法是,根据 device 选择加载不同的组件资源,甚至是 simulatorUrl @@ -349,7 +353,7 @@ export class SimulatorRendererContainer implements BuiltinSimulatorRenderer { } createComponent(schema: NodeSchema): Component | null { - let _schema: any = { + const _schema: any = { ...schema, }; _schema.methods = {}; @@ -364,92 +368,19 @@ export class SimulatorRendererContainer implements BuiltinSimulatorRenderer { doc.getElementsByTagName('head')[0].appendChild(s); } - const node = host.currentDocument?.createNode(_schema); - _schema = node?.export(TransformStage.Render) || {}; + // const node = host.currentDocument?.createNode(_schema); + // _schema = node?.export(TransformStage.Render) || {}; - const processPropsSchema = (propsSchema: any, propsMap: any): any => { - if (!propsSchema) { - return {}; - } - const result = { ...propsSchema }; - const reg = /^(?:this\.props|props)\.(\S+)$/; - Object.keys(result).map((key: string) => { - if (result[key]?.type === 'JSExpression') { - const { value } = result[key]; - const matched = reg.exec(value); - if (matched) { - const propName = matched[1]; - result[key] = propsMap[propName]; - } - } else if (result[key]?.type === 'JSSlot') { - const schema = result[key].value; - result[key] = createElement(Ele, { schema, propsMap: {} }); - } - }); - - return result; - }; const renderer = this; const { componentsMap } = renderer; - class Ele extends React.Component<{ schema: any; propsMap: any }> { - private isModal: boolean; - - constructor(props: any) { - super(props); - const componentMeta = host.currentDocument?.getComponentMeta(props.schema.componentName); - if (componentMeta?.prototype?.isModal()) { - this.isModal = true; - } - } - - render() { - if (this.isModal) { - return null; - } - const { schema, propsMap } = this.props; - const Com = componentsMap[schema.componentName]; - if (!Com) { - return null; - } - let children = null; - if (schema.children && schema.children.length > 0) { - children = schema.children.map((item: any) => createElement(Ele, { schema: item, propsMap })); - } - const props = processPropsSchema(schema.props, propsMap); - const _leaf = host.currentDocument?.createNode(schema); - - return createElement(Com, { ...props, _leaf }, children); - } - } - - class Com extends React.Component { - // TODO: 暂时解决性能问题 - shouldComponentUpdate() { - return false; - } - - render() { - const { componentName } = _schema; - if (componentName === 'Component') { - let children = []; - const propsMap = this.props || {}; - if (_schema.children && Array.isArray(_schema.children)) { - children = _schema.children.map((item: any) => createElement(Ele, { schema: item, propsMap })); - } - return createElement('div', {}, children); - } else { - return createElement(Ele, { schema: _schema, propsMap: {} }); - } - } - } - - return Com; + return getComponentController(schema, componentsMap); } private _running = false; + run() { if (this._running) { return; @@ -533,7 +464,7 @@ function getNodeInstance(fiberNode: any, specId?: string): NodeInstance { + if (!propsSchema) { + return {}; + } + + const result = { ...propsSchema }; + const reg = /^(?:this\.props|props)\.(\S+)$/; + Object.keys(result).map((key: string) => { + if (result[key]?.type === 'JSExpression') { + const { value } = result[key]; + const matched = reg.exec(value); + if (matched) { + const propName = matched[1]; + result[key] = propsMap[propName]; + } + } else if (result[key]?.type === 'JSSlot') { + const schema = result[key].value; + result[key] = createElement(ComponentCreator, { schema, propsMap: {}, componentsMap }); + } + }); + + return result; +}; + +class ComponentCreator extends React.Component<{ schema: any; propsMap: any, componentsMap: any }> { + private isModal: boolean; + + constructor(props: any) { + super(props); + const componentMeta = host.currentDocument?.getComponentMeta(props.schema.componentName); + if (componentMeta?.prototype?.isModal()) { + this.isModal = true; + } + } + + render() { + if (this.isModal) { + return null; + } + const { schema, propsMap } = this.props; + const componentsMap = this.props.componentsMap; + const ComponentClass = componentsMap[schema.componentName]; + if (!ComponentClass) { + return null; + } + let children = null; + if (schema.children && schema.children.length > 0) { + children = schema.children.map((item: any) => createElement(ComponentCreator, { schema: item, propsMap, componentsMap })); + } + const props = processPropsSchema(schema.props, propsMap, componentsMap); + const _leaf = host.currentDocument?.createNode(schema); + + return createElement(ComponentClass, { ...props, _leaf }, children); + } +} + +function getComponentController(schema: NodeSchema, componentsMap: any) { + class ComponentController extends React.Component<{ schema: any }> { + renderSchema: any; + + constructor(props: any) { + super(props); + const node = host.currentDocument?.createNode(schema); + this.renderSchema = node?.export(TransformStage.Render) || {}; + } + + // TODO: 暂时解决性能问题 + shouldComponentUpdate() { + return false; + } + + render() { + const { renderSchema } = this; + const { componentName } = renderSchema; + if (componentName === 'Component') { + let children = [] as any; + const propsMap = this.props || {}; + if (renderSchema.children && Array.isArray(renderSchema.children)) { + children = renderSchema.children.map((item: any) => createElement(ComponentCreator, { schema: item, propsMap, componentsMap })); + } + return createElement('div', {}, children); + } else { + return createElement(ComponentCreator, { schema, propsMap: {}, componentsMap }); + } + } + } + return ComponentController; +} + export default new SimulatorRendererContainer();