fix: supports

This commit is contained in:
kangwei 2020-05-09 23:44:40 +08:00
parent d4e0898705
commit 371b84cc66
12 changed files with 118 additions and 54 deletions

View File

@ -120,7 +120,7 @@ export class SettingField extends SettingPropEntry implements SettingEntry {
// ======= compatibles for vision ======
getHotValue(): any {
// avoid View modify
let v = cloneDeep(this.getValue());
let v = cloneDeep(this.getMockOrValue());
if (v == null) {
v = this.extraProps.defaultValue;
}
@ -128,7 +128,17 @@ export class SettingField extends SettingPropEntry implements SettingEntry {
}
setHotValue(data: any) {
this.setValue(this.transducer.toNative(data));
const v = this.transducer.toNative(data);
if (this.isUseVariable()) {
const ov = this.getValue();
this.setValue({
type: 'JSExpression',
value: ov.value,
mock: v,
});
} else {
this.setValue(v);
}
this.valueChange();
}

View File

@ -101,7 +101,7 @@ export class SettingPropEntry implements SettingEntry {
*
*/
@computed getValue(): any {
let val: any = null;
let val: any = undefined;
if (this.type === 'field') {
val = this.parent.getPropValue(this.name);
}

View File

@ -46,7 +46,7 @@ export class Transducer {
setter = setter.componentName;
}
if (typeof setter === 'string') {
setter = getSetter(setter);
setter = getSetter(setter).component;
}
this.setterTransducer = combineTransducer(

View File

@ -504,7 +504,7 @@ export class Node<Schema extends NodeSchema = NodeSchema> {
const schema: any = {
...baseSchema,
props: this.document.designer.transformProps(props, this, stage),
..._extras_,
...this.document.designer.transformProps(_extras_, this, stage),
};
if (this.isParental() && this.children.size > 0) {

View File

@ -35,7 +35,16 @@ class AliGlobalLocale {
if (this._locale != null) {
return this._locale;
}
const { g_config, navigator } = window as any;
// TODO: store 1 & store 2 abstract out as custom implements
// store 1: config from window
let locale: string = getConfig('locale');
if (locale) {
return languageMap[locale] || locale.replace('_', '-');
}
// store 2: config from storage
if (hasLocalStorage(window)) {
const store = window.localStorage;
let config: any;
@ -47,20 +56,14 @@ class AliGlobalLocale {
if (config?.locale) {
return (config.locale || '').replace('_', '-');
}
} else if (g_config) {
if (g_config.locale) {
return languageMap[g_config.locale] || g_config.locale.replace('_', '-');
}
}
let locale: string = '';
// store 2: config from system
const { navigator } = window as any;
if (navigator.language) {
const lang = (navigator.language as string);
return languageMap[lang] || lang.replace('_', '-');
}
// IE10 及更低版本使用 browserLanguage
if (navigator.browserLanguage) {
} else if (navigator.browserLanguage) {
const it = navigator.browserLanguage.split('-');
locale = it[0];
if (it[1]) {
@ -116,6 +119,15 @@ class AliGlobalLocale {
}
}
function getConfig(name: string) {
const win: any = window;
return (
win[name]
|| (win.g_config || {})[name]
|| (win.pageConfig || {})[name]
);
}
function hasLocalStorage(obj: any): obj is WindowLocalStorage {
return obj.localStorage;
}

View File

@ -3,12 +3,7 @@ import { SVGIcon, IconProps } from "@ali/lowcode-utils";
export function IconConvert(props: IconProps) {
return (
<SVGIcon viewBox="0 0 1024 1024" {...props}>
<path d="M508.16 889.6C291.84 889.6 115.2 714.24 115.2 497.92 115.2 281.6 291.84 106.24 509.44 106.24c43.52 0 85.76 6.4 124.16 20.48l-10.24 30.72c-35.84-11.52-72.96-17.92-113.92-17.92-199.68 0-362.24 161.28-362.24 359.68s162.56 358.4 360.96 358.4 359.68-161.28 359.68-359.68c0-66.56-17.92-131.84-51.2-185.6L844.8 294.4c37.12 60.16 56.32 130.56 56.32 203.52-1.28 216.32-176.64 391.68-392.96 391.68z" />
<path d="M627.2 140.8m-15.36 0a15.36 15.36 0 1 0 30.72 0 15.36 15.36 0 1 0-30.72 0Z" />
<path d="M832 304.64m-15.36 0a15.36 15.36 0 1 0 30.72 0 15.36 15.36 0 1 0-30.72 0Z" />
<path d="M348.16 497.92m-35.84 0a35.84 35.84 0 1 0 71.68 0 35.84 35.84 0 1 0-71.68 0Z" fill="#35A2D4" />
<path d="M508.16 497.92m-35.84 0a35.84 35.84 0 1 0 71.68 0 35.84 35.84 0 1 0-71.68 0Z" fill="#35A2D4" />
<path d="M668.16 497.92m-35.84 0a35.84 35.84 0 1 0 71.68 0 35.84 35.84 0 1 0-71.68 0Z" fill="#35A2D4" />
<path d="M620.8 256c-12.8-12.8-32-12.8-44.8 0s-12.8 32 0 44.8l83.2 83.2H288c-19.2 0-32 12.8-32 32s12.8 32 32 32h448c6.4 0 32 0 32-32 0-19.2-6.4-25.6-6.4-25.6L620.8 256zM736 576H288c-6.4 0-32 0-32 32 0 19.2 6.4 25.6 6.4 25.6L403.2 768c12.8 12.8 32 12.8 44.8 0s12.8-32 0-44.8L364.8 640H736c19.2 0 32-12.8 32-32s-12.8-32-32-32zM512 64C262.4 64 64 262.4 64 512s198.4 448 448 448 448-198.4 448-448S761.6 64 512 64z m0 832c-211.2 0-384-172.8-384-384s172.8-384 384-384 384 172.8 384 384-172.8 384-384 384z" />
</SVGIcon>
);
}

View File

@ -13,7 +13,7 @@ export default function(metadata: TransformedComponentMetadata): TransformedComp
name: 'children',
title: { type: 'i18n', 'zh-CN': '内容设置', 'en-US': 'Content' },
setter: {
componentName: 'MixinSetter',
componentName: 'MixedSetter',
props: {
// TODO:
setters: [
@ -41,11 +41,11 @@ export default function(metadata: TransformedComponentMetadata): TransformedComp
};
}
const { props, events = {}, styles } = configure as any;
const { props, supports = {} } = configure as any;
const isRoot: boolean = componentName === 'Page' || componentName === 'Component';
const eventsDefinition: any[] = [];
const supportedLifecycles =
events.supportedLifecycles ||
supports.lifecycles ||
(isRoot
? /*[
{
@ -73,11 +73,11 @@ export default function(metadata: TransformedComponentMetadata): TransformedComp
list: supportedLifecycles.map((event: any) => (typeof event === 'string' ? { name: event } : event)),
});
}
if (events.supportedEvents) {
if (supports.events) {
eventsDefinition.push({
type: 'events',
title: '事件',
list: (events.supportedEvents || []).map((event: any) => (typeof event === 'string' ? { name: event } : event)),
list: (supports.events || []).map((event: any) => (typeof event === 'string' ? { name: event } : event)),
});
}
// 通用设置
@ -150,14 +150,14 @@ export default function(metadata: TransformedComponentMetadata): TransformedComp
items: propsGroup,
},
];
if (styles?.supportClassName) {
if (supports.className) {
stylesGroup.push({
name: 'className',
title: { type: 'i18n', 'zh-CN': '类名绑定', 'en-US': 'ClassName' },
setter: 'ClassNameSetter',
});
}
if (styles?.supportInlineStyle) {
if (supports.style) {
stylesGroup.push({
name: 'style',
title: { type: 'i18n', 'zh-CN': '行内样式', 'en-US': 'Style' },
@ -201,8 +201,8 @@ export default function(metadata: TransformedComponentMetadata): TransformedComp
}
if (!isRoot) {
advanceGroup = advanceGroup.concat([
{
if (supports.condition !== false) {
advanceGroup.push({
name: '___condition',
title: { type: 'i18n', 'zh-CN': '是否渲染', 'en-US': 'Condition' },
defaultValue: true,
@ -211,14 +211,17 @@ export default function(metadata: TransformedComponentMetadata): TransformedComp
}, {
componentName: 'VariableSetter'
}],
},
{
});
}
if (supports.loop !== false) {
advanceGroup.push({
name: '#loop',
title: { type: 'i18n', 'zh-CN': '循环', 'en-US': 'Loop' },
items: [
{
name: '___loop',
title: { type: 'i18n', 'zh-CN': '循环数据', 'en-US': 'Loop Data' },
defaultValue: [],
setter: [{
componentName: 'JsonSetter',
props: {
@ -258,8 +261,8 @@ export default function(metadata: TransformedComponentMetadata): TransformedComp
}],
},
],
},
])
})
}
}
if (advanceGroup.length > 0) {
combined.push({

View File

@ -143,7 +143,7 @@ function propTypeToSetter(propType: PropType): SetterType {
};
case 'oneOfType':
return {
componentName: 'MixinSetter',
componentName: 'MixedSetter',
props: {
// TODO:
// setters: (propType as OneOfType).value.map(item => propTypeToSetter(item)),
@ -153,7 +153,7 @@ function propTypeToSetter(propType: PropType): SetterType {
}
return {
componentName: 'MixinSetter',
componentName: 'MixedSetter',
isRequired,
};
}
@ -175,8 +175,8 @@ export default function(metadata: TransformedComponentMetadata): TransformedComp
},
};
}
const { component = {}, events = {}, styles = {} } = configure;
const supportedEvents: any[] | null = (events as any).supportedEvents ? null : [];
const { component = {}, supports = {} } = configure;
const supportedEvents: any[] | null = (supports as any).events ? null : [];
const props: FieldConfig[] = [];
metadata.props.forEach((prop) => {
@ -197,21 +197,21 @@ export default function(metadata: TransformedComponentMetadata): TransformedComp
name,
description,
});
(events as any).supportedEvents = supportedEvents;
(supports as any).events = supportedEvents;
}
return;
}
if (name === 'className' && (propType === 'string' || propType === 'any')) {
if ((styles as any).supportClassName == null) {
(styles as any).supportClassName = true;
if ((supports as any).className == null) {
(supports as any).className = true;
}
return;
}
if (name === 'style' && (propType === 'object' || propType === 'any')) {
if ((styles as any).supportInlineStyle == null) {
(styles as any).supportInlineStyle = true;
if ((supports as any).style == null) {
(supports as any).style = true;
}
return;
}
@ -224,8 +224,7 @@ export default function(metadata: TransformedComponentMetadata): TransformedComp
configure: {
...configure,
props,
events,
styles,
supports,
component,
},
};

View File

@ -233,7 +233,7 @@ export default class BaseEngine extends PureComponent {
return null;
}
if (schema.loop !== undefined) {
if (schema.loop != null) {
return this.__createLoopVirtualDom(
{
...schema,
@ -244,7 +244,7 @@ export default class BaseEngine extends PureComponent {
idx,
);
}
const condition = schema.condition === undefined ? true : parseData(schema.condition, self);
const condition = schema.condition == null ? true : parseData(schema.condition, self);
if (!condition) return null;
let scopeKey = '';

View File

@ -78,9 +78,16 @@ export interface Experimental {
export interface Configure {
props?: FieldConfig[];
styles?: object;
events?: object;
component?: ComponentConfigure;
supports?: {
events?: any[];
className?: boolean;
style?: boolean;
lifecycles?: any[];
// general?: boolean;
loop?: boolean;
condition?: boolean;
};
}
export interface ActionContentObject {

View File

@ -141,7 +141,8 @@ export interface OldPrototypeConfig {
canDragging?: boolean; // => ?
canOperating?: boolean; // => disabledActions
canSelecting?: boolean;
canUseCondition?: boolean;
canLoop?: boolean;
canContain?: (dragment: Node) => boolean; // => nestingRule
canDropTo?: ((container: Node) => boolean) | boolean | string | string[]; // => nestingRule
@ -545,6 +546,8 @@ export function upgradeMetadata(oldConfig: OldPrototypeConfig) {
canDropto,
canDropIn,
canDroping,
canUseCondition,
canLoop,
// hooks
canDraging,
@ -727,9 +730,16 @@ export function upgradeMetadata(oldConfig: OldPrototypeConfig) {
});
experimental.initials = initials;
const events = {};
const styles = {};
meta.configure = { props, component, events, styles };
const supports: any = {};
if (canUseCondition != null) {
console.info('canUseCondition', componentName);
supports.condition = canUseCondition;
}
if (canLoop != null) {
console.info('canLoop', componentName);
supports.loop = canLoop;
}
meta.configure = { props, component, supports };
meta.experimental = experimental;
return meta;
}

View File

@ -1,4 +1,4 @@
import { isJSBlock } from '@ali/lowcode-types';
import { isJSBlock, isJSExpression, isJSSlot } from '@ali/lowcode-types';
import { isPlainObject } from '@ali/lowcode-utils';
import { globalContext, Editor } from '@ali/lowcode-editor-core';
import { Designer, TransformStage, addBuiltinComponentAction } from '@ali/lowcode-designer';
@ -20,6 +20,7 @@ editor.set(Skeleton, skeleton);
export const designer = new Designer({ editor: editor });
editor.set(Designer, designer);
// 节点 props 初始化
designer.addPropsReducer((props, node) => {
// run initials
const initials = node.componentMeta.getMetadata().experimental?.initials;
@ -37,6 +38,7 @@ designer.addPropsReducer((props, node) => {
return props;
}, TransformStage.Init);
// 国际化渲染时处理
designer.addPropsReducer(i18nReducer, TransformStage.Render);
function upgradePropsReducer(props: any) {
@ -64,6 +66,7 @@ function upgradePropsReducer(props: any) {
});
return newProps;
}
// 升级 Props
designer.addPropsReducer(upgradePropsReducer, TransformStage.Init);
// 设计器组件样式处理
@ -97,6 +100,31 @@ function stylePropsReducer(props: any, node: any) {
}
designer.addPropsReducer(stylePropsReducer, TransformStage.Render);
// FIXME: 表达式使用 mock 值未来live 模式直接使用原始值
function expressionReducer(obj?: any): any {
if (!obj) {
return obj;
}
if (Array.isArray(obj)) {
return obj.map((item) => expressionReducer(item));
}
if (isPlainObject(obj)) {
if (isJSExpression(obj)) {
return obj.mock;
}
if (isJSSlot(obj)) {
return obj;
}
const out: any = {};
Object.keys(obj).forEach((key) => {
out[key] = expressionReducer(obj[key]);
});
return out;
}
return obj;
}
designer.addPropsReducer(expressionReducer, TransformStage.Render);
skeleton.add({
area: 'mainArea',
name: 'designer',