diff --git a/packages/designer/src/app-providers.ts b/packages/designer/src/app-providers.ts index ffd9aed57029ec6f8cd4481c1ec81a94cf2e8c5a..71db35c8b35eb76621211585f1c3091038ceb993 100644 --- a/packages/designer/src/app-providers.ts +++ b/packages/designer/src/app-providers.ts @@ -1,6 +1,7 @@ -import { FLoadingService, FTooltipDirective, FMessageBoxService, F_MODAL_SERVICE_TOKEN, FModalService, LookupSchemaRepositoryToken, FieldSelectorRepositoryToken, F_NOTIFY_SERVICE_TOKEN, FNotifyService, ControllerSchemaRepositorySymbol, FormSchemaRepositorySymbol } from "@farris/ui-vue/components"; import { App } from "vue"; +import { FLoadingService, FTooltipDirective, FMessageBoxService, F_MODAL_SERVICE_TOKEN, FModalService, LookupSchemaRepositoryToken, FieldSelectorRepositoryToken, F_NOTIFY_SERVICE_TOKEN, FNotifyService, ControllerSchemaRepositorySymbol, FormSchemaRepositorySymbol } from "@farris/ui-vue/components"; +import { LookupSchemaRepositoryToken as MobileLookupSchemaRepositoryToken, FieldSelectorRepositoryToken as MobileFieldSelectorRepositoryToken } from "@farris/mobile-ui-vue"; import { MetadataService } from "./components/composition/metadata.service"; import { MetadataPathToken, MetadataServiceToken } from "./components/types"; import { LookupFieldSelectorService, LookupSchemaService } from "./components/composition/schema-repository"; @@ -26,6 +27,8 @@ export default { app.provide(LookupSchemaRepositoryToken, new LookupSchemaService(metadataService)); app.provide(FieldSelectorRepositoryToken, new LookupFieldSelectorService(metadataService)); + app.provide(MobileLookupSchemaRepositoryToken, new LookupSchemaService(metadataService)); + app.provide(MobileFieldSelectorRepositoryToken, new LookupFieldSelectorService(metadataService)); app.provide(F_NOTIFY_SERVICE_TOKEN, new FNotifyService()); app.provide(ControllerSchemaRepositorySymbol, new ControllerSelectorSchemaService(metadataService,designerContext)); app.provide(FormSchemaRepositorySymbol, new FormSelectorSchemaService(metadataService)); diff --git a/packages/designer/src/components/composition/designer-context/use-mobile-designer-context.ts b/packages/designer/src/components/composition/designer-context/use-mobile-designer-context.ts index e3da548d7aefa207d1e761cc10e48fd9c63d6063..5fbd807d013b31a09dbed20ccd1cde4bcb296a0b 100644 --- a/packages/designer/src/components/composition/designer-context/use-mobile-designer-context.ts +++ b/packages/designer/src/components/composition/designer-context/use-mobile-designer-context.ts @@ -3,7 +3,7 @@ import ToolboxItems from '../../types/toolbox/mobile-toolbox.json'; import SupportedControllers from '../../composition/command/supported-controllers/mobile-supported-controller.json'; import { - Component, PageContainer, PageHeaderContainer, PageBodyContainer, PageFooterContainer, Picker, NumberInput, Textarea, DatePicker, DateTimePicker, + Component, PageContainer, PageHeaderContainer, PageBodyContainer, PageFooterContainer, Picker, NumberInput, Textarea, DatePicker, DateTimePicker, Lookup, ContentContainer, FloatContainer, Navbar, ListView, Form, FormItem, InputGroup, Button, registerDesignerComponents, Switch, CheckboxGroup, RadioGroup, } from '@farris/mobile-ui-vue'; import { useMobileControlCreator } from "../control-creator/use-mobile-control-creator"; @@ -21,7 +21,7 @@ export function useMobileDesignerContext(): UseDesignerContext { /** 要注册的UI组件 */ const componentsToRegister: any[] = [ Component, PageContainer, PageHeaderContainer, PageBodyContainer, PageFooterContainer, - ContentContainer, FloatContainer,Textarea,DatePicker,DateTimePicker, + ContentContainer, FloatContainer,Textarea,DatePicker,DateTimePicker,Lookup, Navbar, ListView,Picker,NumberInput,Switch,CheckboxGroup,RadioGroup, Form, FormItem, InputGroup, Button diff --git a/packages/designer/vite.config.dev.ts b/packages/designer/vite.config.dev.ts index 37b7971cdf1d8b0b5c4ffdce89b652f79e10e673..f0595c897cf390bbefae995c9ae404c7f51583af 100644 --- a/packages/designer/vite.config.dev.ts +++ b/packages/designer/vite.config.dev.ts @@ -20,7 +20,7 @@ export default defineConfig({ '@': resolve(__dirname, '../'), '@farris/ui-vue': resolve(__dirname, '../ui-vue'), '@farris/code-editor-vue': resolve(__dirname, '../code-editor'), - '@farris/mobile-ui-vue': resolve(__dirname, '../mobile-ui-vue/components') + '@farris/mobile-ui-vue': resolve(__dirname, '../mobile-ui-vue/components'), } } }); diff --git a/packages/mobile-render/farris.config.mjs b/packages/mobile-render/farris.config.mjs new file mode 100644 index 0000000000000000000000000000000000000000..724337a10f2a8c1f15aa7d7020d9bb70dc1628b6 --- /dev/null +++ b/packages/mobile-render/farris.config.mjs @@ -0,0 +1,38 @@ +import { fileURLToPath, URL } from 'node:url'; + +const externals = []; + +export default { + format: "system", + minify: false, + target: 'es2015', + externalDependencies: true, + externals: { + include: externals, + filter: (externals) => { + return (id) => { + return externals.find((item) => item && id.indexOf(item) === 0); + }; + } + }, + server: { + proxy: { + "/api": { + target: "http://localhost:5200", + changeOrigin: true, + secure: false + }, + "/apps": { + target: "http://localhost:5200", + changeOrigin: true, + secure: false + } + } + }, + alias: [ + { find: "@farris/devkit-vue", replacement: fileURLToPath(new URL('../devkit/lib', import.meta.url)) }, + { find: "@farris/bef-vue", replacement: fileURLToPath(new URL('../bef/lib', import.meta.url)) }, + { find: "@farris/mobile-command-services-vue", replacement: fileURLToPath(new URL('../mobile-command-services/lib', import.meta.url)) }, + { find: '@farris/mobile-ui-vue', replacement: fileURLToPath(new URL('../mobile-ui-vue/components', import.meta.url)) } + ] +}; diff --git a/packages/mobile-render/index-publish.html b/packages/mobile-render/index-publish.html index 3f5ff874feadddb936ca5f5aa931739fc8c3b2c4..c0f951989d79d34fb893875660d97ac798281280 100644 --- a/packages/mobile-render/index-publish.html +++ b/packages/mobile-render/index-publish.html @@ -4,12 +4,19 @@ Mobile Render - - - - + +
+ + + diff --git a/packages/mobile-render/package.json b/packages/mobile-render/package.json index 2f167a8cdc7ee75ab08561e7722bc7d558a66c90..0b9186b866eed90bd38a3c510c47695e4c227d34 100644 --- a/packages/mobile-render/package.json +++ b/packages/mobile-render/package.json @@ -14,9 +14,9 @@ "url": "git@gitee.com:ubml/farris-vue.git" }, "scripts": { - "dev": "vite", - "build": "vue-tsc --noEmit && vite build", - "preview": "vite preview", + "dev": "farris-cli dev", + "build": "farris-cli build", + "preview": "farris-cli preview", "lint": "eslint . --ext .vue,.js,.jsx,.cjs,.mjs,.ts,.tsx,.cts,.mts --fix --ignore-path .gitignore", "format": "prettier --write src/" }, @@ -30,45 +30,26 @@ "vue-router": "^4.3.0" }, "devDependencies": { + "@farris/cli": "workspace:*", "@rushstack/eslint-patch": "^1.8.0", "@vue/eslint-config-prettier": "^9.0.0", "@vue/eslint-config-typescript": "^13.0.0", "@vue/tsconfig": "^0.5.1", - "eslint": "^8.57.0", "eslint-plugin-vue": "^9.23.0", "prettier": "^3.2.5", - "vite-plugin-dts": "^2.1.0", - "@babel/parser": "^7.19.0", - "@babel/preset-env": "^7.19.0", - "@babel/preset-typescript": "^7.18.0", - "@babel/traverse": "^7.19.0", "@commitlint/cli": "^17.1.0", "@commitlint/config-conventional": "^17.1.0", "@testing-library/vue": "^7.0.0", "@types/jest": "^26.0.24", "@typescript-eslint/eslint-plugin": "^7.15.0", "@typescript-eslint/parser": "^7.15.0", - "@vitejs/plugin-vue": "^4.0.0", - "@vitejs/plugin-vue-jsx": "^3.0.0", - "@vue/babel-plugin-jsx": "^1.1.1", "@vue/compiler-sfc": "^3.2.0", "@vue/test-utils": "^2.0.0", - "@vuedx/typecheck": "^0.7.5", - "@vuedx/typescript-plugin-vue": "^0.7.5", "babel-jest": "^29.0.3", - "chalk": "^5.0.0", - "commander": "^9.4.0", "conventional-changelog-cli": "^2.2.2", - "happy-dom": "^8.9.0", - "inquirer": "^9.1.1", "jest": "^29.0.0", - "ora": "^6.1.2", - "patch-vue-directive-ssr": "^0.0.1", "shelljs": "^0.8.4", "typescript": "^4.6.4", - "vite": "^4.1.4", - "vite-plugin-banner": "^0.8.0", - "vite-svg-loader": "^4.0.0", "vitest": "^0.29.2", "vue-tsc": "^1.2.0" } diff --git a/packages/mobile-render/scripts/publish.sh b/packages/mobile-render/scripts/publish.sh index 024391d4f69d49c13aef1c014dc7be5f275ca3c0..b6888d76a933b6f03e6608ff7af63cf5c8c2fe94 100644 --- a/packages/mobile-render/scripts/publish.sh +++ b/packages/mobile-render/scripts/publish.sh @@ -14,7 +14,7 @@ mkdir -p $RENDER_DIR # 拷贝文件 cp -r -p ../mobile-ui-vue/package/index.css "${STYLE_DIR}/farris-mobile-ui-vue.css" -cp -r -p ../mobile-ui-vue/public/assets/farris-mobile-page.css "${STYLE_DIR}/farris-mobile-page-vue.css" +cp -r -p ../mobile-ui-vue/lib/page.css "${STYLE_DIR}/farris-mobile-page-vue.css" cp -r -p ../mobile-ui-vue/package/index.systemjs.js "${SCRIPT_DIR}/mobile-ui-vue.js" cp -r -p ../devkit/dist-rollup/@farris/devkit-vue.js "${SCRIPT_DIR}/devkit-vue.js" diff --git a/packages/mobile-render/tsconfig.node.json b/packages/mobile-render/tsconfig.node.json index d8915f131adf0c7ed78b511e1d8cae09947858d3..7fed214121acaa7dee0c3d91e2a5ebca73829536 100644 --- a/packages/mobile-render/tsconfig.node.json +++ b/packages/mobile-render/tsconfig.node.json @@ -7,8 +7,5 @@ "verbatimModuleSyntax": false, "allowSyntheticDefaultImports": true, "forceConsistentCasingInFileNames": true - }, - "include": [ - "vite.config.ts" - ] + } } \ No newline at end of file diff --git a/packages/mobile-render/vite.config.ts b/packages/mobile-render/vite.config.ts deleted file mode 100644 index 4c68bb48c60634d5415ea698456095740e60676b..0000000000000000000000000000000000000000 --- a/packages/mobile-render/vite.config.ts +++ /dev/null @@ -1,52 +0,0 @@ -// / -import path from 'path'; -import { defineConfig } from 'vite'; -import type { InlineConfig } from 'vitest'; -import type { UserConfig } from 'vite'; -import vue from '@vitejs/plugin-vue'; -import vueJsx from '@vitejs/plugin-vue-jsx'; - -interface VitestConfigExport extends UserConfig { - test: InlineConfig; -} - -// https://vitejs.dev/config/ -export default defineConfig({ - // base: process.env.NODE_ENV === 'production' ? '/platform/common/web/mobile-renderer/' : './', - build: { - minify: false - }, - plugins: [vue(), vueJsx()], - test: { - globals: true, - environment: 'happy-dom', - include: ['**/*.test.tsx'] - }, - server: { - proxy: { - "/api": { - target: "http://127.0.0.1:5200", - changeOrigin: true, - secure: false - }, - "/apps": { - target: "http://127.0.0.1:5200", - changeOrigin: true, - secure: false - } - } - }, - resolve: { - alias: { - 'vue': 'vue/dist/vue.esm-bundler.js', - "@farris/devkit-vue": path.resolve(__dirname, "../devkit/lib/index"), - "@farris/bef-vue": path.resolve(__dirname, "../bef/lib/index"), - "@farris/mobile-ui-vue": path.resolve(__dirname, "../mobile-ui-vue/components/index"), - "@farris/mobile-command-services-vue": path.resolve(__dirname, "../mobile-command-services/lib/index"), - "@components": path.resolve(__dirname, "../mobile-ui-vue/components"), - "@/components": path.resolve(__dirname, "../mobile-ui-vue/components"), - - } - }, - logLevel: 'error' -} as VitestConfigExport); diff --git a/packages/mobile-ui-vue/.gitignore b/packages/mobile-ui-vue/.gitignore index bef97693ba64ab5b2b3dea6be3d88776698eee39..1c11aea63f56f621cd6d1755a6733287d1f64328 100644 --- a/packages/mobile-ui-vue/.gitignore +++ b/packages/mobile-ui-vue/.gitignore @@ -9,6 +9,7 @@ lerna-debug.log* node_modules dist +lib package dist-ssr *.local diff --git a/packages/mobile-ui-vue/components/button-group/index.ts b/packages/mobile-ui-vue/components/button-group/index.ts index 4bb2569a6ccba3cf3caf163eafed9e9d93e2abb5..4e36f328dc9ae18347c5895957f19f51b38d10a9 100644 --- a/packages/mobile-ui-vue/components/button-group/index.ts +++ b/packages/mobile-ui-vue/components/button-group/index.ts @@ -11,4 +11,4 @@ withRegister(ButtonGroup, { name: BUTTON_GROUP_REGISTERED_NAME, propsResolverGen export * from './src/button-group.props'; export { ButtonGroup }; -export default ButtonGroup as typeof ButtonGroup & Plugin; +export default ButtonGroup; diff --git a/packages/mobile-ui-vue/components/button/index.ts b/packages/mobile-ui-vue/components/button/index.ts index f0dcd4d389a941de763a8275e39fd57dc4f8e80c..55939f34cff93ccfbd79a5f7bb9336d645ff09a0 100644 --- a/packages/mobile-ui-vue/components/button/index.ts +++ b/packages/mobile-ui-vue/components/button/index.ts @@ -1,5 +1,4 @@ -import { Plugin } from 'vue'; -import { withInstall, RegisterContext } from '@farris/mobile-ui-vue/common'; +import { withInstall, withRegister, withRegisterDesigner } from '@farris/mobile-ui-vue/common'; import ButtonInstallless from './src/button.component'; import { propsResolverGenerator } from './src/button.props'; import ButtonDesign from './src/designer/button.design.component'; @@ -7,22 +6,9 @@ import ButtonDesign from './src/designer/button.design.component'; const BUTTON_REGISTERED_NAME = 'button'; const Button = withInstall(ButtonInstallless); -Button.register = ( - componentMap: Record, propsResolverMap: Record, - configResolverMap: Record, resolverMap: Record, registerContext: RegisterContext -) => { - componentMap[BUTTON_REGISTERED_NAME] = Button; - propsResolverMap[BUTTON_REGISTERED_NAME] = propsResolverGenerator(registerContext); -}; - -Button.registerDesigner = ( - componentMap: Record, propsResolverMap: Record, - configResolverMap: Record, registerContext: RegisterContext -) => { - componentMap[BUTTON_REGISTERED_NAME] = ButtonDesign; - propsResolverMap[BUTTON_REGISTERED_NAME] = propsResolverGenerator(registerContext); -}; +withRegister(Button, { name: BUTTON_REGISTERED_NAME, propsResolverGenerator }); +withRegisterDesigner(Button, { name: BUTTON_REGISTERED_NAME, propsResolverGenerator, designerComponent: ButtonDesign }); export { Button }; -export default Button as typeof Button & Plugin; +export default Button; diff --git a/packages/mobile-ui-vue/components/button/src/button.component.tsx b/packages/mobile-ui-vue/components/button/src/button.component.tsx index fc8dbfeb2bf0c076e9ff8ae1daba9e9bde88897d..5854499fdef960104520de98b885afdee1d2467c 100644 --- a/packages/mobile-ui-vue/components/button/src/button.component.tsx +++ b/packages/mobile-ui-vue/components/button/src/button.component.tsx @@ -1,13 +1,13 @@ import { CSSProperties, computed, defineComponent } from 'vue'; +import { useBem, stopPropagation } from '@farris/mobile-ui-vue/common'; import { Icon } from '@farris/mobile-ui-vue/icon'; -import { useBem } from '@farris/mobile-ui-vue/common'; -import { BUTTON_NAME, ButtonProps, buttonProps } from './button.props'; +import { BUTTON_NAME, buttonProps } from './button.props'; export default defineComponent({ name: BUTTON_NAME, props: buttonProps, emits: ['click'], - setup(props: ButtonProps, context) { + setup(props, context) { const { slots } = context; const { bem, getModifierClass } = useBem(BUTTON_NAME); @@ -24,7 +24,7 @@ export default defineComponent({ return classList; }); - const applyGradientBorderBehavior = (style: CSSProperties, color: string) =>{ + const applyGradientBorderBehavior = (style: CSSProperties, color: string) => { const isGradientColor = color.includes('gradient'); if (isGradientColor) { style.border = 0; @@ -47,10 +47,11 @@ export default defineComponent({ return style; }); - const onClickButton = ($event: Event) =>{ - $event.stopPropagation(); - if (!props.disabled) { - context.emit('click', $event); + const onClickButton = (event: Event) => { + if (props.disabled) { + stopPropagation(event); + } else { + context.emit('click', event); } }; @@ -73,8 +74,8 @@ export default defineComponent({ ); }; - const renderText = ()=> { - return slots.default && {slots.default()}; + const renderText = () => { + return (slots.default || props.text) && {slots.default ? slots.default() : props.text}; }; return () => ( diff --git a/packages/mobile-ui-vue/components/button/src/button.props.ts b/packages/mobile-ui-vue/components/button/src/button.props.ts index 003aed6d5570c955b3d915a6432fddd4f231972d..e5a1224d2448133b3464b864199bd0d72ecac4e8 100644 --- a/packages/mobile-ui-vue/components/button/src/button.props.ts +++ b/packages/mobile-ui-vue/components/button/src/button.props.ts @@ -1,67 +1,57 @@ import { ExtractPropTypes, PropType } from 'vue'; -import { getPropsResolverGenerator } from '../../dynamic-resolver'; +import { getPropsResolverGenerator } from '@farris/mobile-ui-vue/dynamic-resolver'; import buttonSchema from './schema/button.schema.json'; import { schemaMapper } from './schema/schema-mapper'; import { schemaResolver } from './schema/schema-resolver'; -export type ButtonType = 'primary' | 'secondary' | 'success' | 'warning' | 'danger' | 'info'; -export type ButtonSize = 'large' | 'normal' | 'small' | 'mini'; +export enum ButtonType { + primary = 'primary', + secondary = 'secondary', + success = 'success', + warning = 'warning', + danger = 'danger' +} -export const BUTTON_NAME = "fm-button"; +export enum ButtonSize { + large = 'large', + middle = 'middle', + small = 'small', + mini = 'mini' +} + +export const BUTTON_NAME = 'FmButton'; export const buttonProps = { - type: { - type: String as PropType, - default: 'primary' - }, - size: { - type: String as PropType, - default: '' - }, - color: { - type: String, - default: '' - }, - block: { - type: Boolean, - default: false - }, - noBorder: { - type: Boolean, - default: false - }, - plain: { - type: Boolean, - default: false - }, - round: { - type: Boolean, - default: false - }, - disabled: { - type: Boolean, - default: false - }, - icon: { - type: String, - default: '' - }, - loading: { - type: Boolean, - default: false - }, - loadingText: { - type: String, - default: '' - } + type: { type: String as PropType, default: ButtonType.primary }, + + size: { type: String as PropType, default: ButtonSize.middle }, + + color: { type: String, default: '' }, + + block: { type: Boolean, default: false }, + + noBorder: { type: Boolean, default: false }, + + plain: { type: Boolean, default: false }, + + round: { type: Boolean, default: false }, + + disabled: { type: Boolean, default: false }, + + icon: { type: String, default: '' }, + + loading: { type: Boolean, default: false }, + + text: { type: String, default: '' }, + + loadingText: { type: String, default: '' } }; export type ButtonProps = ExtractPropTypes; - -export const propsResolverGenerator = getPropsResolverGenerator( - buttonProps, - buttonSchema, - schemaMapper, - schemaResolver +export const propsResolverGenerator = getPropsResolverGenerator( + buttonProps, + buttonSchema, + schemaMapper, + schemaResolver ); diff --git a/packages/mobile-ui-vue/components/button/src/button.scss b/packages/mobile-ui-vue/components/button/src/button.scss index a578b806053d544fc83ccf564d13db0aceeb4e91..b6c4be58c47ca7ddfbfae2c6fb38cf2a818ebd49 100644 --- a/packages/mobile-ui-vue/components/button/src/button.scss +++ b/packages/mobile-ui-vue/components/button/src/button.scss @@ -39,7 +39,7 @@ line-height: var(--fm-button-line-height); border-radius: var(--fm-button-radius); - @include m((primary, info)) { + @include m((primary)) { background: var(--fm-primary-color); } @@ -63,7 +63,7 @@ @include m(plain) { box-shadow: none; background: var(--fm-button-plain-background); - @include root-m((primary, info)) { + @include root-m((primary)) { color: var(--fm-primary-color); border: var(--fm-button-border-width) solid var(--fm-primary-color); } @@ -90,7 +90,7 @@ font-size: var(--fm-button-lg-font-size); } - @include m(normal) { + @include m(middle) { height: var(--fm-button-md-height); font-size: var(--fm-button-md-font-size); } diff --git a/packages/mobile-ui-vue/components/button/src/designer/button.design.component.tsx b/packages/mobile-ui-vue/components/button/src/designer/button.design.component.tsx index 0e63f594deb0e1297f0cf1a15aa29ad8c4533ff9..740e2c790099fce6ed3b25944de3198128a2750c 100644 --- a/packages/mobile-ui-vue/components/button/src/designer/button.design.component.tsx +++ b/packages/mobile-ui-vue/components/button/src/designer/button.design.component.tsx @@ -15,9 +15,9 @@ * limitations under the License. */ import { computed, defineComponent, inject, onMounted, ref, SetupContext } from 'vue'; +import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/common';; import { ButtonProps, buttonProps } from '../button.props'; -import Button from '../..'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import Button from '../button.component'; import { useDesignerRules } from './use-designer-rules'; export default defineComponent({ @@ -44,6 +44,8 @@ export default defineComponent({ block: props.block, icon: props.icon, type: props.type, + plain: props.plain, + size: props.size, })); return () => { diff --git a/packages/mobile-ui-vue/components/button/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/button/src/designer/use-designer-rules.ts index 07e0e64d7d437b9f5be6dc57dc5790e4bee20e14..da2a3b6fd2bf5d9e7930caf9655f682c305f89dd 100644 --- a/packages/mobile-ui-vue/components/button/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/button/src/designer/use-designer-rules.ts @@ -1,7 +1,7 @@ import { ref } from "vue"; +import { DraggingResolveContext } from "@farris/mobile-ui-vue/common"; +import { DesignerHostService, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; import { ButtonProperty } from "../property-config/button.property-config"; -import { DesignerHostService, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; -import { DraggingResolveContext } from "@farris/mobile-ui-vue/designer-canvas/src/composition/types"; export function useDesignerRules(designItemContext: DesignerItemContext, designerHostService?: DesignerHostService): UseDesignerRules { @@ -45,13 +45,13 @@ export function useDesignerRules(designItemContext: DesignerItemContext, designe return { canAccepts, - triggerBelongedComponentToMoveWhenMoved, - triggerBelongedComponentToDeleteWhenDeleted, - checkCanMoveComponent, - checkCanDeleteComponent, + // triggerBelongedComponentToMoveWhenMoved, + // triggerBelongedComponentToDeleteWhenDeleted, + // checkCanMoveComponent, + // checkCanDeleteComponent, hideNestedPaddingInDesginerView, - getStyles, - getDesignerClass, + // getStyles, + // getDesignerClass, getPropsConfig }; } diff --git a/packages/mobile-ui-vue/components/button/src/property-config/button.property-config.ts b/packages/mobile-ui-vue/components/button/src/property-config/button.property-config.ts index 9188aae389f52eda03ee78bc875809fc7094b4e2..2e3db3fe0451b1a430e2b42c006f1f1f582ffc34 100644 --- a/packages/mobile-ui-vue/components/button/src/property-config/button.property-config.ts +++ b/packages/mobile-ui-vue/components/button/src/property-config/button.property-config.ts @@ -1,4 +1,4 @@ -import { BaseControlProperty } from "@farris/mobile-ui-vue/property-panel"; +import { BaseControlProperty } from "@farris/mobile-ui-vue/common"; export class ButtonProperty extends BaseControlProperty { constructor(componentId: string, designerHostService: any) { @@ -10,12 +10,12 @@ export class ButtonProperty extends BaseControlProperty { // 外观 this.propertyConfig.categories['appearance'] = this.getAppearanceConfig(propertyData); // 行为 - this.propertyConfig.categories['behavior'] = this.getBehaviorConfig(propertyData); + this.propertyConfig.categories['behavior'] = this.getButtonBehaviorConfig(propertyData); return this.propertyConfig; } - private getBehaviorConfig(propertyData) { + private getButtonBehaviorConfig(propertyData) { return { description: "基本信息", title: "行为", @@ -29,6 +29,10 @@ export class ButtonProperty extends BaseControlProperty { title: "只读", type: "boolean", }, + text: { + title: "文本", + type: "string", + }, displayType: { title: "按钮类型", type: 'select', @@ -37,12 +41,27 @@ export class ButtonProperty extends BaseControlProperty { textField: 'name', valueField: 'value', editable: false, - data: [{ value:'primary' , name: '主要按钮' }, + data: [ + { value:'primary' , name: '主要按钮' }, { value:'secondary' , name: '次要按钮' }, { value:'success' , name: '成功按钮' }, { value:'warning' , name: '警告按钮' }, - { value:'danger' , name: '危险按钮' }, - { value:'info' , name: '提示按钮' }, + { value:'danger' , name: '危险按钮' } + ] + } + }, + size: { + title: "按钮尺寸", + type: 'select', + editor: { + type: 'combo-list', + textField: 'name', + valueField: 'value', + editable: false, + data: [ + { value:'large' , name: '大号' }, + { value:'middle' , name: '中号' }, + { value:'small' , name: '小号' }, ] } }, @@ -54,8 +73,12 @@ export class ButtonProperty extends BaseControlProperty { title: "启用圆角", type: "boolean", }, - text: { - title: "提示文本", + plain: { + title: "启用朴素按钮", + type: "boolean", + }, + icon: { + title: "图标", type: "string", } } diff --git a/packages/mobile-ui-vue/components/button/src/schema/button.schema.json b/packages/mobile-ui-vue/components/button/src/schema/button.schema.json index 0243498e5cb9e90c43f7144a3cf7311db4f5bf5d..365c21abd54d4cebf3eafdaf7646cc91ad1f786d 100644 --- a/packages/mobile-ui-vue/components/button/src/schema/button.schema.json +++ b/packages/mobile-ui-vue/components/button/src/schema/button.schema.json @@ -61,6 +61,11 @@ "type": "boolean", "default": false }, + "size": { + "description": "", + "type": "string", + "default": "middle" + }, "icon": { "description": "图标", "type": "string" diff --git a/packages/mobile-ui-vue/components/button/src/schema/schema-mapper.ts b/packages/mobile-ui-vue/components/button/src/schema/schema-mapper.ts index eca9607abe43c13c4f01ef3884aa12c77ea0ba3a..adc95460db64a2defb6fa5783b3c33b2e055a05e 100644 --- a/packages/mobile-ui-vue/components/button/src/schema/schema-mapper.ts +++ b/packages/mobile-ui-vue/components/button/src/schema/schema-mapper.ts @@ -1,4 +1,4 @@ -import { resolveAppearance, MapperFunction } from '../../../dynamic-resolver'; +import { resolveAppearance, MapperFunction } from '@farris/mobile-ui-vue/dynamic-resolver'; function createTemplatePropResolver(name: string): MapperFunction { return (key: string, content: string) => { diff --git a/packages/mobile-ui-vue/components/button/src/schema/schema-resolver.ts b/packages/mobile-ui-vue/components/button/src/schema/schema-resolver.ts index c1bf8da88a08c01a3c8d6e9f3d81859d84d87aa6..329b35ae2e0c3d0c503f0e67320ca1e6c8516560 100644 --- a/packages/mobile-ui-vue/components/button/src/schema/schema-resolver.ts +++ b/packages/mobile-ui-vue/components/button/src/schema/schema-resolver.ts @@ -1,4 +1,4 @@ -import { DynamicResolver } from "../../../dynamic-resolver"; +import { DynamicResolver } from "@farris/mobile-ui-vue/dynamic-resolver"; export function schemaResolver(resolver: DynamicResolver, schema: Record, context: Record): Record { return schema; diff --git a/packages/mobile-ui-vue/components/checkbox-group/src/checkbox-group.component.tsx b/packages/mobile-ui-vue/components/checkbox-group/src/checkbox-group.component.tsx index 844917718c10dc2dc2e174e62f8f84513752decc..ddf46838896c926290dbe18ab95014d9030b6f7f 100644 --- a/packages/mobile-ui-vue/components/checkbox-group/src/checkbox-group.component.tsx +++ b/packages/mobile-ui-vue/components/checkbox-group/src/checkbox-group.component.tsx @@ -1,34 +1,17 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -import { SetupContext, computed, defineComponent, ref, toRaw, watch } from 'vue'; +import { computed, defineComponent, ref, toRaw, watch } from 'vue'; import { isArray, isString, useBem, useLink } from '@farris/mobile-ui-vue/common'; import Checkbox from '@farris/mobile-ui-vue/checkbox'; +import { useGroupItems } from './composition'; import { CHECKBOX_GROUP_NAME, CheckboxGroupContext, - CheckboxGroupProps, checkboxGroupProps } from './checkbox-group.props'; -import { useGroupItems } from './composition'; export default defineComponent({ name: CHECKBOX_GROUP_NAME, props: checkboxGroupProps, - setup(props: CheckboxGroupProps, context: SetupContext) { + setup(props, context) { const { emit, slots } = context; const checkeds = ref<(string | number)[]>([]); diff --git a/packages/mobile-ui-vue/components/checkbox-group/src/checkbox-group.props.ts b/packages/mobile-ui-vue/components/checkbox-group/src/checkbox-group.props.ts index b823c42c2c9ea9cb39abcc83b02a4b8c6618374a..1cdf9b3da8fee460e1e6ea34eb4adc8be694cd04 100644 --- a/packages/mobile-ui-vue/components/checkbox-group/src/checkbox-group.props.ts +++ b/packages/mobile-ui-vue/components/checkbox-group/src/checkbox-group.props.ts @@ -1,5 +1,5 @@ import { ExtractPropTypes, PropType } from 'vue'; -import { CheckerShape, CheckerShapeMap, CheckerType, CheckerTypeMap } from '@farris/mobile-ui-vue/checker'; +import { CheckerShape, CheckerType } from '@farris/mobile-ui-vue/checker'; import { schemaMapper } from './schema/schema-mapper'; import { schemaResolver } from './schema/schema-resolver'; import inputSchema from './schema/checkbox-group.schema.json'; @@ -11,13 +11,11 @@ export type CheckboxItem = { [key: string]: any; }; -export const enum CheckboxDirectionMap { +export const enum CheckboxDirection { Vertical = 'vertical', Horizontal = 'horizontal' } -export type CheckboxDirection = `${CheckboxDirectionMap}`; - export const CHECKBOX_GROUP_NAME = 'fm-checkbox-group'; export const checkboxGroupProps = { @@ -27,11 +25,11 @@ export const checkboxGroupProps = { readonly: { type: Boolean, default: false }, - shape: { type: String as PropType, default: CheckerShapeMap.Square }, + shape: { type: String as PropType, default: CheckerShape.Square }, - type: { type: String as PropType, default: CheckerTypeMap.Check }, + type: { type: String as PropType, default: CheckerType.Check }, - direction: { type: String as PropType, default: CheckboxDirectionMap.Vertical }, + direction: { type: String as PropType, default: CheckboxDirection.Vertical }, options: { type: Array as PropType, default: undefined }, @@ -40,7 +38,7 @@ export const checkboxGroupProps = { textField: { type: String, default: 'text' }, showDisabledItem: { type: Boolean, default: true }, -} as Record; +}; export type CheckboxGroupProps = ExtractPropTypes; @@ -50,5 +48,5 @@ export type CheckboxGroupContext = { updateChecked: (value: string | number, checked: boolean) => void; }; -export const propsResolverGenerator = getPropsResolverGenerator(checkboxGroupProps, inputSchema, schemaMapper, schemaResolver); +export const propsResolverGenerator = getPropsResolverGenerator(checkboxGroupProps, inputSchema, schemaMapper, schemaResolver); diff --git a/packages/mobile-ui-vue/components/checkbox-group/src/designer/checkbox-group.design.component.tsx b/packages/mobile-ui-vue/components/checkbox-group/src/designer/checkbox-group.design.component.tsx index 1103be0fd1cfeb80a2057cd8551c772ae90352fe..d394591c00ed7592e3f1ef8246e895970f6fbde3 100644 --- a/packages/mobile-ui-vue/components/checkbox-group/src/designer/checkbox-group.design.component.tsx +++ b/packages/mobile-ui-vue/components/checkbox-group/src/designer/checkbox-group.design.component.tsx @@ -1,74 +1,74 @@ - -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -import { computed, defineComponent, inject, onMounted, readonly, ref, SetupContext } from 'vue'; -import { CheckboxGroup, checkboxGroupProps, CheckboxGroupProps } from '../..'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas'; -import { useCheckBoxGroupProperty } from './use-designer-rules';; +import { computed, defineComponent, inject, onMounted, ref } from 'vue'; +import { + DesignerHostService, + DesignerItemContext, + extractProperties, + useDesignerComponent +} from '@farris/mobile-ui-vue/common'; +import { useCheckBoxGroupProperty } from './use-designer-rules'; +import { checkboxGroupProps } from '../checkbox-group.props'; +import CheckboxGroup from '../checkbox-group.component'; export default defineComponent({ - name: 'FmEnumFieldInputDesign', - props: checkboxGroupProps, - emits: [] as (string[] & ThisType) | undefined, - setup(props: CheckboxGroupProps, context: SetupContext) { - const elementRef = ref(); - const designerHostService = inject('designer-host-service'); - const designItemContext = inject('design-item-context') as DesignerItemContext; - const designerRulesComposition = useCheckBoxGroupProperty(designItemContext, designerHostService); - const componentInstance = useDesignerComponent(elementRef, designItemContext, designerRulesComposition); + name: 'FmCheckboxGroupDesign', + props: extractProperties(checkboxGroupProps, [ + 'options', + 'textField', + 'valueField', + 'direction', + 'type' + ]), + setup(props, context) { + const elementRef = ref(); + const designerHostService = inject('designer-host-service'); + const designItemContext = inject( + 'design-item-context' + ) as DesignerItemContext; + const designerRulesComposition = useCheckBoxGroupProperty( + designItemContext, + designerHostService + ); + const componentInstance = useDesignerComponent( + elementRef, + designItemContext, + designerRulesComposition + ); - onMounted(() => { - elementRef.value.componentInstance = componentInstance; - }); + onMounted(() => { + elementRef.value.componentInstance = componentInstance; + }); - /** - * 解决在设计时,数据为空数组,界面不显示内容的问题 - */ - const realEnumData = computed(() => { - if (!props.options || props.options.length === 0) { - const result = [] as any; - [ - { value: 'example1', name: '示例一' }, - { value: 'example2', name: '示例二' } - ].map(item => { - const tempData = {}; - tempData[props.valueField] = item['value']; - tempData[props.textField] = item['name']; - result.push(tempData); - }); - return result; - } - return props.options; + /** + * 解决在设计时,数据为空数组,界面不显示内容的问题 + */ + const realEnumData = computed(() => { + if (!props.options || props.options.length === 0) { + const result = [] as any; + [ + { value: 'example1', name: '示例一' }, + { value: 'example2', name: '示例二' } + ].map((item) => { + const tempData = {}; + tempData[props.valueField] = item['value']; + tempData[props.textField] = item['name']; + result.push(tempData); }); + return result; + } + return props.options; + }); + + context.expose(componentInstance.value); - const inputGroupProps = computed(() => ({ - ...props, - editable: false, - readonly: true, - modelValue:null, - options:realEnumData.value, - type:null - })); - - context.expose(componentInstance.value); + const checkboxGroupProps = computed(() => ({ + ...props, + editable: false, + readonly: true, + options: realEnumData.value + })); - return () => { - return ( - - ); - }; - } + return () => { + return ; + }; + } }); diff --git a/packages/mobile-ui-vue/components/checkbox-group/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/checkbox-group/src/designer/use-designer-rules.ts index e2bb1a7808a33a90e3d0bfb2e505ccc4411ff192..0c4a681f89eea5c5e130bb1e1cb6de38c68c7151 100644 --- a/packages/mobile-ui-vue/components/checkbox-group/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/checkbox-group/src/designer/use-designer-rules.ts @@ -1,4 +1,4 @@ -import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; +import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; import { CheckBoxGroupProperty } from "../property-config/checkbox-group.property-config"; export function useCheckBoxGroupProperty(designItemContext: DesignerItemContext, designerHostService): UseDesignerRules { @@ -6,8 +6,8 @@ export function useCheckBoxGroupProperty(designItemContext: DesignerItemContext, // 构造属性配置方法 function getPropsConfig(componentId: string, componentInstance: DesignerComponentInstance) { - const radioGroupProps = new CheckBoxGroupProperty(componentId, designerHostService); - return radioGroupProps.getPropertyConfig(schema, componentInstance); + const radioGroupProps = new CheckBoxGroupProperty(componentId, designerHostService); + return radioGroupProps.getPropertyConfig(schema, componentInstance); } return { getPropsConfig } as UseDesignerRules; diff --git a/packages/mobile-ui-vue/components/checkbox-group/src/property-config/checkbox-group.property-config.ts b/packages/mobile-ui-vue/components/checkbox-group/src/property-config/checkbox-group.property-config.ts index 8d632abab80e3c0714b9535a56cebfb177b21712..66d4c07288cf1ba275aeb5e5631031fee3326f17 100644 --- a/packages/mobile-ui-vue/components/checkbox-group/src/property-config/checkbox-group.property-config.ts +++ b/packages/mobile-ui-vue/components/checkbox-group/src/property-config/checkbox-group.property-config.ts @@ -1,4 +1,4 @@ -import { InputBaseProperty } from '@farris/mobile-ui-vue/common/src/entity/input-base-property'; +import { InputBaseProperty } from '@farris/mobile-ui-vue/common'; export class CheckBoxGroupProperty extends InputBaseProperty { constructor(componentId: string, designerHostService: any) { @@ -9,19 +9,15 @@ export class CheckBoxGroupProperty extends InputBaseProperty { const self = this; const editorProperties = self.getComponentConfig( propertyData, - {}, + { type: 'check-group' }, { placeholder: { visible: false }, - disabled: { - visible: false - }, data: { description: '', title: '数据', type: 'array', - $converter: '/converter/enum-data.converter', ...self.getItemCollectionEditor( propertyData, propertyData.editor.valueField, @@ -43,7 +39,7 @@ export class CheckBoxGroupProperty extends InputBaseProperty { readonly: true } }, - (changeObject, parameters) => { + (changeObject) => { if (!changeObject) { return; } diff --git a/packages/mobile-ui-vue/components/checkbox-group/src/schema/checkbox-group.schema.json b/packages/mobile-ui-vue/components/checkbox-group/src/schema/checkbox-group.schema.json index 0a7a1f7c964b8c65cee01e7301995a5081266b5c..2cc30d0d6c0edd7e24fa24408300262270efbcac 100644 --- a/packages/mobile-ui-vue/components/checkbox-group/src/schema/checkbox-group.schema.json +++ b/packages/mobile-ui-vue/components/checkbox-group/src/schema/checkbox-group.schema.json @@ -1,88 +1,77 @@ { - "$schema": "https://json-schema.org/draft/2020-12/schema", - "$id": "https://farris-design.gitee.io/check-group.schema.json", - "title": "check-group", - "description": "A Farris Input Component", - "type": "object", - "properties": { - "id": { - "description": "The unique identifier for a Input Group", - "type": "string" - }, - "type": { - "description": "The type string of Input Group component", - "type": "string", - "default": "check-group" - }, - "appearance": { - "description": "", - "type": "object", - "properties": { - "class": { - "type": "string" - }, - "style": { - "type": "string" - } - }, - "default": {} - }, - "binding": { - "description": "", - "type": "object", - "default": {} - }, - "readonly": { - "type": "string", - "default": false - }, - "title": { - "description": "", - "type": "string", - "default": "" - }, - "label": { - "description": "", - "type": "string", - "default": "" - }, - "lableWidth": { - "description": "", - "type": "number" - }, - "visible": { - "description": "", - "type": "boolean", - "default": true - }, - "data": { - "description": "", - "type": "array", - "default": [] - }, - "direction": { - "description": "", - "type": "string", - "default": "horizontal" - }, - "textField": { - "description": "", - "type": "string", - "default": "name" + "$schema": "https://json-schema.org/draft/2020-12/schema", + "$id": "https://farris-design.gitee.io/check-group.schema.json", + "title": "check-group", + "description": "A Farris Input Component", + "type": "object", + "properties": { + "id": { + "description": "The unique identifier for a Input Group", + "type": "string" + }, + "type": { + "description": "The type string of Input Group component", + "type": "string", + "default": "check-group" + }, + "appearance": { + "description": "", + "type": "object", + "properties": { + "class": { + "type": "string" }, - "valueField": { - "description": "", - "type": "string", - "default": "value" + "style": { + "type": "string" } + }, + "default": {} + }, + "binding": { + "description": "", + "type": "object", + "default": {} + }, + "required": { + "description": "必填", + "type": "boolean", + "default": false + }, + "readonly": { + "type": "string", + "default": false + }, + "visible": { + "description": "", + "type": "boolean", + "default": true + }, + "data": { + "description": "", + "type": "array", + "default": [] + }, + "direction": { + "description": "", + "type": "string", + "default": "vertical" + }, + "textField": { + "description": "", + "type": "string", + "default": "name" + }, + "valueField": { + "description": "", + "type": "string", + "default": "value" }, - "required": [ - "type" - ], - "ignore": [ - "id", - "appearance", - "binding", - "visible" - ] -} \ No newline at end of file + "checkerType": { + "description": "", + "type": "string", + "default": "default" + } + }, + "required": ["type"], + "ignore": ["id", "appearance", "binding", "visible"] +} diff --git a/packages/mobile-ui-vue/components/checkbox-group/src/schema/schema-mapper.ts b/packages/mobile-ui-vue/components/checkbox-group/src/schema/schema-mapper.ts index cbfb41ab58450975f85c6e86786ba4f978d3437c..c414d91b7f5f5f39989f9c4ad92ce87a6e10e169 100644 --- a/packages/mobile-ui-vue/components/checkbox-group/src/schema/schema-mapper.ts +++ b/packages/mobile-ui-vue/components/checkbox-group/src/schema/schema-mapper.ts @@ -1,7 +1,10 @@ -import { MapperFunction, resolveAppearance, resolveData } from '@farris/mobile-ui-vue/dynamic-resolver'; +import { + MapperFunction, + resolveAppearance +} from '@farris/mobile-ui-vue/dynamic-resolver'; export const schemaMapper = new Map([ - ['appearance', resolveAppearance], - ['data', resolveData], + ['appearance', resolveAppearance], + ['data', 'options'], + ['checkerType', 'type'] ]); - diff --git a/packages/mobile-ui-vue/components/checkbox-group/src/schema/schema-resolver.ts b/packages/mobile-ui-vue/components/checkbox-group/src/schema/schema-resolver.ts index 7c8af7fc63d68147438fc329e74ebce565df4ef7..1e756819460221c500d1b646dbd318d77d7cfaf0 100644 --- a/packages/mobile-ui-vue/components/checkbox-group/src/schema/schema-resolver.ts +++ b/packages/mobile-ui-vue/components/checkbox-group/src/schema/schema-resolver.ts @@ -1,5 +1,9 @@ -import { DynamicResolver } from "@farris/mobile-ui-vue/dynamic-resolver"; +import { DynamicResolver } from '@farris/mobile-ui-vue/dynamic-resolver'; -export function schemaResolver(resolver: DynamicResolver, schema: Record, context: Record): Record { - return schema; +export function schemaResolver( + resolver: DynamicResolver, + schema: Record, + context: Record +): Record { + return schema; } diff --git a/packages/mobile-ui-vue/components/checkbox/src/checkbox.component.tsx b/packages/mobile-ui-vue/components/checkbox/src/checkbox.component.tsx index 5510e7d5ae285149ae971fa619e98960addc0485..cb4537077d00783d917c722df6fc5b057f7b86f3 100644 --- a/packages/mobile-ui-vue/components/checkbox/src/checkbox.component.tsx +++ b/packages/mobile-ui-vue/components/checkbox/src/checkbox.component.tsx @@ -1,22 +1,6 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - import { computed, defineComponent } from 'vue'; -import { useLink } from '@farris/mobile-ui-vue/common'; -import { Checker, CheckerRoleMap, CheckerShapeMap } from '@farris/mobile-ui-vue/checker'; +import { useBem, useLink } from '@farris/mobile-ui-vue/common'; +import { Checker, CheckerRole } from '@farris/mobile-ui-vue/checker'; import { CHECKBOX_GROUP_NAME, CheckboxGroupContext } from '@farris/mobile-ui-vue/checkbox-group'; import { CHECKBOX_NAME, @@ -30,6 +14,8 @@ export default defineComponent({ setup(props: CheckboxProps, context) { const { emit } = context; + const { bem } = useBem(CHECKBOX_NAME); + const { getParent } = useLink(CHECKBOX_GROUP_NAME); const checkboxGroup = getParent(); @@ -37,30 +23,25 @@ export default defineComponent({ checkboxGroup?.updateChecked(props.name, checked); emit('change', checked); }; - const handlerUpdateModelValue = (value: boolean) => { - emit('update:modelValue', value); - }; const innerValue = computed(() => { return checkboxGroup?.getChecked ? checkboxGroup.getChecked(props.name) : props.modelValue; }); - const renderCheckbox = () => { - return ( - - ); - }; + const renderCheckbox = () => ( + + ); - return () =>
{renderCheckbox()}
; + return () =>
{renderCheckbox()}
; } }); diff --git a/packages/mobile-ui-vue/components/checkbox/src/checkbox.props.ts b/packages/mobile-ui-vue/components/checkbox/src/checkbox.props.ts index 6fe9e2469b6ff3b2cecd53c18b629bf03aecb525..dd1666b80fdb3cc1c590b35c7afd5205078373e2 100644 --- a/packages/mobile-ui-vue/components/checkbox/src/checkbox.props.ts +++ b/packages/mobile-ui-vue/components/checkbox/src/checkbox.props.ts @@ -1,7 +1,7 @@ import { ExtractPropTypes } from 'vue'; import { checkerProps } from '@farris/mobile-ui-vue/checker'; -export const CHECKBOX_NAME = 'fm-checkbox'; +export const CHECKBOX_NAME = 'FmCheckbox'; export const checkboxProps = { ...checkerProps, diff --git a/packages/mobile-ui-vue/components/checker/src/checker.component.tsx b/packages/mobile-ui-vue/components/checker/src/checker.component.tsx index 82bb9de3ee55810878225d4f8d548f60626ab6e6..2f18ae5b9b57e766e5817b700e14473e9ed66c0f 100644 --- a/packages/mobile-ui-vue/components/checker/src/checker.component.tsx +++ b/packages/mobile-ui-vue/components/checker/src/checker.component.tsx @@ -17,7 +17,7 @@ import { computed, defineComponent, ref, watch } from 'vue'; import { Icon } from '@farris/mobile-ui-vue/icon'; import { useBem } from '@farris/mobile-ui-vue/common'; -import { CheckerProps, checkerProps, CHECKER_NAME, CheckerTypeMap, CheckerShapeMap, CheckerRoleMap } from './checker.props'; +import { CheckerProps, checkerProps, CHECKER_NAME, CheckerType, CheckerShape, CheckerRole } from './checker.props'; export default defineComponent({ name: CHECKER_NAME, @@ -67,8 +67,8 @@ export default defineComponent({ [bem('', 'readonly')]: props.readonly, [bem('', 'disabled')]: props.disabled, [bem('', 'checked')]: innerValue.value, - [bem('', 'round')]: props.shape === CheckerShapeMap.Round, - [bem('', 'button')]: props.type === CheckerTypeMap.Button + [bem('', 'round')]: props.shape === CheckerShape.Round, + [bem('', 'button')]: props.type === CheckerType.Button }; }); @@ -76,7 +76,7 @@ export default defineComponent({ if (props.readonly || props.disabled) { return; } - if(props.role === CheckerRoleMap.Radio && innerValue.value) { + if(props.role === CheckerRole.Radio && innerValue.value) { return; } innerValue.value = !innerValue.value; @@ -86,7 +86,7 @@ export default defineComponent({ return () => (
- {props.type === CheckerTypeMap.Check && renderIcon()} + {props.type === CheckerType.Check && renderIcon()} {props.label && renderLabel()}
); diff --git a/packages/mobile-ui-vue/components/checker/src/checker.props.ts b/packages/mobile-ui-vue/components/checker/src/checker.props.ts index 9befeef8cf3e3f95aa4e057232d0b0468acfbe40..085de6d4d982dff5133d4f82275a752a7df777aa 100644 --- a/packages/mobile-ui-vue/components/checker/src/checker.props.ts +++ b/packages/mobile-ui-vue/components/checker/src/checker.props.ts @@ -1,26 +1,20 @@ import { ExtractPropTypes, PropType } from 'vue'; -export const enum CheckerRoleMap { +export const enum CheckerRole { Checkbox = 'checkbox', Radio = 'radio' } -export const enum CheckerShapeMap { +export const enum CheckerShape { Square = 'square', Round = 'round' } -export const enum CheckerTypeMap { +export const enum CheckerType { Check = 'default', Button = 'button' } -export type CheckerType = `${CheckerTypeMap}`; - -export type CheckerShape = `${CheckerShapeMap}`; - -export type CheckerRole = `${CheckerRoleMap}`; - export const CHECKER_NAME = 'fm-checker'; export const checkerProps = { @@ -32,11 +26,11 @@ export const checkerProps = { readonly: { type: Boolean, default: false }, - type: { type: String as PropType, default: CheckerTypeMap.Check }, + type: { type: String as PropType, default: CheckerType.Check }, - role: { type: String as PropType, default: CheckerRoleMap.Checkbox }, + role: { type: String as PropType, default: CheckerRole.Checkbox }, - shape: { type: String as PropType, default: CheckerShapeMap.Square }, + shape: { type: String as PropType, default: CheckerShape.Square }, labelLimit: { type: Number, default: undefined }, }; diff --git a/packages/mobile-ui-vue/components/common/index.ts b/packages/mobile-ui-vue/components/common/index.ts index c6917cafadcc154e08e45791d964f58244936ad1..463f7bfd49f73cde6c6433052689d0bafdef3217 100644 --- a/packages/mobile-ui-vue/components/common/index.ts +++ b/packages/mobile-ui-vue/components/common/index.ts @@ -1,6 +1,4 @@ export * from './src/compositions'; export * from './src/utils'; -export * from './types'; - -export const FM_UI_PROVIDER_SERVICE_TOKEN = Symbol('UIProviderService'); - +export * from './src/types'; +export * from './src/properties'; diff --git a/packages/mobile-ui-vue/components/common/src/compositions/index.ts b/packages/mobile-ui-vue/components/common/src/compositions/index.ts index cde065de7d2b1150aa5db1d426d427f785b6bed5..d4ed1c00f4d18a1f3cb8e2ce525d22339fd25c3b 100644 --- a/packages/mobile-ui-vue/components/common/src/compositions/index.ts +++ b/packages/mobile-ui-vue/components/common/src/compositions/index.ts @@ -17,3 +17,4 @@ export * from './use-momentum'; export * from './use-scroll-parent'; export * from './use-resize-observer'; export * from './use-long-press'; +export * from './use-designer-component/use-designer-component'; diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/function/use-designer-component.ts b/packages/mobile-ui-vue/components/common/src/compositions/use-designer-component/use-designer-component.ts similarity index 97% rename from packages/mobile-ui-vue/components/designer-canvas/src/composition/function/use-designer-component.ts rename to packages/mobile-ui-vue/components/common/src/compositions/use-designer-component/use-designer-component.ts index 8d6342d347d4e49979a20af797be96e748d51aed..0c31d5f8fd84dff1ecc319d40dbcdb61dda5def6 100644 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/function/use-designer-component.ts +++ b/packages/mobile-ui-vue/components/common/src/compositions/use-designer-component/use-designer-component.ts @@ -1,7 +1,7 @@ import { Ref, ref } from "vue"; -import { DesignerHostService, DesignerHTMLElement, DraggingResolveContext, UseDesignerRules } from "../types"; -import { ComponentSchema, DesignerComponentInstance, DesignerItemContext } from "../../types"; -import { getSchemaByTypeForDesigner } from '../../../../dynamic-resolver/src/resolver/schema/schema-resolver-design'; +import { DesignerHostService, DesignerHTMLElement, DraggingResolveContext, UseDesignerRules } from "../../types/designer-rule"; +import { ComponentSchema, DesignerComponentInstance, DesignerItemContext } from "../../types/designer-component"; +import { getSchemaByTypeForDesigner } from '@farris/mobile-ui-vue/dynamic-resolver/src/resolver/schema/schema-resolver-design'; export function useDesignerComponent( elementRef: Ref, diff --git a/packages/mobile-ui-vue/components/common/src/entity/base-property.ts b/packages/mobile-ui-vue/components/common/src/entity/base-property.ts deleted file mode 100644 index fa1776ca76eb2c7dd5d9761831d682ae3d26aff4..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/common/src/entity/base-property.ts +++ /dev/null @@ -1,129 +0,0 @@ -import { DesignerComponentInstance, DgControl } from "@farris/mobile-ui-vue/designer-canvas"; -import { cloneDeep } from "lodash-es"; - -/** - * 控件属性基类 - */ -export class BaseControlProperty { - public componentId: string; - - public viewModelId: string; - - public eventsEditorUtils: any; - - public formSchemaUtils: any; - public formMetadataConverter: any; - public designViewModelUtils: any; - public designViewModelField: any; - public controlCreatorUtils: any; - public designerHostService: any; - - schemaService: any = null; - - metadataService: any = null; - - protected propertyConfig = { - type: 'object', - categories: {} - }; - - constructor(componentId: string, designerHostService: any) { - this.componentId = componentId; - this.designerHostService = designerHostService; - this.eventsEditorUtils = designerHostService['eventsEditorUtils']; - this.formSchemaUtils = designerHostService['formSchemaUtils']; - this.formMetadataConverter = designerHostService['formMetadataConverter']; - this.viewModelId = this.formSchemaUtils?.getViewModelIdByComponentId(componentId) || ''; - this.designViewModelUtils = designerHostService['designViewModelUtils']; - this.controlCreatorUtils = designerHostService['controlCreatorUtils']; - this.metadataService = designerHostService['metadataService']; - this.schemaService = designerHostService['schemaService']; - } - - getTableInfo() { - return this.schemaService?.getTableInfoByViewModelId(this.viewModelId); - } - - setDesignViewModelField(propertyData: any) { - const bindingFieldId = propertyData.binding && propertyData.binding.type === 'Form' && propertyData.binding.field; - // 视图模型中[字段更新时机]属性现在要在控件上维护,所以在控件上复制一份属性值 - if (bindingFieldId) { - if (!this.designViewModelField) { - const dgViewModel = this.designViewModelUtils.getDgViewModel(this.viewModelId); - this.designViewModelField = dgViewModel.fields.find(f => f.id === bindingFieldId); - } - propertyData.updateOn = this.designViewModelField?.updateOn; - } - } - - getBasicPropConfig(propertyData: any): any { - return { - description: 'Basic Information', - title: '基本信息', - properties: { - id: { - description: '组件标识', - title: '标识', - type: 'string', - readonly: true - }, - type: { - description: '组件类型', - title: '控件类型', - type: 'select', - editor: { - type: 'combo-list', - textField: 'name', - valueField: 'value', - editable: false, - data: [{ value: propertyData.type, name: DgControl[propertyData.type] && DgControl[propertyData.type].name }] - } - } - } - }; - - } - - - protected getAppearanceConfig(propertyData = null): any { - return { - title: "外观", - description: "Appearance", - properties: { - class: { - title: "class样式", - type: "string", - description: "组件的CSS样式", - $converter: "/converter/appearance.converter" - }, - style: { - title: "style样式", - type: "string", - description: "组件的样式", - $converter: "/converter/appearance.converter" - } - } - }; - } - - /** - * - * @param propertyId - * @param componentInstance - * @returns - */ - public updateElementByParentContainer(propertyId: string, componentInstance: DesignerComponentInstance) { - // 1、定位控件父容器 - const parentContainer = componentInstance && componentInstance.parent && componentInstance.parent['schema']; - if (!parentContainer) { - return; - } - const index = parentContainer.contents.findIndex(c => c.id === propertyId); - // 通过cloneDeep方式的触发更新 - const controlSchema = cloneDeep(parentContainer.contents[index]); - // 5、替换控件 - parentContainer.contents.splice(index, 1); - parentContainer.contents.splice(index, 0, controlSchema); - } - -} diff --git a/packages/mobile-ui-vue/components/common/src/properties/base-property.ts b/packages/mobile-ui-vue/components/common/src/properties/base-property.ts new file mode 100644 index 0000000000000000000000000000000000000000..f1dd8fb14772bc0042ef36720bde9261a1a88655 --- /dev/null +++ b/packages/mobile-ui-vue/components/common/src/properties/base-property.ts @@ -0,0 +1,374 @@ +import { cloneDeep } from "lodash-es"; +// import { refreshCanvas } from "../../../../common/src/composition/update-cancas"; +// import { canvasChanged } from "../../../../common/src/composition/common-changed"; +import { ExpressionProperty } from "./expression-property"; +import { usePropertyEditor } from "./use-property-editor"; +import { DgControl } from "./dg-control"; +import { DesignerComponentInstance, PropertyChangeObject } from "../types"; + +/** + * 控件属性基类 + */ +export class BaseControlProperty { + public componentId: string; + + public viewModelId: string; + + public eventsEditorUtils: any; + + public formSchemaUtils: any; + public formMetadataConverter: any; + public designViewModelUtils: any; + public designViewModelField: any; + public controlCreatorUtils: any; + public designerHostService: any; + + schemaService: any = null; + + metadataService: any = null; + + protected propertyConfig = { + type: 'object', + categories: {} + }; + + constructor(componentId: string, designerHostService: any) { + this.componentId = componentId; + this.designerHostService = designerHostService; + this.eventsEditorUtils = designerHostService['eventsEditorUtils']; + this.formSchemaUtils = designerHostService['formSchemaUtils']; + this.formMetadataConverter = designerHostService['formMetadataConverter']; + this.viewModelId = this.formSchemaUtils?.getViewModelIdByComponentId(componentId) || ''; + this.designViewModelUtils = designerHostService['designViewModelUtils']; + this.controlCreatorUtils = designerHostService['controlCreatorUtils']; + this.metadataService = designerHostService['metadataService']; + this.schemaService = designerHostService['schemaService']; + } + + getTableInfo() { + return this.schemaService?.getTableInfoByViewModelId(this.viewModelId); + } + + setDesignViewModelField(propertyData: any) { + const bindingFieldId = propertyData.binding && propertyData.binding.type === 'Form' && propertyData.binding.field; + // 视图模型中[字段更新时机]属性现在要在控件上维护,所以在控件上复制一份属性值 + if (bindingFieldId) { + if (!this.designViewModelField) { + const dgViewModel = this.designViewModelUtils.getDgViewModel(this.viewModelId); + this.designViewModelField = dgViewModel.fields.find(f => f.id === bindingFieldId); + } + propertyData.updateOn = this.designViewModelField?.updateOn; + } + } + + getBasicPropConfig(propertyData: any): any { + return { + description: 'Basic Information', + title: '基本信息', + properties: { + id: { + description: '组件标识', + title: '标识', + type: 'string', + readonly: true + }, + type: { + description: '组件类型', + title: '控件类型', + type: 'select', + editor: { + type: 'combo-list', + textField: 'name', + valueField: 'value', + idField: 'value', + editable: false, + data: [{ value: propertyData.type, name: DgControl[propertyData.type] && DgControl[propertyData.type].name }] + } + } + } + }; + + } + + + protected getAppearanceConfig(propertyData = null, properties = {}, setPropertyRelates?: (changeObject, propertyData, parameters) => any): any { + const appearanceBasic = { + title: "外观", + description: "Appearance", + }; + const appearancePoperties = { + class: { + title: "class样式", + type: "string", + description: "组件的CSS样式", + $converter: "/converter/appearance.converter" + }, + style: { + title: "style样式", + type: "string", + description: "组件的样式", + $converter: "/converter/appearance.converter" + } + + }; + for (const key in properties) { + // 合并属性,保留原属性值 + appearancePoperties[key] = Object.assign(appearancePoperties[key] || {}, properties[key]); + } + return { + ...appearanceBasic, properties: { ...appearancePoperties }, setPropertyRelates(changeObject, parameters: any) { + if (!changeObject) { + return; + } + if (!changeObject) { + return; + } + switch (changeObject && changeObject.propertyID) { + case 'class': case 'style': { + // canvasChanged.value++; + break; + } + } + if (setPropertyRelates) { + setPropertyRelates(changeObject, propertyData, parameters); + } + } + + }; + } + protected getPropertyEditorParams(propertyData, propertyTypes: any = [], propertyName = 'visible', constInfos = {}, variableInfos = {}) { + const { getVariables, getControlName, getStateMachines } = usePropertyEditor(this.designerHostService); + const targetType = this.getRealTargetType(propertyData); + const newPropertyTypes = propertyTypes && propertyTypes.length > 0 ? propertyTypes : ['Const', 'Variable', 'Custom', 'StateMachine', 'Expression']; + const resultProperty = { + type: "property-editor", + propertyTypes: newPropertyTypes + }; + newPropertyTypes.map(item => { + switch (item) { + case 'Const': + Object.assign(resultProperty, { + constType: 'enum', + constEnums: [{ id: true, name: '是' }, { id: false, name: '否' }] + }, constInfos); + break; + case 'Expression': + resultProperty['expressionConfig'] = this.getExpressionOptions(propertyData, targetType, propertyName); + break; + case 'StateMachine': + resultProperty['stateMachines'] = getStateMachines(this.viewModelId); + break; + case 'Variable': + Object.assign(resultProperty, { + controlName: getControlName(propertyData), + newVariablePrefix: 'is', + newVariableType: 'Boolean', + variables: getVariables(this.viewModelId) + }, variableInfos); + break; + } + }); + return resultProperty; + } + + protected getVisibleProperty(propertyData, position = '') { + const editor = this.getPropertyEditorParams(propertyData, position === 'gridFieldEditor' ? ['Const', 'Expression'] : ['Const', 'Variable', 'Custom', 'StateMachine', 'Expression'], 'visible'); + return { + visible: { + title: "是否可见", + type: "boolean", + description: "运行时组件是否可见", + editor + } + }; + } + /** + * 获取行为 + * @param propertyData + * @param viewModelId + * @returns + */ + public getBehaviorConfig(propertyData: any, position = '', properties = {}, setPropertyRelates?: any): any { + const behaviorBasic = { + title: "行为", + description: "" + }; + const behaviorPoperties = this.getVisibleProperty(propertyData, position); + for (const key in properties) { + // 合并属性,保留原属性值 + behaviorPoperties[key] = Object.assign(behaviorPoperties[key] || {}, properties[key]); + } + const self = this; + + return { + ...behaviorBasic, properties: { ...behaviorPoperties }, setPropertyRelates(changeObject, parameters: any) { + if (!changeObject) { + return; + } + switch (changeObject.propertyID) { + case 'disabled': + case 'readonly': + case 'visible': + self.afterMutilEditorChanged(propertyData, changeObject); + break; + } + if (setPropertyRelates) { + setPropertyRelates(changeObject, parameters); + } + } + + }; + } + /** + * 当多值编辑器变更时 + * @param propertyData + * @param changeObject + */ + public afterMutilEditorChanged(propertyData, changeObject) { + // 变量 + this.addNewVariableToViewModel(changeObject, this.viewModelId); + // 更新表达式 + this.updateExpressionValue(changeObject); + // 清空表达式 + this.clearExpression(changeObject, propertyData); + } + + /** + * 更新element + * @param propertyId + * @param componentInstance + * @returns + */ + public updateElementByParentContainer(propertyId: string, componentInstance: DesignerComponentInstance) { + // 1、定位控件父容器 + const parentContainer = componentInstance && componentInstance.parent && componentInstance.parent['schema']; + if (!parentContainer) { + return; + } + const index = parentContainer.contents.findIndex(c => c.id === propertyId); + // 通过cloneDeep方式的触发更新 + const controlSchema = cloneDeep(parentContainer.contents[index]); + // 5、替换控件 + parentContainer.contents.splice(index, 1); + parentContainer.contents.splice(index, 0, controlSchema); + // refreshCanvas(); + } + + /** + * 属性编辑器,在编辑过程中会新增变量,此处需要将新增的变量追加到ViewModel中 + * @param changeObject + * @param viewModelId + * @returns + */ + public addNewVariableToViewModel(changeObject: PropertyChangeObject, viewModelId: string) { + const newPropertyValue = changeObject.propertyValue; + // 1、判断当前属性值是否为对象 + const isObject = newPropertyValue && typeof newPropertyValue === 'object'; + if (!isObject) { + return; + } + + // 2、判断是否为新变量 + const isNewVariable = newPropertyValue.type === 'Variable' && newPropertyValue.isNewVariable; + if (!isNewVariable) { + return; + } + + // 3、构造变量结构 + const newVariable = { + id: newPropertyValue.field, + category: 'locale', + code: newPropertyValue.fullPath, + name: newPropertyValue.fullPath, + type: newPropertyValue.newVariableType || 'String' + }; + delete newPropertyValue.newVariableType; + delete newPropertyValue.isNewVariable; + + // 4、把新变量添加到ViewModel中 + const existedVariable = this.formSchemaUtils.getVariableByCode(newVariable.code); + if (!existedVariable) { + const viewModel = this.formSchemaUtils.getViewModelById(viewModelId); + viewModel.states.push(newVariable); + } + } + + /** + * 更新表达式到expressions节点 + * @param changeObject + */ + public updateExpressionValue(changeObject: PropertyChangeObject) { + const newPropertyValue = changeObject.propertyValue; + const newValueType = newPropertyValue && newPropertyValue.type; + + // 1、判断是否需要更新表达式 + const needUpdateExpression = newValueType === 'Expression' && newPropertyValue.expressionInfo; + if (!needUpdateExpression) { + return; + } + + const { expressionId, expressionInfo } = newPropertyValue; + const { targetId, targetType, expressionType, value, message } = expressionInfo; + const module = this.formSchemaUtils.getModule(); + module.expressions ??= []; + const { expressions } = module; + + // 2、获取目标表达式,如果不存在,则创建一个空的目标表达式 + let targetExpression = expressions.find(expression => expression.target === targetId); + if (!targetExpression) { + targetExpression = { target: targetId, rules: [], targetType }; + expressions.push(targetExpression); + } + + // 3、更新表达式 + const expressionItem = targetExpression.rules.find(rule => rule.type === expressionType); + if (expressionItem) { + expressionItem.value = value; + expressionItem.message = message; + } else { + const newExpressionRule = { id: expressionId, type: expressionType, value, message }; + targetExpression.rules.push(newExpressionRule); + } + delete newPropertyValue.expressionInfo; + } + + /** + * 属性类型切换为非表达式后,清除原表达式 + * @param changeObject + * @param propertyData + * @returns + */ + clearExpression(changeObject: PropertyChangeObject, propertyData: any) { + const newPropertyValue = changeObject.propertyValue; + const isExpression = newPropertyValue && newPropertyValue.type === 'Expression'; + // 1、如果为当前属性为表达式,则不需要清空 + if (isExpression) { + return; + } + + // 2、属性值不是表达式后,需要清空表达式 + const expressionType = changeObject.propertyID; + const expressions = this.formSchemaUtils.getExpressions(); + + const targetId = propertyData.binding ? propertyData.binding.field : propertyData.id; + const targetExpression = expressions.find(expression => expression.target === targetId); + if (!targetExpression || !targetExpression.rules) { + return; + } + targetExpression.rules = targetExpression.rules.filter(rule => rule.type !== expressionType); + } + + getExpressionOptions(propertyData: any, targetType: 'Field' | 'Button' | 'Container', expressionType: string) { + return new ExpressionProperty(this.formSchemaUtils).getExpressionOptions(propertyData, targetType, expressionType); + } + + getRealTargetType(propertyData: any,) { + if (['response-toolbar-item', 'tab-toolbar-item', 'section-toolbar-item'].indexOf(propertyData.type) > -1) { + return 'Button'; + } + if (propertyData.binding && propertyData.binding.field) { + return 'Field'; + } + return 'Container'; + } +} diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/dg-control.ts b/packages/mobile-ui-vue/components/common/src/properties/dg-control.ts similarity index 100% rename from packages/mobile-ui-vue/components/designer-canvas/src/composition/dg-control.ts rename to packages/mobile-ui-vue/components/common/src/properties/dg-control.ts diff --git a/packages/mobile-ui-vue/components/common/src/properties/expression-property.ts b/packages/mobile-ui-vue/components/common/src/properties/expression-property.ts new file mode 100644 index 0000000000000000000000000000000000000000..24b91f61777f5ec22452f8d872d6b9f879d98706 --- /dev/null +++ b/packages/mobile-ui-vue/components/common/src/properties/expression-property.ts @@ -0,0 +1,385 @@ +export interface RuleModel { + id: string; + type: 'compute' | 'dependency' | 'validate' | 'visible' | 'readonly' | 'required' | 'dataPicking' | string; + value: string; + message?: string; + elementId?: string; + messageType?: string; +} + +export interface ExpressionModel { + target: string; + rules: Array; + targetType: string; +} + + +export class ExpressionProperty { + + private sessionVariables = [ + { + key: "CurrentSysOrgName", + name: "当前组织Name", + description: "当前组织Name" + }, + // { + // key: "CurrentSysOrgCode", + // name: "当前组织Code", + // description: "当前组织Code" + // }, + { + key: "CurrentSysOrgId", + name: "当前组织Id", + description: "当前组织Id" + }, + { + key: "CurrentUserName", + name: "当前用户Name", + description: "当前用户Name" + }, + { + key: "CurrentUserCode", + name: "当前用户Code", + description: "当前用户Code" + }, + { + key: "CurrentUserId", + name: "当前用户Id", + description: "当前用户Id" + }, + { + key: "CurrentLanguage", + name: "当前语言编号", + description: "当前登录的语言编号,例如简体中文返回'zh-CHS',英文返回'en',繁体中文'zh-CHT'" + } + ]; + + constructor(private formSchemaService: any) { + } + + private getExpressionRule(expressionId: any, rultType: string) { + const expressions = this.formSchemaService.getExpressions(); + if (!expressions) { + return ''; + } + const expressionItem = expressions.find(item => item.target === expressionId); + if (!expressionItem) { + return ''; + } + + const ruleItem = expressionItem.rules.find(item => item.type === rultType); + if (!ruleItem) { + return ''; + } + + return ruleItem; + } + + // 获取上下文表单变量 + private getContextFormVariables() { + const { module } = this.formSchemaService.getFormSchema(); + if (!module.viewmodels || module.viewmodels.length === 0) { + return []; + } + + const rootViewModelId = this.formSchemaService.getRootViewModelId(); + const viewModel = this.formSchemaService.getViewModelById(rootViewModelId); + + if (!viewModel || !viewModel.states || viewModel.states.length === 0) { + return []; + } + + const contextEntities: any = []; + viewModel.states.forEach(variable => { + if (variable.category === 'remote') { + contextEntities.push({ + key: variable.code, + name: variable.name, + description: variable.name + }); + } + }); + return contextEntities; + } + + private createTreeNode(element: any, parentCodes: string[], fieldName = 'label') { + return { + id: element.id, + name: element.name, + bindingPath: element[fieldName], + parents: parentCodes + }; + } + + + private buildEntityFieldsTreeData(fields: any[] | null = null, parentCodes: string[]): any[] { + const treeData: any[] = []; + fields?.forEach(element => { + const nodeData = this.createTreeNode(element, parentCodes); + + let children: any[] = []; + if (element.type?.fields) { + children = this.buildEntityFieldsTreeData(element.type.fields, [...parentCodes, element.label]); + } + + treeData.push({ + data: nodeData, + children, + expanded: true + }); + }); + return treeData; + } + + private buildChildEntityTreeData(entities: any[] | null = null, parentCodes: string[]): any[] { + const treeData: any[] = []; + entities?.forEach(element => { + const nodeData = this.createTreeNode(element, parentCodes); + + const children = this.buildEntityFieldsTreeData(element.type?.fields, [...parentCodes, element.label]); // 可选链 + const childEntities = this.buildChildEntityTreeData(element.type?.entities, [...parentCodes, element.label]); // 可选链 + + if (childEntities?.length) { // 空值检查 + children?.push(...childEntities); + } + + treeData.push({ + data: nodeData, + children: children || [], // 空值回退 + expanded: true + }); + }); + return treeData; + } + + private getEntitiesTreeData() { + const entities = this.formSchemaService.getSchemaEntities(); + if (!entities?.length) { // 空值检查 + return []; + } + + const mainTable = entities[0]; + if (!mainTable?.type) { return []; } // 空值检查 + + const childFields = this.buildEntityFieldsTreeData(mainTable.type.fields, [mainTable.code]); + const childEntities = this.buildChildEntityTreeData(mainTable.type.entities, [mainTable.code]); + + if (childEntities?.length) { // 空值检查 + childFields?.push(...childEntities); + } + + return { + entityCode: mainTable.code, + fields: [{ + data: this.createTreeNode(mainTable, [], 'code'), + children: childFields || [] + }] + }; + } + + + getEntitiesAndVariables() { + return { + entities: this.getEntitiesTreeData(), + variables: { + session: { + name: '系统变量', + items: this.sessionVariables + }, + forms: { + name: '表单变量', + items: this.getContextFormVariables() + } + } + }; + } + + private onBeforeOpenExpression(propertyData: any, expressionType: string, targetType: string) { + const expressionId = targetType === 'Field' ? propertyData.binding.field : propertyData.id; + const rule = this.getExpressionRule(expressionId, expressionType); + const entitiesAndVariables = this.getEntitiesAndVariables(); + const data: any = { + message: ['validate', 'required','dataPicking'].includes(expressionType) && rule ? rule.message : '', + ...entitiesAndVariables + }; + + if (rule.messageType != null) { + data.messageType = rule.messageType; + } + + return data; + } + + private buildRule(targetId, expressionObject: Record, ruleType: string, controlId?: string) { + const { expression: expressionValue, message, messageType } = expressionObject; + const rule: RuleModel = { + id: `${targetId}_${ruleType}`, + type: ruleType, + value: expressionValue, + message, + messageType + }; + + if (ruleType === 'validate' && controlId) { + rule.elementId = controlId; + } + + return rule; + } + + private getExpressionData(): Array { + const { expressions } = this.formSchemaService.getFormSchema().module; + return expressions || []; + } + + private updateExpression(propertyData: any, + targetType: 'Field' | 'Button' | 'Container', + expressionObject: Record, ruleType: string) { + const targetId = targetType === 'Field' ? propertyData.binding.field : propertyData.id; + const newRule = this.buildRule(targetId, expressionObject, ruleType, propertyData.type === 'form-group' ?propertyData.id: ''); + + const currentExpressiones = this.getExpressionData(); + let expressionItem = currentExpressiones.find((item: ExpressionModel) => { + return item.targetType === targetType && item.target === targetId; + }); + + // 提取重复逻辑:判断 value 是否为空 + const isValueEmpty = (rule: RuleModel): boolean => rule.value.trim() === ''; + + if (expressionItem) { + const ruleItem = expressionItem.rules.find((rule) => rule.id === newRule.id); + if (ruleItem) { + if (isValueEmpty(newRule)) { + expressionItem.rules = expressionItem.rules.filter((rule) => rule.id !== newRule.id); + } else { + ruleItem.value = newRule.value; + ruleItem.message = newRule.message; + + if (ruleType === 'dataPicking') { + ruleItem.messageType = newRule.messageType; + } + + if (ruleType === 'validate' && propertyData.type === 'form-group') { + ruleItem.elementId = propertyData.id; + } + } + } else { + if (isValueEmpty(newRule)) { + return null; + } + + expressionItem.rules = expressionItem.rules || []; + expressionItem.rules.push(newRule); + } + } else { + + if (isValueEmpty(newRule)) { + return null; + } + + expressionItem = { + target: `${targetId}`, + rules: [newRule], + targetType: targetType + }; + + } + return expressionItem; + } + + private expressionNames = { + compute: '计算表达式', + dependency: '依赖表达式', + validate: '验证表达式', + dataPicking: '帮助前表达式', + visible: '可见表达式', + readonly: '只读表达式', + required: '必填表达式' + }; + + private getExpressionConverter = (expressionId: string, ruleType?: string) => { + return { + convertFrom: (schema: Record, propertyKey: string, schemaService, componentId) => { + const rule = schemaService.getExpressionRuleValue(expressionId, ruleType || propertyKey); + return rule && rule.value || ''; + }, + convertTo: (schema: Record, propertyKey: string, propertyValue: any[], + schemaService, componentId + ) => { + schemaService.updateExpression(propertyValue); + } + }; + }; + + private getExpressionEditorOptions(propertyData, targetType: 'Field' | 'Button' | 'Container', + expressionTypes: string[], callback?: (rule: Record) => void) { + return expressionTypes.reduce((expressions: Record, name: string) => { + const expressionId = targetType === 'Field' ? propertyData?.binding?.field : propertyData.id; + expressions[name] = { + hide: targetType === 'Field' ? !!propertyData?.binding?.field : false, + description: "", + title: this.expressionNames[name], + type: "string", + $converter: this.getExpressionConverter(expressionId), + editor: { + type: "expression-editor", + singleExpand: false, + dialogTitle: `${this.expressionNames[name]}编辑器`, + showMessage: name === 'validate' || name === 'dataPicking', + showMessageType: name === 'dataPicking', + beforeOpen: () => { + return this.onBeforeOpenExpression(propertyData, name, targetType); + }, + onSubmitModal: (expressionObject: any) => { + const expressionData: any = this.updateExpression(propertyData, targetType, expressionObject, name); + if (callback) { + const rule = this.buildRule(expressionId, expressionObject, name); + callback(rule); + } + return expressionData; + } + } + }; + + return expressions; + }, {}); + } + + private getExpressionInfo(propertyData: any, targetType: 'Field' | 'Button' | 'Container', expressionType: string) { + const targetId = targetType === 'Field' ? propertyData.binding.field : propertyData.id; + const expressionRule = this.getExpressionRule(targetId, expressionType); + const expressionInfo = { + value: expressionRule && expressionRule.value, + message: expressionRule && expressionRule.message, + targetId, + targetType, + expressionType + }; + return expressionInfo; + } + + getExpressionConfig(propertyData: any, type: 'Field' | 'Button' | 'Container', + expressionTypes: string[] = ['compute', 'dependency', 'validate'], + callback?: (rule: Record) => void) { + return { + description: "表达式", + title: "表达式", + properties: { + ...this.getExpressionEditorOptions(propertyData, type, expressionTypes, callback) + } + }; + } + + getExpressionOptions(propertyData: any, targetType: 'Field' | 'Button' | 'Container', expressionType: string) { + const expressionInfo = this.getExpressionInfo(propertyData, targetType, expressionType); + return { + dialogTitle: `${this.expressionNames[expressionType]}编辑器`, + singleExpand: false, + showMessage: expressionType === 'require', + beforeOpen: () => { + return this.onBeforeOpenExpression(propertyData, expressionType, targetType); + }, + expressionInfo + }; + } +} diff --git a/packages/mobile-ui-vue/components/common/src/properties/index.ts b/packages/mobile-ui-vue/components/common/src/properties/index.ts new file mode 100644 index 0000000000000000000000000000000000000000..d95bdeae6a141ba60c8f591fd316a3216b861d33 --- /dev/null +++ b/packages/mobile-ui-vue/components/common/src/properties/index.ts @@ -0,0 +1,4 @@ +export * from './dg-control'; +export { SchemaDOMMapping } from './schema-dom-mapping'; +export { BaseControlProperty } from './base-property'; +export { InputBaseProperty } from './input-base-property'; diff --git a/packages/mobile-ui-vue/components/common/src/entity/input-base-property.ts b/packages/mobile-ui-vue/components/common/src/properties/input-base-property.ts similarity index 35% rename from packages/mobile-ui-vue/components/common/src/entity/input-base-property.ts rename to packages/mobile-ui-vue/components/common/src/properties/input-base-property.ts index ce09243094574836b7e9edfd00b4621669bb4a8f..c563a8c9562aa52163ea7cefa9ae920a7b88264d 100644 --- a/packages/mobile-ui-vue/components/common/src/entity/input-base-property.ts +++ b/packages/mobile-ui-vue/components/common/src/properties/input-base-property.ts @@ -1,27 +1,43 @@ -import { BaseControlProperty } from './base-property'; -import { DesignerComponentInstance } from "@farris/mobile-ui-vue/designer-canvas"; -import { SchemaDOMMapping } from "@farris/mobile-ui-vue/property-panel"; -import { canvasChanged } from "@farris/mobile-ui-vue/designer-canvas/src/composition/designer-canvas-changed"; -import { FormSchemaEntityFieldType$Type } from './entity-schema'; + +import { BaseControlProperty } from "./base-property"; +import { SchemaDOMMapping } from './schema-dom-mapping'; +import { ExpressionProperty } from "./expression-property"; +import { FormSchemaEntityField$Type, FormSchemaEntityFieldType$Type, FormVariable } from "../types/entity-schema"; +import { DesignerComponentInstance, FormBindingType, FormPropertyChangeObject } from "../types"; +import { DgControl } from "./dg-control"; export class InputBaseProperty extends BaseControlProperty { + /** 控件绑定的变量 */ + public bindingVarible?: FormVariable; + + public labelAlignVisible = true; + public labelAlignReadonly = false; + constructor(componentId: string, designerHostService: any) { super(componentId, designerHostService); } - - public getPropertyConfig(propertyData: any, componentInstance: DesignerComponentInstance) { + private getCommonPropertyConfig(propertyData: any, componentInstance: DesignerComponentInstance | null) { // 基本信息 this.propertyConfig.categories['basic'] = this.getBasicProperties(propertyData, componentInstance); // 外观 this.propertyConfig.categories['appearance'] = this.getAppearanceProperties(propertyData, componentInstance); + this.propertyConfig.categories['behavior'] = this.getBehaviorConfig(propertyData); // 编辑器 this.propertyConfig.categories['editor'] = this.getEditorProperties(propertyData); + // 表达式编辑器 + this.propertyConfig.categories['expressons'] = this.getExpressionConfig(propertyData, 'Field'); + } + public getPropertyConfig(propertyData: any, componentInstance: DesignerComponentInstance) { + this.getCommonPropertyConfig(propertyData, componentInstance); + // 事件 暂不支持 + // this.propertyConfig.categories['eventsEditor'] = this.getEventPropertyConfig(propertyData); return this.propertyConfig; } public getBasicProperties(propertyData, componentInstance): any { const self = this; this.setDesignViewModelField(propertyData); + const { canChangeControlType, editorTypeList } = this.getAvailableEditorType(propertyData); return { description: 'Basic Information', title: '基本信息', @@ -36,20 +52,16 @@ export class InputBaseProperty extends BaseControlProperty { description: '编辑器类型', title: '编辑器类型', type: 'string', - refreshPanelAfterChanged: true, $converter: '/converter/change-editor.converter', editor: { type: 'combo-list', textField: 'value', valueField: 'key', + idField: 'key', editable: false, - data: self.designViewModelField ? SchemaDOMMapping.getEditorTypesByMDataType(self.designViewModelField.type?.name) : SchemaDOMMapping.getAllInputTypes() - } - }, - label: { - title: "标签", - type: "string", - $converter: '/converter/form-group-label.converter' + data: editorTypeList, + readonly: !canChangeControlType + }, }, binding: { description: "绑定的表单字段", @@ -65,10 +77,34 @@ export class InputBaseProperty extends BaseControlProperty { disableOccupiedFields: true }, textField: 'bindingField' - } + }, + refreshPanelAfterChanged: true + }, + label: { + title: "标签", + type: "string", + $converter: '/converter/form-group-label.converter' + }, + labelAlign: { + title: "标签排列方式", + type: "string", + $converter: '/converter/form-group-label.converter', + visible: this.labelAlignVisible, + editor: { + type: 'combo-list', + data: [{id: 'left', name: '左侧'},{id: 'top', name: '上侧'}], + readonly: this.labelAlignReadonly + }, + refreshPanelAfterChanged: true + }, + labelWidth: { + title: "标签宽度", + type: "string", + $converter: '/converter/form-group-label.converter', + visible: propertyData.labelAlign !== 'top' } }, - setPropertyRelates(changeObject, prop) { + setPropertyRelates(changeObject, prop, paramters: any) { if (!changeObject) { return; } @@ -81,10 +117,72 @@ export class InputBaseProperty extends BaseControlProperty { changeObject.needRefreshControlTree = true; break; } + case 'binding': { + self.changeBindingField(propertyData, changeObject, paramters); + break; + } } } }; } + + /** + * 校验控件是否支持切换类型 + * @param control 控件 + */ + private checkCanChangeControlType(propertyData: any, viewModelId: string): boolean { + // 没有绑定信息的控件 + if (!propertyData.binding) { + return false; + } + + if (propertyData.binding.type === 'Variable') { + this.bindingVarible = this.formSchemaUtils.getVariableById(propertyData.binding.field); + // vm中已移除的变量 + if (!this.bindingVarible) { + return false; + } + } else { + // schema中已移除的字段 或者绑定复杂类型的字段 + if (!this.designViewModelField || this.designViewModelField.$type !== FormSchemaEntityField$Type.SimpleField) { + return false; + } + } + return true; + + } + /** + * 获取可选的编辑器类型 + */ + private getAvailableEditorType(propertyData: any) { + const canChangeControlType = this.checkCanChangeControlType(propertyData, this.viewModelId); + if (!canChangeControlType) { + return { + canChangeControlType: false, + editorTypeList: [{ + key: propertyData.editor.type, + value: DgControl[propertyData.editor.type]?.name || propertyData.editor.type + }] + }; + } + + let editorTypeList: any = []; + if (this.designViewModelField && this.designViewModelField.$type === FormSchemaEntityField$Type.SimpleField) { + // 绑定字段 + editorTypeList = SchemaDOMMapping.getEditorTypesByMDataType(this.designViewModelField.type.name); + } else if (this.bindingVarible) { + // 绑定变量 + editorTypeList = SchemaDOMMapping.getEditorTypesByMDataType(this.bindingVarible.type); + } + return { canChangeControlType, editorTypeList }; + } + + public changeBindingField(propertyData: any, changeObject: FormPropertyChangeObject, paramters?: any): any { + // 刷新实体树 + // changeObject.needRefreshEntityTree = true; + } + + public getAppearanceProperties(propertyData, componentInstance): any { const self = this; @@ -101,9 +199,10 @@ export class InputBaseProperty extends BaseControlProperty { style: { title: "style样式", type: "string", - description: "组件的样式", + description: "组件的内联样式", $converter: "/converter/appearance.converter" } + }, setPropertyRelates(changeObject, prop) { if (!changeObject) { @@ -111,8 +210,13 @@ export class InputBaseProperty extends BaseControlProperty { } switch (changeObject && changeObject.propertyID) { case 'class': - self.updateElementByParentContainer(propertyData.id, componentInstance); + self.updateUnifiedLayoutAfterControlChanged(changeObject.propertyValue, propertyData.id, this.componentId); + // canvasChanged.value++; + break; + case 'style': { + // canvasChanged.value++; break; + } } } @@ -129,7 +233,7 @@ export class InputBaseProperty extends BaseControlProperty { * @param propertyData 控件DOM属性 * @param newControlType 新控件类型 */ - private changeControlType(propertyData, changeObject, componentInstance: DesignerComponentInstance) { + private changeControlType(propertyData, changeObject, componentInstance: DesignerComponentInstance | null) { const newControlType = changeObject.propertyValue; // 1、定位控件父容器 @@ -139,20 +243,24 @@ export class InputBaseProperty extends BaseControlProperty { } const index = parentContainer.contents.findIndex(c => c.id === propertyData.id); + if (index === -1) { + return; + } const oldControl = parentContainer.contents[index]; let newControl; - // 2、记录绑定字段viewModel的变更 + if (this.designViewModelField) { + // 2、记录绑定字段viewModel的变更 + const viewModel = this.formSchemaUtils.getViewModelById(this.viewModelId); + const viewModelField = viewModel.fields.find(field => field.id === this.designViewModelField.id); + const viewModelFieldSchema = viewModelField.fieldSchema || {}; + if (!viewModelFieldSchema.editor) { viewModelFieldSchema.editor = {}; } + viewModelFieldSchema.editor.$type = newControlType; + const dgViewModel = this.designViewModelUtils.getDgViewModel(this.viewModelId); - dgViewModel.changeField(this.designViewModelField.id, { - editor: { - $type: newControlType - }, - name: this.designViewModelField.name, - require: this.designViewModelField.require, - readonly: this.designViewModelField.readonly - }, false); + dgViewModel.changeField(this.designViewModelField.id, viewModelFieldSchema, false); + // 3、创建新控件 newControl = this.controlCreatorUtils.setFormFieldProperty(this.designViewModelField, newControlType); } @@ -165,21 +273,26 @@ export class InputBaseProperty extends BaseControlProperty { appearance: oldControl.appearance, size: oldControl.size, label: oldControl.label, - binding: oldControl.binding, - visible: oldControl.visible - }); - Object.assign(newControl.editor, { - isTextArea: newControl.isTextArea && oldControl.isTextArea, - placeholder: oldControl.editor?.placeholder, - holdPlace: oldControl.editor?.holdPlace, - readonly: oldControl.editor?.readonly, - required: oldControl.editor?.required, + binding: oldControl.binding }); - + // 解决undefined下默认值问题 + if (Object.prototype.hasOwnProperty.call(oldControl, 'visible')) { + Object.assign(newControl, { visible: oldControl.visible }); + } + if (oldControl.editor) { + ['readonly', 'required', 'placeholder'].map((item) => { + if (Object.prototype.hasOwnProperty.call(oldControl.editor, item)) { + newControl.editor[item] = oldControl.editor[item]; + } + }); + } // 5、替换控件 parentContainer.contents.splice(index, 1); parentContainer.contents.splice(index, 0, newControl); componentInstance.schema = Object.assign(oldControl, newControl); + // 重组VM + // this.designViewModelUtils.assembleDesignViewModel(); + Object.assign(propertyData, newControl); // 6、暂时移除旧控件的选中样式(后续考虑更好的方式) Array.from(document.getElementsByClassName('dgComponentSelected') as HTMLCollectionOf).forEach( @@ -190,11 +303,11 @@ export class InputBaseProperty extends BaseControlProperty { (element: HTMLElement) => element.classList.remove('dgComponentFocused') ); // 7、触发刷新 - canvasChanged.value++; + // canvasChanged.value++; } - public getComponentConfig(propertyData, info = {}, properties = {}, setPropertyRelates?: any) { + public getComponentConfig(propertyData, info = {}, properties = {}, setPropertyRelates?: (changeObject, propertyData, parameters) => any) { const editorBasic = Object.assign({ description: "编辑器", title: "编辑器", @@ -202,42 +315,81 @@ export class InputBaseProperty extends BaseControlProperty { $converter: "/converter/property-editor.converter" }, info); - const editorProperties = Object.assign({ + const readonlyEditor = this.getPropertyEditorParams(propertyData, [], 'readonly'); + const requiredEditor = this.getPropertyEditorParams(propertyData, [], 'required'); + const editorProperties = { readonly: { description: "", title: "只读", - type: "boolean", - editor: { - enableClear: true, - editable: true - } - }, - disabled: { - description: "", - title: "禁用", - type: "boolean", - visible: false + editor: readonlyEditor }, required: { description: "", title: "必填", type: "boolean", - visible: false + editor: requiredEditor }, placeholder: { - description: "空值时,输入控件内的占位文本", + description: "当控件没有值时在输入框中显示的文本", title: "提示文本", - type: "string", - visible: false - + type: "string" } - }, properties); + }; + for (const key in properties) { + // 合并属性,保留原属性值 + editorProperties[key] = Object.assign(editorProperties[key] || {}, properties[key]); + } + const self = this; - return { ...editorBasic, properties: { ...editorProperties }, setPropertyRelates }; + return { + ...editorBasic, properties: { ...editorProperties }, setPropertyRelates(changeObject, parameters: any) { + if (!changeObject) { + return; + } + switch (changeObject.propertyID) { + case 'readonly': + case 'required': + self.afterMutilEditorChanged(propertyData, changeObject); + break; + } + if (setPropertyRelates) { + setPropertyRelates(changeObject, propertyData, parameters); + } + } + }; } + /** + * 修改某一输入控件的样式后更新Form的统一布局配置 + * @param controlClass 控件样式 + * @param controlId 控件Id + * @param componentId 控件所在组件id + */ + private updateUnifiedLayoutAfterControlChanged(controlClass: string, controlId: string, componentId: string) { + const controlClassArray = controlClass.split(' '); + + let colClass = controlClassArray.find(item => /^col-([1-9]|10|11|12)$/.test(item)); + let colMDClass = controlClassArray.find(item => /^col-md-([1-9]|10|11|12)$/.test(item)); + let colXLClass = controlClassArray.find(item => /^col-xl-([1-9]|10|11|12)$/.test(item)); + let colELClass = controlClassArray.find(item => /^col-el-([1-9]|10|11|12)$/.test(item)); + + colClass = colClass || 'col-12'; + colMDClass = colMDClass || 'col-md-' + colClass.replace('col-', ''); + colXLClass = colXLClass || 'col-xl-' + colMDClass.replace('col-md-', ''); + colELClass = colELClass || 'col-el-' + colXLClass.replace('col-xl-', ''); + + const latestControlLayoutConfig = { + id: controlId, + columnInSM: parseInt(colClass.replace('col-', ''), 10), + columnInMD: parseInt(colMDClass.replace('col-md-', ''), 10), + columnInLG: parseInt(colXLClass.replace('col-xl-', ''), 10), + columnInEL: parseInt(colELClass.replace('col-el-', ''), 10), + }; + + } + /** * 枚举项编辑器 * @param propertyData @@ -253,7 +405,7 @@ export class InputBaseProperty extends BaseControlProperty { columns: [ { field: valueField, title: '值', dataType: 'string' }, { field: textField, title: '名称', dataType: 'string' }, - { field: 'disabled', title: '禁用', visible: false, dataType: 'boolean', editor: { type: 'switch' } }, + { field: 'disabled', title: '禁用', dataType: 'boolean', editor: { type: 'switch' } }, ], type: "item-collection-editor", valueField: valueField, @@ -265,12 +417,12 @@ export class InputBaseProperty extends BaseControlProperty { }; } /** - * 判断枚举数据是否只读 - * 1、没有绑定信息或者绑定变量,可以新增、删除、修改 - * 2、绑定类型为字段,且字段为枚举字段,则不可新增、删除、修改枚举值。只能从be修改然后同步到表单上。 - * @param propertyData 下拉框控件属性值 - */ - private checkEnumDataReadonly(propertyData: any): boolean { + * 判断枚举数据是否只读 + * 1、没有绑定信息或者绑定变量,可以新增、删除、修改 + * 2、绑定类型为字段,且字段为枚举字段,则不可新增、删除、修改枚举值。只能从be修改然后同步到表单上。 + * @param propertyData 下拉框控件属性值 + */ + protected checkEnumDataReadonly(propertyData: any): boolean { // 没有绑定信息或者绑定变量 if (!propertyData.binding || propertyData.binding.type !== 'Form') { return false; @@ -282,4 +434,118 @@ export class InputBaseProperty extends BaseControlProperty { } return false; } + /** + * 将字段值变化前事件、变化后事件追加到交互面板 + * 注意:因为绑定字段值变化后事件与下拉框的值变化事件(valueChanged)重名,所以这里将事件label都重命名下 + */ + appendFieldValueChangeEvents(propertyData: any, eventList: any[]) { + // 若绑定了字段,则需要显示字段变更前后事件 + if (propertyData.binding && propertyData.binding.type === FormBindingType.Form && propertyData.binding.field) { + const valueChangingExist = eventList.find(eventListItem => eventListItem.label === 'fieldValueChanging'); + if (!valueChangingExist) { + eventList.push( + { + label: 'fieldValueChanging', + name: '绑定字段值变化前事件' + } + ); + } + const valueChangedExist = eventList.find(eventListItem => eventListItem.label === 'fieldValueChanged'); + if (!valueChangedExist) { + eventList.push( + { + label: 'fieldValueChanged', + name: '绑定字段值变化后事件' + } + ); + } + if (this.designViewModelField) { + // 因为字段变更属性是存到VM中的,但是这里需要在控件上编辑,所以复制一份数据 + propertyData.fieldValueChanging = this.designViewModelField.valueChanging; + propertyData.fieldValueChanged = this.designViewModelField.valueChanged; + } + } else { + // 未绑定字段,则移除值变化事件 + eventList = eventList.filter(eventListItem => eventListItem.label !== 'fieldValueChanging' && eventListItem.label !== 'fieldValueChanged'); + } + } + private getControlMethodType(propertyData: any) { + if (!propertyData.binding) { + return propertyData.type; + } + switch (propertyData.binding.type) { + case FormBindingType.Form: { + return propertyData.binding.path || propertyData.type; + } + case FormBindingType.Variable: { + return propertyData.binding.fullPath || propertyData.type; + } + } + + return propertyData.type; + } + /** + * 组装输入类控件的交互面板:包含标签超链、绑定字段值变化前后事件等。 + * @param propertyData 属性值 + * @param viewModelId 视图模型id + * @param showPosition 面板展示位置 + * @param customEvent 输入控件特有的事件配置 + */ + public getEventPropertyConfig(propertyData: any, showPosition = 'card', customEventList?: { label: string, name: string }[], setPropertyRelates?: (changeObject, data, parameters) => void) { + const self = this; + // 静态事件 + let eventList = [] as any; + if (customEventList) { + eventList = eventList.concat(customEventList); + } + // 追加值变化 + this.appendFieldValueChangeEvents(propertyData, eventList); + + const initialData = self.eventsEditorUtils['formProperties'](propertyData, self.viewModelId, eventList); + const properties = {}; + properties[self.viewModelId] = { + type: 'events-editor', + editor: { + initialData + } + }; + const eventsEditorConfig = { + title: '事件', + hideTitle: true, + properties, + tabId: 'commands', + tabName: '交互', + setPropertyRelates(changeObject: FormPropertyChangeObject, data: any) { + const parameters = changeObject.propertyValue; + delete propertyData[self.viewModelId]; + if (parameters) { + parameters.setPropertyRelates = this.setPropertyRelates; // 添加自定义方法后,调用此回调方法,用于处理联动属性 + parameters.controlInfo = { type: self.getControlMethodType(propertyData), name: propertyData.title }; // 暂存控件信息,用于自动创建新方法的方法编号和名称 + + self.eventsEditorUtils.saveRelatedParameters(propertyData, self.viewModelId, parameters['events'], parameters); + } + + if (setPropertyRelates) { + setPropertyRelates(changeObject, data, parameters); + } + + // 同步视图模型值变化事件 + const designVM = self.designViewModelUtils.getDgViewModel(self.viewModelId); + if (designVM && self.designViewModelField) { + designVM.changeField(self.designViewModelField.id, { valueChanging: propertyData.fieldValueChanging, valueChanged: propertyData.fieldValueChanged }); + } + } + }; + + return eventsEditorConfig; + } + + getExpressionConfig(propertyData: any, type: 'Field' | 'Button' | 'Container', + expressionTypes: string[] = ['compute', 'dependency', 'validate'], + associationCallBack?: (rule: Record) => void + ) { + return new ExpressionProperty(this.formSchemaUtils).getExpressionConfig( + propertyData, type, expressionTypes, associationCallBack); + } + } diff --git a/packages/mobile-ui-vue/components/property-panel/src/composition/entity/schema-dom-mapping.ts b/packages/mobile-ui-vue/components/common/src/properties/schema-dom-mapping.ts similarity index 97% rename from packages/mobile-ui-vue/components/property-panel/src/composition/entity/schema-dom-mapping.ts rename to packages/mobile-ui-vue/components/common/src/properties/schema-dom-mapping.ts index 066d549361dc5d754b30fdefcf061a1389703eb8..71f7291318c39c4c8b25616a7b694db330805072 100644 --- a/packages/mobile-ui-vue/components/property-panel/src/composition/entity/schema-dom-mapping.ts +++ b/packages/mobile-ui-vue/components/common/src/properties/schema-dom-mapping.ts @@ -1,5 +1,5 @@ -import { DgControl } from "../../../../designer-canvas/src/composition/dg-control"; +import { DgControl } from "./dg-control"; export class SchemaDOMMapping { diff --git a/packages/mobile-ui-vue/components/common/src/properties/use-property-editor.ts b/packages/mobile-ui-vue/components/common/src/properties/use-property-editor.ts new file mode 100644 index 0000000000000000000000000000000000000000..edc1e1d510145b7459b33e306a9346228b7681e8 --- /dev/null +++ b/packages/mobile-ui-vue/components/common/src/properties/use-property-editor.ts @@ -0,0 +1,73 @@ +import { DesignerHostService } from "../types"; + +/** + * PropertyEditor对外提供的接口 + * @param designerHostService + * @returns + */ +export function usePropertyEditor(designerHostService: DesignerHostService): any { + const { formSchemaUtils, formStateMachineUtils } = designerHostService; + + /** + * 把变量视图模型的变量转化为PropertyEditor的变量格式 + * @param variable + * @returns + */ + function convertToEditorVariable(variable: any, pathPrefix: string = ''): any { + return { + path: pathPrefix + variable.code, + field: variable.id, + fullPath: variable.code + }; + } + + /** + * 获取视图模型上的变量 + * @param viewModelId + * @returns + */ + function getVariablesByViewModelId(viewModelId: string, pathPrefix: string = ''): any[] { + const viewModel = formSchemaUtils.getViewModelById(viewModelId); + return viewModel.states.map(state => convertToEditorVariable(state, pathPrefix)); + } + + /** + * 获取PropertyEditor需要的变量数据 + */ + function getVariables(viewModelId: string): any[] { + const rootViewModelId = formSchemaUtils.getRootViewModelId(); + // 1、当前组件的组件变量 + const currentViewModelVariables = getVariablesByViewModelId(viewModelId); + if (viewModelId === rootViewModelId) { + return currentViewModelVariables; + } + + // 2、根组件的组件变量 + const rootViewModelVariables = getVariablesByViewModelId(rootViewModelId, 'root-component.'); + return [...currentViewModelVariables, ...rootViewModelVariables]; + } + + /** + * 获取控件名称 + * @param propertyData + * @returns + */ + function getControlName(propertyData: any): string { + const controlName = propertyData.binding && propertyData.binding.path || propertyData.id || ''; + return controlName; + } + + /** + * 获取PropertyEditor需要的状态机数据 + */ + function getStateMachines(viewModelId:string): any[] { + const renderStates = formStateMachineUtils && formStateMachineUtils.getRenderStates(); + if(renderStates){ + const viewModel = formSchemaUtils.getViewModelById(viewModelId); + return renderStates.filter(renderState => renderState.stateMachineId === viewModel.stateMachine); + } + return renderStates || []; + } + + return { getVariables, getControlName, getStateMachines }; +} diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/types.ts b/packages/mobile-ui-vue/components/common/src/types/designer-component.ts similarity index 98% rename from packages/mobile-ui-vue/components/designer-canvas/src/types.ts rename to packages/mobile-ui-vue/components/common/src/types/designer-component.ts index c63ceb11c799e56767b8962c6e51f34ea487c690..6ca1bb9c26e2843c9972a3120b3473f569a51d27 100644 --- a/packages/mobile-ui-vue/components/designer-canvas/src/types.ts +++ b/packages/mobile-ui-vue/components/common/src/types/designer-component.ts @@ -1,6 +1,6 @@ /* eslint-disable no-use-before-define */ import { Ref, SetupContext } from "vue"; -import { DesignerHostService, DesignerHTMLElement, DraggingResolveContext } from "./composition/types"; +import { DesignerHostService, DesignerHTMLElement, DraggingResolveContext } from "./designer-rule"; export interface ComponentSchema { diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/types.ts b/packages/mobile-ui-vue/components/common/src/types/designer-rule.ts similarity index 93% rename from packages/mobile-ui-vue/components/designer-canvas/src/composition/types.ts rename to packages/mobile-ui-vue/components/common/src/types/designer-rule.ts index a3dc5bbfad20596649c87001a8891b6d575a47e7..ed261cb18f6ec651c94bc51f992f1c3ff9ec08c3 100644 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/types.ts +++ b/packages/mobile-ui-vue/components/common/src/types/designer-rule.ts @@ -1,6 +1,6 @@ -import { DesignFormVariable, DesignViewModelField, FormSchemaEntity, FormSchemaEntityField } from "../../../common/entity/entity-schema"; import { Ref } from "vue"; -import { ComponentSchema, DesignerComponentButton, DesignerComponentInstance } from "../types"; +import { ComponentSchema, DesignerComponentButton, DesignerComponentInstance } from "./designer-component"; +import { DesignFormVariable, DesignViewModelField, FormSchemaEntity, FormSchemaEntityField } from "./entity-schema"; export interface DesignerHTMLElement extends HTMLElement { /** 记录各子元素对应的控件schema json的集合,用于container类dom节点 */ @@ -12,14 +12,6 @@ export interface DesignerHTMLElement extends HTMLElement { schema: ComponentSchema; } - -export interface UseDragula { - attachComponents: (element: HTMLElement, component: ComponentSchema) => void; - - initializeDragula: (containerElement: DesignerHTMLElement) => void; - - getDragulaInstance: () => any; -} export interface DesignerHostService { eventsEditorUtils: any; formSchemaUtils: any; diff --git a/packages/mobile-ui-vue/components/common/src/entity/entity-schema.ts b/packages/mobile-ui-vue/components/common/src/types/entity-schema.ts similarity index 100% rename from packages/mobile-ui-vue/components/common/src/entity/entity-schema.ts rename to packages/mobile-ui-vue/components/common/src/types/entity-schema.ts diff --git a/packages/mobile-ui-vue/components/common/src/types/index.ts b/packages/mobile-ui-vue/components/common/src/types/index.ts new file mode 100644 index 0000000000000000000000000000000000000000..195bea74cd34c250e739f2c5ef58be6524bfa349 --- /dev/null +++ b/packages/mobile-ui-vue/components/common/src/types/index.ts @@ -0,0 +1,5 @@ +export * from './types'; +export * from './designer-component'; +export * from './designer-rule'; +export * from './entity-schema'; +export * from './property-config'; diff --git a/packages/mobile-ui-vue/components/property-panel/src/composition/entity/property-entity.ts b/packages/mobile-ui-vue/components/common/src/types/property-config.ts similarity index 79% rename from packages/mobile-ui-vue/components/property-panel/src/composition/entity/property-entity.ts rename to packages/mobile-ui-vue/components/common/src/types/property-config.ts index 5650de17982343f9aae78c1feefd1b04b20894cf..0b525f2bea35eb24f03127225016801ae9b2f1d3 100644 --- a/packages/mobile-ui-vue/components/property-panel/src/composition/entity/property-entity.ts +++ b/packages/mobile-ui-vue/components/common/src/types/property-config.ts @@ -1,4 +1,3 @@ -import { EditorConfig } from "@farris/mobile-ui-vue/dynamic-form"; import { Ref } from "vue"; export interface KeyMap { @@ -6,6 +5,29 @@ export interface KeyMap { value: any; } +export type EditorType = 'button-edit' | 'check-box' | 'check-group' | 'combo-list' | 'combo-lookup' | 'combo-tree' | + 'date-picker' | 'date-range' | 'datetime-picker' | 'datetime-range' | 'events-editor' | 'month-picker' | 'month-range' | + 'year-picker' | 'year-range' | 'input-group' | 'lookup' | 'number-range' | 'number-spinner' | 'radio-group' | 'text' | + 'response-layout-editor-setting' | 'switch' | 'grid-field-editor' | 'field-selector' | 'schema-selector' | 'mapping-editor' | + 'textarea' | 'response-form-layout-setting'|'binding-selector' | 'query-solution-config' | 'solution-preset' | 'item-collection-editor'; + +export interface EditorConfig { + /** 编辑器类型 */ + type: EditorType; + /** 自定义样式 */ + customClass?: string; + /** 禁用 */ + disabled?: boolean; + /** 只读 */ + readonly?: boolean; + /** 必填 */ + required?: boolean; + /** 提示文本 */ + placeholder?: string; + /** 其他属性 */ + [key: string]: any; +} + /** 属性实体 */ export interface PropertyEntity { /** @@ -223,8 +245,8 @@ export interface FormPropertyChangeObject extends PropertyChangeObject { /** 是否需要刷新控件树 */ needRefreshControlTree?: boolean; - /** 是否需要更新控件树节点名称 */ - needUpdateControlTreeNodeName?: boolean; + /** 是否需要刷新控件树 */ + needRefreshEntityTree?: boolean; /** 关联变更的属性集合,用于更新表单DOM属性 */ relateChangeProps?: Array<{ @@ -232,9 +254,13 @@ export interface FormPropertyChangeObject extends PropertyChangeObject { propertyValue: any }>; - /** 属性变更后是否需要向schema字段同步 */ - needSyncToSchemaField?: boolean; - /** 强关联的属性id:在当前属性变更后,页面自动定位到强关联的属性 */ autoLocatedPropertyId?: string; } + + +export enum FormBindingType { + Form = "Form", + Variable = "Variable" +} + diff --git a/packages/mobile-ui-vue/components/common/types.ts b/packages/mobile-ui-vue/components/common/src/types/types.ts similarity index 97% rename from packages/mobile-ui-vue/components/common/types.ts rename to packages/mobile-ui-vue/components/common/src/types/types.ts index 351245ac179f504189fe4585915dc7d14424b87b..b0c10ec0675c8abedb42be0f6383977821cbe5e4 100644 --- a/packages/mobile-ui-vue/components/common/types.ts +++ b/packages/mobile-ui-vue/components/common/src/types/types.ts @@ -1,5 +1,5 @@ import { ComputedRef, Ref } from "vue"; -import { EffectFunction, SchemaResolverFunction } from "../dynamic-resolver"; +import { EffectFunction, SchemaResolverFunction } from "@farris/mobile-ui-vue/dynamic-resolver/src/types"; export interface TextBoxProps { @@ -136,4 +136,4 @@ export interface RegisterContext { schemaResolverMap: Record; propertyConfigSchemaMap: Record; propertyEffectMap: Record; -} \ No newline at end of file +} diff --git a/packages/mobile-ui-vue/components/common/src/utils/src/common.ts b/packages/mobile-ui-vue/components/common/src/utils/src/common.ts index 1010e19020f584c0011c18b95daa19ff85c425ef..d258ec7627ac43f26006460f5b55c34dba3ce2d9 100644 --- a/packages/mobile-ui-vue/components/common/src/utils/src/common.ts +++ b/packages/mobile-ui-vue/components/common/src/utils/src/common.ts @@ -86,3 +86,14 @@ export const setValue = (obj: Record, field: string, val: any) => { obj[field] = val; } }; +export function extractProperties( + obj: T, + props: K[] +): Pick { + return props.reduce((result, prop) => { + if (prop in obj) { + result[prop] = obj[prop]; + } + return result; + }, {} as Pick); +} diff --git a/packages/mobile-ui-vue/components/common/src/utils/src/with-register-designer.ts b/packages/mobile-ui-vue/components/common/src/utils/src/with-register-designer.ts index eb801e50c1bf20afb37fe5ee02f63bb000002a0c..b0b5557958ac4bb5589ef9e47acf776dca5a8a70 100644 --- a/packages/mobile-ui-vue/components/common/src/utils/src/with-register-designer.ts +++ b/packages/mobile-ui-vue/components/common/src/utils/src/with-register-designer.ts @@ -1,4 +1,4 @@ -import { RegisterContext } from '@farris/mobile-ui-vue/common/types'; +import { RegisterContext } from '@farris/mobile-ui-vue/common'; import type { App, Component } from 'vue'; export type WithRegisterDesigner = T & { diff --git a/packages/mobile-ui-vue/components/common/src/utils/src/with-register.ts b/packages/mobile-ui-vue/components/common/src/utils/src/with-register.ts index 94a387f7ed89f2fa61c2463fb9796624d7583f06..15608d737bd99b87dd2a53d032751f640b7da7b5 100644 --- a/packages/mobile-ui-vue/components/common/src/utils/src/with-register.ts +++ b/packages/mobile-ui-vue/components/common/src/utils/src/with-register.ts @@ -1,4 +1,4 @@ -import { RegisterContext } from '@farris/mobile-ui-vue/common/types'; +import { RegisterContext } from '@farris/mobile-ui-vue/common'; import type { App, Component } from 'vue'; export type WithRegister = T & { diff --git a/packages/mobile-ui-vue/components/component/index.ts b/packages/mobile-ui-vue/components/component/index.ts index ba722ade21f9ec81eaec0c9a148c5bd1ad75c43c..bf0f9d3a345668840eef6bac567e82efd5f30834 100644 --- a/packages/mobile-ui-vue/components/component/index.ts +++ b/packages/mobile-ui-vue/components/component/index.ts @@ -42,4 +42,4 @@ Component.registerDesigner = ( export * from './src/component.props'; export { Component }; -export default Component as typeof Component & Plugin; +export default Component; diff --git a/packages/mobile-ui-vue/components/component/src/designer/component.design.component.tsx b/packages/mobile-ui-vue/components/component/src/designer/component.design.component.tsx index b49f4f2b19daec817e99e41dae26802131560539..d2e9b308c7b52ac34a5a2d164867d1431d69fad4 100644 --- a/packages/mobile-ui-vue/components/component/src/designer/component.design.component.tsx +++ b/packages/mobile-ui-vue/components/component/src/designer/component.design.component.tsx @@ -1,7 +1,7 @@ import { SetupContext, defineComponent, inject, ref, onMounted, computed } from 'vue'; import { ComponentPropsType, componentProps } from '../component.props'; import { useDesignerRules } from './use-designer-rules'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas'; +import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/common'; export default defineComponent({ name: 'FComponetDesign', diff --git a/packages/mobile-ui-vue/components/component/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/component/src/designer/use-designer-rules.ts index 96d8098d982b43dbfd68240f9c401356a1a81757..02050723a6fa2e5095a7112ba846f797c8f6c720 100644 --- a/packages/mobile-ui-vue/components/component/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/component/src/designer/use-designer-rules.ts @@ -1,4 +1,4 @@ -import { DesignerHostService, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; +import { DesignerHostService, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; import { ComponentProperty } from "../property-config/component.property-config"; export function useDesignerRules(designItemContext: DesignerItemContext, designerHostService?: DesignerHostService): UseDesignerRules { diff --git a/packages/mobile-ui-vue/components/component/src/property-config/component.property-config.ts b/packages/mobile-ui-vue/components/component/src/property-config/component.property-config.ts index 3fa6c4ccc37628a68f65f091fd0287a22cb4a0e2..43b773f68a1d98af19de80a94d784e3edd896cd2 100644 --- a/packages/mobile-ui-vue/components/component/src/property-config/component.property-config.ts +++ b/packages/mobile-ui-vue/components/component/src/property-config/component.property-config.ts @@ -1,4 +1,4 @@ -import { BaseControlProperty } from "@farris/mobile-ui-vue/property-panel"; +import { BaseControlProperty } from "@farris/mobile-ui-vue/common"; export class ComponentProperty extends BaseControlProperty { diff --git a/packages/mobile-ui-vue/components/content-container/index.ts b/packages/mobile-ui-vue/components/content-container/index.ts index d6c256518cfed069637f42a0834f2808eec5a729..3b5995969eaccbf3759e7ec27fbdf9a208f132d1 100644 --- a/packages/mobile-ui-vue/components/content-container/index.ts +++ b/packages/mobile-ui-vue/components/content-container/index.ts @@ -1,32 +1,14 @@ -import { App, Plugin } from 'vue'; -import FContentContainer from './src/content-container.component'; +import { withInstall, withRegister, withRegisterDesigner } from '@farris/mobile-ui-vue/common'; +import ContentContainerInstallless from './src/content-container.component'; import { propsResolverGenerator } from './src/content-container.props'; import ContentContainerDesign from './src/designer/content-container.design.component'; -import { RegisterContext } from '../common'; -const CONTENT_CONTAINER_REGISTERED_NAME = 'content-container'; - -FContentContainer.install = (app: App) => { - app.component(FContentContainer.name as string, FContentContainer); -}; +const ContentContainer = withInstall(ContentContainerInstallless); -FContentContainer.register = ( - componentMap: Record, propsResolverMap: Record, - configresolverMap: Record, resolverMap: Record,registerContext: RegisterContext -) => { - componentMap[CONTENT_CONTAINER_REGISTERED_NAME] = FContentContainer; - propsResolverMap[CONTENT_CONTAINER_REGISTERED_NAME] = propsResolverGenerator(registerContext); -}; - -FContentContainer.registerDesigner = ( - componentMap: Record, propsResolverMap: Record, - configresolverMap: Record,registerContext: RegisterContext -) => { - componentMap[CONTENT_CONTAINER_REGISTERED_NAME] = ContentContainerDesign; - propsResolverMap[CONTENT_CONTAINER_REGISTERED_NAME] = propsResolverGenerator(registerContext); -}; +const CONTENT_CONTAINER_REGISTERED_NAME = 'content-container'; +withRegister(ContentContainer, { name: CONTENT_CONTAINER_REGISTERED_NAME, propsResolverGenerator }); +withRegisterDesigner(ContentContainer, { name: CONTENT_CONTAINER_REGISTERED_NAME, propsResolverGenerator, designerComponent: ContentContainerDesign }); -export * from './src/content-container.props'; -export { FContentContainer }; -export default FContentContainer as typeof FContentContainer & Plugin; +export { ContentContainer }; +export default ContentContainer; diff --git a/packages/mobile-ui-vue/components/content-container/src/designer/content-container.design.component.tsx b/packages/mobile-ui-vue/components/content-container/src/designer/content-container.design.component.tsx index 5164ec64e00bbdd28fc4c6b3ef9015acc4fb7a42..5e2ccbc41159a8a8c22d57d5fd3007ebb9e8f396 100644 --- a/packages/mobile-ui-vue/components/content-container/src/designer/content-container.design.component.tsx +++ b/packages/mobile-ui-vue/components/content-container/src/designer/content-container.design.component.tsx @@ -1,14 +1,14 @@ import { SetupContext, computed, defineComponent, inject, onMounted, ref } from 'vue'; -import { ContentContainerPropsType, contentContainerProps } from '../content-container.props'; +import { ContentContainerProps, contentContainerProps } from '../content-container.props'; import { useDesignerRulesForContentContainer } from './use-designer-rules'; import { getCustomClass } from '@farris/mobile-ui-vue/common'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/common';; export default defineComponent({ name: 'FContentContainerDesign', props: contentContainerProps, emits: [], - setup(props: ContentContainerPropsType, context) { + setup(props: ContentContainerProps, context) { const elementRef = ref(); const designerHostService = inject('designer-host-service'); const designItemContext = inject('design-item-context') as DesignerItemContext; diff --git a/packages/mobile-ui-vue/components/content-container/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/content-container/src/designer/use-designer-rules.ts index 9520f9793cdbd088f152543b8bbe62cff321f575..b78cbfcc46b09de641a5dbf1567ae1d251f77c85 100644 --- a/packages/mobile-ui-vue/components/content-container/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/content-container/src/designer/use-designer-rules.ts @@ -1,6 +1,6 @@ -import { ComponentSchema, DesignerItemContext } from "@farris/mobile-ui-vue/designer-canvas"; +import { ComponentSchema, DesignerItemContext } from "@farris/mobile-ui-vue/common"; import { ContentContainerProperty } from "../property-config/content-container.property-config"; -import { DesignerHostService, DraggingResolveContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas/src/composition/types"; +import { DesignerHostService, DraggingResolveContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; export function useDesignerRulesForContentContainer(designItemContext: DesignerItemContext, designerHostService?: DesignerHostService): UseDesignerRules { const schema = designItemContext.schema as ComponentSchema; diff --git a/packages/mobile-ui-vue/components/content-container/src/property-config/content-container.property-config.ts b/packages/mobile-ui-vue/components/content-container/src/property-config/content-container.property-config.ts index 6512f2c46593ec8903be317bb33cbd58d5d855fa..e7d94c41f1e0833446632df144eae40d4aba41ff 100644 --- a/packages/mobile-ui-vue/components/content-container/src/property-config/content-container.property-config.ts +++ b/packages/mobile-ui-vue/components/content-container/src/property-config/content-container.property-config.ts @@ -1,4 +1,4 @@ -import { BaseControlProperty } from "@farris/mobile-ui-vue/property-panel"; +import { BaseControlProperty } from "@farris/mobile-ui-vue/common"; export class ContentContainerProperty extends BaseControlProperty { constructor(componentId: string, designerHostService: any) { diff --git a/packages/mobile-ui-vue/components/date-picker/src/designer/date-picker.design.component.tsx b/packages/mobile-ui-vue/components/date-picker/src/designer/date-picker.design.component.tsx index d8c19fe65d689d0f13e0c1536a6c354ae20ebd87..6bf49f080e9dc0cdd996dbbdca9b5fbc51b8c630 100644 --- a/packages/mobile-ui-vue/components/date-picker/src/designer/date-picker.design.component.tsx +++ b/packages/mobile-ui-vue/components/date-picker/src/designer/date-picker.design.component.tsx @@ -1,54 +1,42 @@ - -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -import { computed, defineComponent, inject, onMounted, readonly, ref, SetupContext } from 'vue'; - -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import { computed, defineComponent, inject, onMounted, ref } from 'vue'; +import { + DesignerHostService, + DesignerItemContext, + extractProperties, + useDesignerComponent +} from '@farris/mobile-ui-vue/common'; +import InputGroup from '@farris/mobile-ui-vue/input-group'; import { useDesignerRules } from './use-designer-rules'; -import { datePickerProps, DatePickerProps } from '../date-picker.props'; -import DatePickerInput from '../..'; +import { datePickerProps } from '../date-picker.props'; export default defineComponent({ - name: 'FmDatePickerInputDesign', - props: datePickerProps, - emits: [], - setup(props: DatePickerProps, context: SetupContext) { - const elementRef = ref(); - const designItemContext = inject('design-item-context') as DesignerItemContext; - const designerHostService = inject('designer-host-service'); - const designerRulesComposition = useDesignerRules(designItemContext, designerHostService); - const componentInstance = useDesignerComponent(elementRef, designItemContext,designerRulesComposition); + name: 'FmDatePickerInputDesign', + inheritAttrs: false, + props: extractProperties(datePickerProps, ['placeholder']), + setup(props, context) { + const elementRef = ref(); + const designItemContext = inject( + 'design-item-context' + ) as DesignerItemContext; + const designerHostService = inject('designer-host-service'); + const designerRulesComposition = useDesignerRules(designItemContext, designerHostService); + const componentInstance = useDesignerComponent( + elementRef, + designItemContext, + designerRulesComposition + ); + + onMounted(() => { + elementRef.value.componentInstance = componentInstance; + }); - onMounted(() => { - elementRef.value.componentInstance = componentInstance; - }); + context.expose(componentInstance.value); - context.expose(componentInstance.value); + const inputProps = computed(() => ({ + ...props, + editable: false + })); - const inputProps = computed(() => ({ - ...props, - editable: false, - readonly: true, - modelValue:null - })); - - return () => { - return ( - - ); - }; - } + return () => ; + } }); diff --git a/packages/mobile-ui-vue/components/date-picker/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/date-picker/src/designer/use-designer-rules.ts index 1c41eedaf45b5ce1c4de944d885f9fe121ba4192..8abda334f14b5e9f8da55fc0cf438c8d1b84e7bb 100644 --- a/packages/mobile-ui-vue/components/date-picker/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/date-picker/src/designer/use-designer-rules.ts @@ -1,4 +1,4 @@ -import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; +import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; import { DatePickerProperty } from "../property-config/date-picker.property-config"; export function useDesignerRules(designItemContext: DesignerItemContext, designerHostService): UseDesignerRules { diff --git a/packages/mobile-ui-vue/components/date-picker/src/property-config/date-picker.property-config.ts b/packages/mobile-ui-vue/components/date-picker/src/property-config/date-picker.property-config.ts index 205e01d02ba792a76b1926c81da530b9bf7b0779..1ea66076a515b4e20972f5532dbe058505703663 100644 --- a/packages/mobile-ui-vue/components/date-picker/src/property-config/date-picker.property-config.ts +++ b/packages/mobile-ui-vue/components/date-picker/src/property-config/date-picker.property-config.ts @@ -1,4 +1,4 @@ -import { InputBaseProperty } from '@farris/mobile-ui-vue/common/src/entity/input-base-property'; +import { InputBaseProperty } from '@farris/mobile-ui-vue/common'; import { DATE_FORMATS } from './date-format'; export class DatePickerProperty extends InputBaseProperty { diff --git a/packages/mobile-ui-vue/components/date-picker/src/schema/schema-mapper.ts b/packages/mobile-ui-vue/components/date-picker/src/schema/schema-mapper.ts index 70f3c0e7744a5425bfce8cf5f4f3e9b295d9073e..728769ef54e46801be6469e1fab2d96ab2d56948 100644 --- a/packages/mobile-ui-vue/components/date-picker/src/schema/schema-mapper.ts +++ b/packages/mobile-ui-vue/components/date-picker/src/schema/schema-mapper.ts @@ -3,5 +3,5 @@ import { MapperFunction, resolveAppearance } from '@farris/mobile-ui-vue/dynamic export const schemaMapper = new Map([ ['appearance', resolveAppearance], ['binding', 'modelValue'], - ['displayFormat','format'] + ['valueFormat','format'] ]); diff --git a/packages/mobile-ui-vue/components/date-time-picker/src/date-time-picker.props.ts b/packages/mobile-ui-vue/components/date-time-picker/src/date-time-picker.props.ts index c2a66c2a27857ad4a581e84a3114865e49d7b193..283d4a1f02b1c2d874791ef61779e68eb2ab7400 100644 --- a/packages/mobile-ui-vue/components/date-time-picker/src/date-time-picker.props.ts +++ b/packages/mobile-ui-vue/components/date-time-picker/src/date-time-picker.props.ts @@ -4,7 +4,7 @@ import { dateTimePickerPanelProps } from './date-time-picker-panel.props'; import { getPropsResolverGenerator } from '../../dynamic-resolver'; import { schemaResolver } from './schema/schema-resolver'; import { schemaMapper } from './schema/schema-mapper'; -import dateTimePickerSchema from './schema/datetime-picker.schema.json' +import dateTimePickerSchema from './schema/datetime-picker.schema.json'; export const DATA_TIME_PICKER_NAME = 'FmDateTimePicker'; diff --git a/packages/mobile-ui-vue/components/date-time-picker/src/designer/date-picker.design.component.tsx b/packages/mobile-ui-vue/components/date-time-picker/src/designer/date-picker.design.component.tsx index 76e3afe317645e7082604a0d6eb1dbd059c7c601..1915144983b54691726692c4072d7bfd4feaae2e 100644 --- a/packages/mobile-ui-vue/components/date-time-picker/src/designer/date-picker.design.component.tsx +++ b/packages/mobile-ui-vue/components/date-time-picker/src/designer/date-picker.design.component.tsx @@ -1,37 +1,42 @@ import { computed, defineComponent, inject, onMounted, ref } from 'vue'; - -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import { + DesignerHostService, + DesignerItemContext, + extractProperties, + useDesignerComponent +} from '@farris/mobile-ui-vue/common'; +import InputGroup from '@farris/mobile-ui-vue/input-group'; import { useDesignerRules } from './use-designer-rules'; -import { ButtonEdit, buttonEditProps} from '@farris/mobile-ui-vue/button-edit'; +import { dateTimePickerProps } from '../date-time-picker.props'; export default defineComponent({ - name: 'FmDatePickerDesign', - props: buttonEditProps, - emits: [], - setup(props, context) { - const elementRef = ref(); - const designItemContext = inject('design-item-context') as DesignerItemContext; - const designerHostService = inject('designer-host-service'); - const designerRulesComposition = useDesignerRules(designItemContext, designerHostService); - const componentInstance = useDesignerComponent(elementRef, designItemContext,designerRulesComposition); + name: 'FmDatePickerDesign', + inheritAttrs: false, + props: extractProperties(dateTimePickerProps, ['placeholder']), + setup(props, context) { + const elementRef = ref(); + const designItemContext = inject( + 'design-item-context' + ) as DesignerItemContext; + const designerHostService = inject('designer-host-service'); + const designerRulesComposition = useDesignerRules(designItemContext, designerHostService); + const componentInstance = useDesignerComponent( + elementRef, + designItemContext, + designerRulesComposition + ); + + onMounted(() => { + elementRef.value.componentInstance = componentInstance; + }); - onMounted(() => { - elementRef.value.componentInstance = componentInstance; - }); + context.expose(componentInstance.value); - context.expose(componentInstance.value); + const inputProps = computed(() => ({ + ...props, + editable: false + })); - const inputProps = computed(() => ({ - ...props, - editable: false, - readonly: true, - modelValue: '' - })); - - return () => { - return ( - - ); - }; - } + return () => ; + } }); diff --git a/packages/mobile-ui-vue/components/date-time-picker/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/date-time-picker/src/designer/use-designer-rules.ts index 6dafcd627e266f140333e17916e8a85786f45405..3219c6ed65d399c1d6ff7c73812ce690654aba5f 100644 --- a/packages/mobile-ui-vue/components/date-time-picker/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/date-time-picker/src/designer/use-designer-rules.ts @@ -1,4 +1,4 @@ -import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; +import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; import { DateTimePickerProperty } from "../property-config/date-picker.property-config"; export function useDesignerRules(designItemContext: DesignerItemContext, designerHostService): UseDesignerRules { diff --git a/packages/mobile-ui-vue/components/date-time-picker/src/property-config/date-picker.property-config.ts b/packages/mobile-ui-vue/components/date-time-picker/src/property-config/date-picker.property-config.ts index 990e7b8e3c4a157480b7ce889c6db5618557af5a..482d93fac08ee2edd0b22efcabcd73d1949d208a 100644 --- a/packages/mobile-ui-vue/components/date-time-picker/src/property-config/date-picker.property-config.ts +++ b/packages/mobile-ui-vue/components/date-time-picker/src/property-config/date-picker.property-config.ts @@ -1,4 +1,4 @@ -import { InputBaseProperty } from '@farris/mobile-ui-vue/common/src/entity/input-base-property'; +import { InputBaseProperty } from '@farris/mobile-ui-vue/common'; import { DATE_FORMATS } from './date-format'; export class DateTimePickerProperty extends InputBaseProperty { @@ -10,7 +10,7 @@ export class DateTimePickerProperty extends InputBaseProperty { const displayFormatOptions = this.getDateFormatOptions(propertyData?.editor); return this.getComponentConfig( propertyData, - {}, + { type: 'datetime-picker' }, { title: { description: '', diff --git a/packages/mobile-ui-vue/components/date-time-picker/src/schema/datetime-picker.schema.json b/packages/mobile-ui-vue/components/date-time-picker/src/schema/datetime-picker.schema.json index 73f07942acef1b63cab6cbd3e2f8e3783f4bf8cf..d254d0e16d9346563a82d7452cc6be2e20135924 100644 --- a/packages/mobile-ui-vue/components/date-time-picker/src/schema/datetime-picker.schema.json +++ b/packages/mobile-ui-vue/components/date-time-picker/src/schema/datetime-picker.schema.json @@ -1,88 +1,80 @@ { - "$schema": "https://json-schema.org/draft/2020-12/schema", - "$id": "https://farris-design.gitee.io/date-picker.schema.json", - "title": "datetime-picker", - "description": "日期时间", - "type": "object", - "properties": { - "id": { - "description": "标识", - "type": "string" - }, - "type": { - "description": "控件类型", - "type": "string", - "default": "datetime-picker" - }, - "appearance": { - "description": "外观", - "type": "object", - "properties": { - "class": { - "type": "string" - }, - "style": { - "type": "string" - } - }, - "default": {} - }, - "binding": { - "description": "绑定", - "type": "object", - "default": {} - }, - "required": { - "description": "必填", - "type": "boolean", - "default": false - }, - "readonly": { - "description": "只读", - "type": "boolean", - "default": false - }, - "disabled": { - "description": "禁用", - "type": "boolean", - "default": false - }, - "placeholder": { - "description": "提示文本", - "type": "string" - }, - "title": { - "description": "标题", - "type": "string", - "default": "" - }, - "displayFormat": { - "description": "展示格式", - "type": "enum", - "default": "yyyy-MM-dd HH:mm:ss" - }, - "maxDate": { - "description": "最大日期", - "type": "string" - }, - "minDate": { - "description": "最小日期", - "type": "string" + "$schema": "https://json-schema.org/draft/2020-12/schema", + "$id": "https://farris-design.gitee.io/date-picker.schema.json", + "title": "datetime-picker", + "description": "日期时间", + "type": "object", + "properties": { + "id": { + "description": "标识", + "type": "string" + }, + "type": { + "description": "控件类型", + "type": "string", + "default": "datetime-picker" + }, + "appearance": { + "description": "外观", + "type": "object", + "properties": { + "class": { + "type": "string" }, - "onUpdate:modelValue": { - "description": "值更新事件", - "type": "string" + "style": { + "type": "string" } + }, + "default": {} + }, + "binding": { + "description": "绑定", + "type": "object", + "default": {} + }, + "required": { + "description": "必填", + "type": "boolean", + "default": false + }, + "readonly": { + "description": "只读", + "type": "boolean", + "default": false + }, + "disabled": { + "description": "禁用", + "type": "boolean", + "default": false + }, + "placeholder": { + "description": "提示文本", + "type": "string" + }, + "title": { + "description": "标题", + "type": "string", + "default": "" + }, + "displayFormat": { + "description": "展示格式", + "type": "enum", + "default": "yyyy-MM-dd HH:mm:ss" + }, + "maxDate": { + "description": "最大日期", + "type": "string" + }, + "minDate": { + "description": "最小日期", + "type": "string" }, - "events": [ - "onUpdate:modelValue" - ], - "required": [ - "type" - ], - "ignore": [ - "id", - "type", - "appearance" - ] -} \ No newline at end of file + "onUpdate:modelValue": { + "description": "值更新事件", + "type": "string" + } + }, + "events": ["onUpdate:modelValue"], + "required": ["type"], + "ignore": ["id", "appearance", "binding", "visible"] +} diff --git a/packages/mobile-ui-vue/components/date-time-picker/src/schema/schema-mapper.ts b/packages/mobile-ui-vue/components/date-time-picker/src/schema/schema-mapper.ts index a14506b5dd6337cb6648aab10116a419f8689ebb..35c0af70ce56b5bcd8eea569cd034621da6d74c8 100644 --- a/packages/mobile-ui-vue/components/date-time-picker/src/schema/schema-mapper.ts +++ b/packages/mobile-ui-vue/components/date-time-picker/src/schema/schema-mapper.ts @@ -3,6 +3,6 @@ import { MapperFunction, resolveAppearance } from '@farris/mobile-ui-vue/dynamic export const schemaMapper = new Map([ ['appearance', resolveAppearance], ['binding', 'modelValue'], - ['displayFormat','format'] + ['valueFormat','format'] ]); diff --git a/packages/mobile-ui-vue/components/designer-canvas/index.ts b/packages/mobile-ui-vue/components/designer-canvas/index.ts deleted file mode 100644 index 6ce6546f37b7992e7cd5fe27f3f9b221c3c3558b..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/index.ts +++ /dev/null @@ -1,14 +0,0 @@ -import FDesignerCanvasInstallless from './src/designer-canvas.component'; -import FDesignerItem from './src/components/designer-item.component'; -import { DgControl } from './src/composition/dg-control'; -import type { DesignerHostService, UseDesignerRules } from './src/composition/types'; -import { withInstall } from '../common'; - -export * from './src/composition/props/designer-canvas.props'; -export * from './src/composition/function/use-designer-component'; -export * from './src/composition/function/use-designer-inner-component'; -export * from './src/types'; -const FDesignerCanvas = withInstall(FDesignerCanvasInstallless); - -export { FDesignerCanvas, FDesignerItem, DgControl, UseDesignerRules, DesignerHostService }; -export default FDesignerCanvas; diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/components/designer-inner-item.component.tsx b/packages/mobile-ui-vue/components/designer-canvas/src/components/designer-inner-item.component.tsx deleted file mode 100644 index 9225b195cbf6ee9e2a52ea21a851accdf8372f28..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/components/designer-inner-item.component.tsx +++ /dev/null @@ -1,257 +0,0 @@ -import { Ref, SetupContext, computed, defineComponent, inject, onMounted, provide, ref, watch, onBeforeUnmount, withModifiers } from 'vue'; -import { DesignerInnerItemPropsType, designerInnerItemProps } from '../composition/props/designer-inner-item.props'; -import { DraggingResolveContext, UseDragula } from '../composition/types'; -import { ComponentSchema, DesignerComponentInstance, DesignerItemContext } from '../types'; -import { canvasChanged, setPositionOfButtonGroup } from '../composition/designer-canvas-changed'; -import { useDesignerInnerComponent } from '../composition/function/use-designer-inner-component'; - -const FDesignerInnerItem = defineComponent({ - name: 'FDesignerInnerItem', - props: designerInnerItemProps, - emits: ['selectionChange', 'addComponent', 'removeComponent'], - setup(props: DesignerInnerItemPropsType, context) { - const canMove = ref(props.canMove); - const canAdd = ref(props.canAdd); - const canDelete = ref(props.canDelete); - const canNested = ref(false); - const contentKey = ref(props.contentKey); - const childType = ref(props.childType); - const childLabel = ref(props.childLabel); - const schema = ref(props.modelValue); - const designComponentStyle = ref(''); - const designerItemElementRef = ref(); - const useDragulaComposition = inject('canvas-dragula'); - const componentInstance = ref() as Ref; - const parent = inject('design-item-context'); - const designItemContext = { designerItemElementRef, componentInstance, schema: schema.value, parent, setupContext: context as SetupContext }; - provide('design-item-context', designItemContext); - - const designerItemClass = computed(() => { - const classObject = { - 'farris-component': true, - // 受position-relative影响,整个容器的高度不能被撑起 - 'flex-fill': props.id === 'root-component', - 'position-relative': canMove.value || canDelete.value, - 'farris-nested': canNested.value, - 'can-move': canMove.value, - 'd-none': designerItemElementRef.value && (designerItemElementRef.value as HTMLElement).classList.contains('d-none') - } as Record; - return classObject; - }); - - const desginerItemStyle = computed(() => { - const styleObject = {} as Record; - if (designComponentStyle.value) { - designComponentStyle.value.split(';').reduce((result: Record, styleString: string) => { - const [styleKey, styleValue] = styleString.split(':'); - if (styleKey) { - result[styleKey] = styleValue; - } - return result; - }, styleObject); - } - return styleObject; - }); - - function onClickDeleteButton(payload: MouseEvent, schemaToRemove: ComponentSchema) { - if (parent && parent.schema[contentKey.value]) { - const indexToRemove = parent.schema[contentKey.value].findIndex( - (contentItem: ComponentSchema) => contentItem.id === schemaToRemove.id - ); - // 如果仍然存在子级,点击子级事件,展示属性面板 - if (indexToRemove > -1) { - const childrenSize = parent.schema[contentKey.value].length; - const nextSchema = parent.schema[contentKey.value][indexToRemove % childrenSize]; - const designerItem = parent.designerItemElementRef.value.querySelector( - `#${nextSchema.id}-design-item` - ); - parent.schema[contentKey.value].splice(indexToRemove, 1); - - // 此处删除子组件schame后,会自动选中第一个元素但属性面板不更新,暂时绕过此问题,使用emit removeComponent方式来解决 - canvasChanged.value++; - context.emit('removeComponent'); - context.emit('selectionChange'); - } - } - - } - - function onClickAddButton(payload: MouseEvent) { - if (componentInstance.value.addNewChildComponentSchema) { - const resolveContext = { - componentType: childType.value, - label: childLabel.value, - parentComponentInstance: componentInstance.value, - targetPosition: -1 - } as DraggingResolveContext; - const childComponentSchema = componentInstance.value.addNewChildComponentSchema(resolveContext); - schema.value[contentKey.value].push(childComponentSchema); - context.emit('addComponent'); - } - } - - function renderAddButton() { - return ( - canAdd.value && ( -
{ - onClickAddButton(payload); - }}> - -
- ) - ); - } - - function renderDeleteButton(componentSchema: ComponentSchema) { - return ( - canDelete.value && ( -
- onClickDeleteButton(payload as MouseEvent, componentSchema), - ['stop'])}> - -
- ) - ); - } - function renderMoveButton() { - return ( - canMove.value && ( -
- -
- ) - ); - } - - function renderIconPanel(componentSchema: ComponentSchema) { - return ( -
-
- {renderAddButton()} - {renderMoveButton()} - {renderDeleteButton(componentSchema)} -
-
- ); - } - - watch( - () => props.modelValue, - (value: any) => { - schema.value = value; - designItemContext.schema = value; - } - ); - - function updatePositionOfButtonGroup(e: Event | any) { - const targetEl = e.target as any; - setPositionOfButtonGroup(targetEl); - } - - function bindingScrollEvent() { - if (schema.value?.contents?.length && designerItemElementRef.value) { - designerItemElementRef.value.addEventListener('scroll', updatePositionOfButtonGroup); - } - } - - function createDefaultComponentInstance() { - const designerItemElement = designerItemElementRef.value as HTMLElement; - const innerComponentElementRef = ref(designerItemElement.children[1] as HTMLElement); - const innerComponentInstance = useDesignerInnerComponent(innerComponentElementRef, designItemContext); - return innerComponentInstance.value; - } - - onMounted(() => { - if (designerItemElementRef.value) { - const draggableContainer = designerItemElementRef.value.querySelector( - `[data-dragref='${schema.value.id}-container']` - ); - componentInstance.value = (draggableContainer && draggableContainer.componentInstance) ? - draggableContainer.componentInstance.value : createDefaultComponentInstance(); - - if (useDragulaComposition && draggableContainer) { - useDragulaComposition.attachComponents(draggableContainer, schema.value); - } - canNested.value = componentInstance.value.canNested !== undefined ? componentInstance.value.canNested : canNested.value; - canAdd.value = componentInstance.value.canAdd !== undefined ? componentInstance.value.canAdd : canAdd.value; - canDelete.value = componentInstance.value.canDelete !== undefined ? componentInstance.value.canDelete : canDelete.value; - canMove.value = componentInstance.value.canMove !== undefined ? componentInstance.value.canMove : canMove.value; - designComponentStyle.value = componentInstance.value.styles || ''; - if (designerItemElementRef.value) { - designerItemElementRef.value.componentInstance = componentInstance; - designerItemElementRef.value.designItemContext = designItemContext; - } - } - bindingScrollEvent(); - - canvasChanged.value++; - }); - - onBeforeUnmount(() => { - if (designerItemElementRef.value) { - designerItemElementRef.value.removeEventListener('scroll', updatePositionOfButtonGroup); - } - }); - - function onClickDesignerItem(payload: MouseEvent) { - - if (payload) { - payload.preventDefault(); - payload.stopPropagation(); - } - let draggabledesignerItemElementRef: any = designItemContext.designerItemElementRef; - const designerItemElement = designerItemElementRef.value as HTMLElement; - if (designerItemElement) { - const currentFocusedElements = document.getElementsByClassName('dgComponentFocused') as HTMLCollectionOf; - // 重复点击 - const duplicateClick = - currentFocusedElements && - currentFocusedElements.length === 1 && - currentFocusedElements[0] === designerItemElementRef.value; - if (!duplicateClick) { - Array.from(currentFocusedElements).forEach((element: HTMLElement) => element.classList.remove('dgComponentFocused')); - Array.from(document.getElementsByClassName('dgComponentSelected') as HTMLCollectionOf).forEach( - (element: HTMLElement) => element.classList.remove('dgComponentSelected') - ); - - designerItemElement.classList.add('dgComponentFocused'); - context.emit('selectionChange', schema.value.type, schema.value, props.componentId, componentInstance.value); - if (componentInstance.value.getDraggableDesignItemElement) { - draggabledesignerItemElementRef = componentInstance.value.getDraggableDesignItemElement(designItemContext); - if (draggabledesignerItemElementRef && draggabledesignerItemElementRef.value) { - draggabledesignerItemElementRef.value.classList.add('dgComponentSelected'); - - } - } - } - } - - updatePositionOfButtonGroup({ target: draggabledesignerItemElementRef?.value }); - } - - return () => { - return ( -
- {renderIconPanel(schema.value)} - {context.slots.default && context.slots.default()} -
- ); - }; - } -}); -export default FDesignerInnerItem; diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/components/designer-placeholder.component.tsx b/packages/mobile-ui-vue/components/designer-canvas/src/components/designer-placeholder.component.tsx deleted file mode 100644 index 5dd90cb489ae5a2637354f7ce168bebeaffd8096..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/components/designer-placeholder.component.tsx +++ /dev/null @@ -1,46 +0,0 @@ -import { SetupContext, computed, defineComponent } from 'vue'; -import { DesignerPlaceholderPropsType, designerPlaceholderProps } from '../composition/props/designer-placeholder.props'; - -export default defineComponent({ - name: 'FDesignerPlaceholder', - props: designerPlaceholderProps, - emits: [], - setup(props: DesignerPlaceholderPropsType) { - const designerPlaceholderClass = computed(() => { - const classObject = { - 'drag-and-drop-alert': true, - 'no-drag': true, - 'w-100': true - } as Record; - return classObject; - }); - - const designerPlaceholderStyle = computed(() => { - const styleObject = { - 'height': '60px', - 'display': 'flex', - 'justify-content': 'center', - 'align-items': 'center', - 'margin': 0, - 'padding': '.75rem 1.25rem', - 'border': '1px solid transparent', - 'border-radius': '3px', - 'color': '#315585', - 'background-color': '#dfedff', - 'border-color': '#d2e6ff', - } as Record; - return styleObject; - }); - - return () => ( - - ); - } -}); diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/components/designer-template-item.component.tsx b/packages/mobile-ui-vue/components/designer-canvas/src/components/designer-template-item.component.tsx deleted file mode 100644 index 9df082c1b83fdb4e00db0ecec29594280820e066..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/components/designer-template-item.component.tsx +++ /dev/null @@ -1,57 +0,0 @@ -import { computed, defineComponent, ref } from 'vue'; -import { DesignerItemPropsType, designerItemProps } from '../composition/props/designer-item.props'; -import { canvasChanged } from '../composition/designer-canvas-changed'; - -const FDesignerTemplateItem = defineComponent({ - name: 'FDesignerTemplateItem', - props: designerItemProps, - emits: ['selectionChange'], - setup(props: DesignerItemPropsType, context) { - const designerItemElementRef = ref(); - - const designerItemClass = computed(() => { - const classObject = { - 'farris-component': true - } as Record; - return classObject; - }); - - function onClickDesignerItem(payload: MouseEvent) { - - if (payload) { - payload.preventDefault(); - payload.stopPropagation(); - } - const designerItemElement = designerItemElementRef.value as HTMLElement; - if (designerItemElement) { - const currentSelectedElements = document.getElementsByClassName('dgComponentFocused') as HTMLCollectionOf; - - // 重复点击 - const duplicateClick = - currentSelectedElements && - currentSelectedElements.length === 1 && - currentSelectedElements[0] === designerItemElementRef.value; - if (!duplicateClick) { - Array.from(currentSelectedElements).forEach((element: HTMLElement) => element.classList.remove('dgComponentSelected')); - Array.from(currentSelectedElements).forEach((element: HTMLElement) => element.classList.remove('dgComponentFocused')); - - designerItemElement.classList.add('dgComponentFocused'); - } - } - canvasChanged.value++; - } - - return () => { - return ( -
- {context.slots.default && context.slots.default()} -
- ); - }; - } -}); -export default FDesignerTemplateItem; diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/class/control.css b/packages/mobile-ui-vue/components/designer-canvas/src/composition/class/control.css deleted file mode 100644 index 9044cd61f76655fb7d387bb70f82e0a3516a5b7d..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/class/control.css +++ /dev/null @@ -1,30 +0,0 @@ -/** 筛选方案 **/ -.f-section-scheme { - background: #fff; - margin: 0.5625rem 0.5rem 0; -} - -/** 标签页tabs **/ -.farris-component-tabs .farris-tabs-content.f-utils-fill-flex-column .farris-component-tab-page:has(.farris-tab-page-active) { - display: flex !important; - overflow: hidden; - flex-shrink: 1; - flex-grow: 1; - flex-basis: 0; - flex-direction: column !important; -} - -/** 布局容器 ResponseLayout **/ -.response-layout { - border: dotted 2px #e8e8e8; - -} - -.response-layout .response-layout-item { - border-right: dotted 2px #e8e8e8; - -} - -.response-layout .response-layout-item:not(:last-child) { - padding-right: 8px !important; -} diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/class/designer-canvas.css b/packages/mobile-ui-vue/components/designer-canvas/src/composition/class/designer-canvas.css deleted file mode 100644 index d92b16e7338c8c4ca9b74ef734ddb3feecb7054a..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/class/designer-canvas.css +++ /dev/null @@ -1,284 +0,0 @@ -.form-group-in-canvas .f-cmp-inputgroup .f-state-readonly .input-group-append{ - display: flex !important; -} -.component-btn-group { - flex-direction: row-reverse; - position: absolute; - z-index: 800; - background: #fff; - display: none; - top: -26px; - right: 0; -} - -.component-btn-group > div { - position: fixed; -} - -.farris-component { - /* border: dotted 2px transparent; */ -} - -.farris-component.farris-nested { - padding: 10px !important; - border: dotted 2px #e8e8e8; -} - -.farris-component.farris-nested.dgComponentFocused { - /* padding: 10px; */ - border: dotted 2px #388fff; -} - -.farris-component.can-move { - padding: 2px; -} - -.farris-component.dgComponentSelected > .component-btn-group { - display: flex; -} - -.component-btn-group .component-settings-button { - display: flex; - cursor: pointer; - float: right; - margin-left: 4px; - padding: 0; - font-size: 10px; - line-height: 1.2em; - border-radius: 2px 2px 0px 0px; - width: 24px !important; - height: 24px !important; - color: #fff !important; - background: #388fff !important; -} - -.component-btn-group .component-settings-button .f-icon { - font-size: 18px; - margin: 0 auto; - line-height: 20px; -} - -.component-btn-group .component-settings-button .f-icon.f-icon-yxs_move { - cursor: move; -} - -.farris-component-content-container .drag-container { - display: inherit; - flex-direction: inherit; - flex-shrink: 1; - flex-grow: 1; - flex-basis: 0%; - flex-wrap: inherit; - justify-content: inherit; - align-items: inherit; - width: 100%; - overflow: inherit; - height: inherit; -} - -/* gu-mirror被添加到镜像中 */ -.gu-mirror { - position: fixed !important; - margin: 0 !important; - z-index: 9999 !important; - opacity: 0.8; - -ms-filter: 'progid:DXImageTransform.Microsoft.Alpha(Opacity=80)'; - filter: alpha(opacity=80); -} - -.gu-mirror.undroppable .component-settings-button .f-icon-yxs_move { - cursor: no-drop; -} - -.component-btn-group .component-settings-button .f-icon.f-icon-yxs_delete { - color: #fff !important; - background: #388fff !important; -} - -.gu-hide { - display: none !important; -} - -/** 拖拽时镜像元素的父级元素 */ -.gu-unselectable { - -webkit-user-select: none !important; - -moz-user-select: none !important; - -ms-user-select: none !important; - user-select: none !important; -} - -/* 当拖动源元素的镜像时,gu-transit被添加到源元素中。只是增加了透明度。 */ -.gu-transit { - opacity: 0.2; - -ms-filter: 'progid:DXImageTransform.Microsoft.Alpha(Opacity=20)'; - filter: alpha(opacity=20); -} - -/* 拖拽经过某区域时,为区域增加底色 */ -.drag-over:not(.no-drop) { - background-color: #f3f8ff !important; -} - -/** 拖拽区域内的元素不显示按钮区域 */ -.gu-unselectable .farris-component.dgComponentSelected > .component-btn-group { - display: none; -} - -/** 拖拽区域内的镜像元素显示按钮区域 */ -.gu-unselectable .gu-mirror.farris-component.dgComponentSelected > .component-btn-group { - display: flex; -} - -/** 拖拽过程中的源元素不显示按钮区域 */ -.gu-transit.farris-component.dgComponentSelected > .component-btn-group { - display: none; -} - -/* 镜像元素为fixed定位 */ -.gu-mirror.farris-component.dgComponentSelected { - position: fixed !important; -} - -/* 镜像元素的按钮区域定位 */ -.gu-mirror.farris-component.dgComponentSelected > .component-btn-group > div { - position: relative; - top: 0 !important; - left: 0 !important; -} - -/** 镜像元素的按钮区域设置宽度。是为了适配控件本身宽度比较小,但是操作按钮比较多时,按钮被换行的问题 */ -.gu-mirror.farris-component.dgComponentSelected > .component-btn-group { - width: max-content; -} - -.dgComponentFocused { - border-top: 2px dotted #388fff !important; - border-left: 2px dotted #388fff !important; - border-right: 2px dotted #388fff !important; - border-bottom: 2px dotted #388fff !important; -} - -.dgComponentSelected { - border-top: 2px solid #388fff !important; - border-left: 2px solid #388fff !important; - border-right: 2px solid #388fff !important; - border-bottom: 2px solid #388fff !important; -} - -.editorDiv { - background-color: #dbe6f7; - overflow-x: auto; -} - -.editorPanel { - position: relative; - height: 100%; - min-width: 900px; -} - -/** 卡片区块 **/ -.editorDiv .f-struct-like-card { - display: block; -} - -/** 解决farristab 开启内容填充后切换标签页导致内部列表不显示的问题**/ -.editorDiv .farris-tabs.f-tabs-content-fill .f-struct-is-subgrid .f-grid-is-sub { - width: 100%; -} - -/** 解决在模态框中弹出右键菜单 菜单不显示的问题**/ -.ide-framework .cdk-overlay-container { - z-index: 1100; -} -.editorDiv .f-struct-wrapper { - margin-bottom: 15px; -} - -.f-struct-wrapper + .f-struct-wrapper { - position: relative; - display: inherit; - margin-bottom: 15px; -} - -.f-page-is-mainsubcard .f-page-main .f-struct-wrapper { - background: #fff; -} - -/** 解决带导航的列表和带导航的卡片模板中,不显示右侧区域的问题 */ -.editorDiv .f-page-navigate .f-page { - position: absolute !important; -} - -/** 解决带导航的列表和带导航的卡片模板中,右侧区域滚动条位置问题 */ -.editorDiv .f-page-navigate .f-page.f-page-card .f-page-main > .drag-container { - display: block; - overflow: unset; -} - -/* 解决OA模板(带页头的导航类模板) 中,右侧滚动条位置问题 */ -.editorDiv .f-page.f-page-navigate.f-page-is-listnav-with-header .f-page-main .f-page-content-main { - display: block; -} - -/** 解决在弹窗中使用smoothDnd时不显示镜像元素的问题 */ -.smooth-dnd-ghost { - z-index: 1100 !important; -} - -/** 解决零代码设计器中OA类卡片表单滚动条位置问题 */ -.editorDiv .farris-oa-page.f-page-card .f-page-main { - display: block !important; - overflow: auto !important; -} - -/** 解决带筛选方案的列表表单中,选中表格组件后没有上边线的问题 */ -.editorDiv .f-page-has-scheme .f-page-main.farris-component { - margin-top: 0; -} - -/** 解决表单设计器中顶层工具栏的下拉面板被属性面板(z-index:850)遮挡的问题 */ -.dropdown-menu.show { - z-index: 860; -} - -/** 解决拟物风下从从表区域的下拉箭头错位的问题 */ -.f-struct-subsub-wrapper { - padding-top: 0 !important; -} - -/** 新拖拽 */ -.gu-mirror.undroppable { - cursor: no-drop; -} - -.gu-insertion { - position: fixed; - z-index: 840 !important; - pointer-events: none !important; - background-color: #388fff; - height: 4px; - overflow: hidden; -} - -/* 在designer canvas中还原嵌套页面样式,解决desinger和canvas各自f-page样式冲突 */ -.editorPanel .f-page::before { - display: initial !important; -} - -.editorPanel .f-page .f-page-main { - margin-right: 0.5rem !important; - margin-left: 0.5rem !important; - margin-bottom: 0.5rem !important; -} - -.editorPanel .f-page.f-page-is-listnav .f-page-main { - margin-top: 0.5rem !important; -} - -.editorPanel .f-page .f-page-main .f-page-main { - margin: 0 !important; -} - -.editorPanel .f-page.f-page-has-scheme .f-page-header{ - margin: 0 .5rem; -} diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/designer-canvas-changed.ts b/packages/mobile-ui-vue/components/designer-canvas/src/composition/designer-canvas-changed.ts deleted file mode 100644 index 11ada793acc2a6cb1f85d72862c14502e86f102e..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/designer-canvas-changed.ts +++ /dev/null @@ -1,104 +0,0 @@ -import { ref } from "vue"; - -/** 用于响应画布发生变更 */ -export const canvasChanged = ref(0); - -/** - * 判断DOM 是否在可视区域内 - * @param el 元素 - * @param containerEl 容器 - */ -function isElementInViewport(el: HTMLElement, containerEl: HTMLElement) { - const container = containerEl.getBoundingClientRect(); - const box = el.getBoundingClientRect(); - const top = box.top >= container.top; - const bottom = box.top <= container.bottom; - return (top && bottom); -} - -function setPositionForSelectedElement(selectElement: HTMLElement) { - const toolbar = selectElement.querySelector('.component-btn-group') as HTMLElement; - if (!toolbar) { - return; - } - toolbar.style.display = ''; - const toolbarRect = toolbar.getBoundingClientRect(); - const divPanel = toolbar.querySelector('div') as HTMLElement; - if (divPanel) { - const divPanelRect = divPanel.getBoundingClientRect(); - divPanel.style.top = toolbarRect.top + 'px'; - - // 若操作按钮的最左边比画布最左边还要靠左,那么操作按钮就以控件的最左边为界 - let left = toolbarRect.left - divPanelRect.width; - const editorDiv = document.querySelector('.editorDiv'); - if (editorDiv) { - const editorDivRect = editorDiv.getBoundingClientRect(); - if (left < editorDivRect.left) { - const elementRect = selectElement.getBoundingClientRect(); - ({ left } = elementRect); - } - } - divPanel.style.left = left + 'px'; - } -} - -/** - * 定位画布中已选控件的操作按钮的位置 - * @param canvasElement 画布父容器 - */ -export function setPositionOfButtonGroup(canvasElement: HTMLElement) { - if (!canvasElement) { - return; - } - let selectElement: HTMLElement; - if (canvasElement.className.includes('dgComponentSelected')) { - selectElement = canvasElement; - } else { - selectElement = canvasElement.querySelector('.dgComponentSelected') as HTMLElement; - } - if (!selectElement) { - return; - } - - const selectDomRect = selectElement.getBoundingClientRect(); - if (selectDomRect.width === 0 && selectDomRect.height === 0) { - return; - } - const toolbar = selectElement.querySelector('.component-btn-group') as HTMLElement; - if (toolbar) { - - const isInView = isElementInViewport(selectElement, canvasElement); - if (!isInView) { - toolbar.style.display = 'none'; - return; - } - // 计算位置 - setPositionForSelectedElement(selectElement); - } -} - - -/** - * 定位页面中选中控件的操作按钮位置。 - * 场景:控件内部点击收折或者切换显示内容后,需要重新计算页面中下方选中控件的按钮位置。 - * 例如点击section控件的收折图标后,需要重新计算section下方已选控件的操作按钮位置 - */ -export function setPositionOfSelectedComponentBtnGroup(canvasElement: HTMLElement) { - const selectElement = document.querySelector('.dgComponentSelected') as HTMLElement; - if (!selectElement) { - return; - } - const selectedElementRect = selectElement.getBoundingClientRect(); - const elementRect = canvasElement.getBoundingClientRect(); - - const toolbar = selectElement.querySelector('.component-btn-group') as HTMLElement; - if (toolbar) { - const toolbarRect = toolbar.getBoundingClientRect(); - const isBelow = elementRect.top < selectedElementRect.top; - - // 选中控件已显示并且在基准位置的下方 - if (toolbarRect.top !== 0 && isBelow) { - setPositionForSelectedElement(selectElement); - } - } -} diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/entity/builder-element.ts b/packages/mobile-ui-vue/components/designer-canvas/src/composition/entity/builder-element.ts deleted file mode 100644 index b071db8858797c51e878802f1839262cb96a72ec..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/entity/builder-element.ts +++ /dev/null @@ -1,12 +0,0 @@ -/** - * 设计器DOM元素结构 - */ -export interface BuilderHTMLElement extends Element{ - /** 记录各子元素对应的控件schema json的集合,用于container类dom节点 */ - childrenContents?: any[]; - - /** 记录element对应的component实例,用于单个component节点 */ - componentInstance?: any; - - component?: any; -}; diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/function/use-designer-inner-component.ts b/packages/mobile-ui-vue/components/designer-canvas/src/composition/function/use-designer-inner-component.ts deleted file mode 100644 index ac207a9f5114b3898a679a203cca03109f877b70..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/function/use-designer-inner-component.ts +++ /dev/null @@ -1,186 +0,0 @@ -import { inject, Ref, ref } from "vue"; -import { DesignerHostService, DesignerHTMLElement, DraggingResolveContext, UseDesignerRules } from "../types"; -import { ComponentSchema, DesignerComponentInstance, DesignerItemContext } from "../../types"; -import { getSchemaByTypeForDesigner } from '../../../../dynamic-resolver/src/resolver/schema/schema-resolver-design'; - -export function useDesignerInnerComponent( - elementRef: Ref, - designItemContext: DesignerItemContext, - designerRules?: UseDesignerRules -): Ref { - const styles = (designerRules && designerRules.getStyles && designerRules.getStyles()) || ''; - const componentInstance = ref(); - /** - * 校验组件是否支持移动 - */ - function checkCanMoveComponent(): boolean { - if (designerRules && designerRules.checkCanMoveComponent) { - return designerRules.checkCanMoveComponent(); - } - return true; - } - - /** - * 校验组件是否支持选中父级 - */ - function checkCanSelectParentComponent(): boolean { - return false; - } - - /** - * 校验组件是否支持删除 - */ - function checkCanDeleteComponent() { - if (designerRules && designerRules.checkCanDeleteComponent) { - return designerRules.checkCanDeleteComponent(); - } - return true; - } - - /** - * 校验组件是否支持添加子元素 - */ - function checkCanAddComponent() { - if (designerRules && designerRules.checkCanAddComponent) { - return designerRules.checkCanAddComponent(); - } - return true; - } - - /** - * 判断在可视化区域中是否隐藏容器间距和线条 - */ - function hideNestedPaddingInDesginerView() { - return true; - } - - /** - * 获取组件在表单DOM中所属的Component的实例 - * @param componentInstance 组件实例 - */ - function getBelongedComponentInstance(componentInstance?: Ref): DesignerComponentInstance | null { - if (!componentInstance || !componentInstance.value) { - return null; - } - const parent = ref(componentInstance?.value.parent) as Ref; - const grandParent = getBelongedComponentInstance(parent); - if (grandParent) { - return grandParent; - } - return null; - } - - function getDraggableDesignItemElement(context: DesignerItemContext = designItemContext): Ref | null { - const { componentInstance, designerItemElementRef } = context; - if (!componentInstance || !componentInstance.value) { - return null; - } - if (componentInstance.value.canMove || componentInstance.value.canAdd || componentInstance.value.canDelete) { - return designerItemElementRef; - } - return getDraggableDesignItemElement(context.parent); - } - - /** - * 判断是否可以接收拖拽新增的子级控件 - * @param data 新控件的类型、所属分类 - * @returns boolean - */ - function canAccepts(draggingContext: DraggingResolveContext) { - return !!designerRules && designerRules.canAccepts(draggingContext); - } - - function getDraggingDisplayText() { - return designItemContext?.schema.label || designItemContext?.schema.title || designItemContext?.schema.name; - } - - /** - * 控件可以拖拽到的最外层容器,用于限制控件向外层容器拖拽的范围。不写则不限制 - */ - function getDragScopeElement(): HTMLElement | undefined { - return undefined; - } - - /** - * 移动控件后事件:在可视化设计器中,将现有的控件移动到容器中 - * @param element 移动的源DOM结构 - */ - function onAcceptMovedChildElement(element: DesignerHTMLElement, sourceContainer?: DesignerHTMLElement) { - if (!element || !sourceContainer) { - return; - } - if (designerRules?.onAcceptMovedChildElement) { - designerRules.onAcceptMovedChildElement(element, sourceContainer); - } - } - - function addNewChildComponentSchema(resolveContext: DraggingResolveContext) { - const { componentType } = resolveContext; - const designerHostServer = inject('designer-host-service') as DesignerHostService; - let componentSchema = getSchemaByTypeForDesigner(componentType, resolveContext, designerHostServer) as ComponentSchema; - if (designerRules && designerRules.onResolveNewComponentSchema) { - componentSchema = designerRules.onResolveNewComponentSchema(resolveContext, componentSchema); - } - - const typePrefix = componentType.toLowerCase().replace(/-/g, '_'); - if (componentSchema && !componentSchema.id && componentSchema.type === componentType) { - componentSchema.id = `${typePrefix}_${Math.random().toString().slice(2, 6)}`; - } - return componentSchema; - } - - /** - * 移动内部控件后事件:在可视化设计器中,将现有的控件移动到容器中 - * @param element 移动的源DOM结构 - */ - function onChildElementMovedOut(element: HTMLElement) { - - } - - /** 属性面板属性 */ - function getPropConfig(...args) { - if (designerRules && designerRules.getPropsConfig) { - return designerRules.getPropsConfig(...args); - } - return []; - } - function onRemoveComponent() { - - } - /** - * 控件属性变更后事件 - */ - function onPropertyChanged(event: any) { - if (designerRules && designerRules.onPropertyChanged) { - return designerRules.onPropertyChanged(event); - } - } - componentInstance.value = { - canMove: checkCanMoveComponent(), - canSelectParent: checkCanSelectParentComponent(), - canAdd: checkCanAddComponent(), - canDelete: checkCanDeleteComponent(), - canNested: !hideNestedPaddingInDesginerView(), - contents: [], - elementRef, - parent: designItemContext.parent?.componentInstance, - schema: designItemContext.schema, - styles, - canAccepts, - getBelongedComponentInstance, - getDraggableDesignItemElement, - getDraggingDisplayText, - getPropConfig, - getDragScopeElement, - onAcceptMovedChildElement, - onChildElementMovedOut, - addNewChildComponentSchema, - onRemoveComponent, - triggerBelongedComponentToMoveWhenMoved: !!designerRules && designerRules.triggerBelongedComponentToMoveWhenMoved || ref(false), - triggerBelongedComponentToDeleteWhenDeleted: !!designerRules && designerRules.triggerBelongedComponentToDeleteWhenDeleted || ref(false), - onPropertyChanged - } as DesignerComponentInstance; - - return componentInstance as Ref; - -} diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/function/use-dragula.ts b/packages/mobile-ui-vue/components/designer-canvas/src/composition/function/use-dragula.ts deleted file mode 100644 index 1b8b01052bc27ae976cbb2ac0d1ab8ed2e1b9c21..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/function/use-dragula.ts +++ /dev/null @@ -1,358 +0,0 @@ -import dragula from '@farris/designer-dragula'; -import { DesignerHostService, DesignerHTMLElement, DraggingResolveContext, UseDragula } from '../types'; -import { findIndex } from 'lodash-es'; -import { ref } from 'vue'; -import { canvasChanged } from '../designer-canvas-changed'; -import { ComponentSchema } from '../../types'; -import { dragResolveService } from './drag-resolve'; - -export function useDragula(designerHostService: DesignerHostService): UseDragula { - - let dragulaInstance: any; - - /** - * 判断是否可以接收拖拽的新控件 - * @param el 拖拽的新控件元素 - * @param target 目标位置 - * @returns boolean - */ - function checkCanAcceptDrops( - element: DesignerHTMLElement, - target: DesignerHTMLElement, - sourceContainer: DesignerHTMLElement - ): boolean { - if (!!element.contains(target) || target.classList.contains('no-drop')) { - return false; - } - const result = true; - if (element.componentInstance && element.componentInstance.value.getDragScopeElement) { - const dragScopEle = element.componentInstance.value.getDragScopeElement(); - if (dragScopEle) { - if (!dragScopEle.contains(target)) { - return false; - } - } - } - if (target.componentInstance && target.componentInstance.value.canAccepts) { - const dragResolveUtil = dragResolveService(designerHostService); - const draggingContext = dragResolveUtil.getComponentResolveContext(element, sourceContainer, target); - - return target.componentInstance.value.canAccepts(draggingContext); - } - return result; - } - - /** - * 判断DOM 是否在可视区域内 - * @param el 元素 - * @param containerEl 容器 - */ - function isElementInViewport(element: HTMLElement, sourceContainer: HTMLElement) { - const container = sourceContainer.getBoundingClientRect(); - const box = element.getBoundingClientRect(); - const top = box.top >= container.top; - const bottom = box.top < container.bottom; - return (top && bottom); - } - - /** - * 拖拽过程若中产生了页面的上下滚动,需要将已选控件的操作按钮上下移动相等的距离。 - * @param formElement 滚动父容器 - * @param scrollDirection 滚动方向 - * @param scrollHeight 滚动距离 - */ - function scrollInDragging(formElement: HTMLElement, scrollHeight: number) { - const selectedDom = formElement.querySelector('.dgComponentSelected') as HTMLElement; - if (!selectedDom || scrollHeight === 0) { - return; - } - if (isElementInViewport(selectedDom, formElement)) { - const toolbar = selectedDom.querySelector('.component-btn-group'); - if (toolbar) { - const divPanel = toolbar.querySelector('div'); - if (divPanel && divPanel.style.top) { - const top = Number.parseFloat(divPanel.style.top); - divPanel.style.top = (top - scrollHeight) + 'px'; - } - } - } - } - - /** - * 将新控件json添加到新容器schema json中 - * @param target 目标容器元素 - * @param sourceControlSchema 新控件的JSON schema结构 - * @param sibling 目标位置的下一个同级元素 - */ - function addNewControlToTarget( - target: DesignerHTMLElement, - sourceControlSchema: ComponentSchema | null, - sibling: DesignerHTMLElement - ): number { - let index = -1; - if (!sourceControlSchema) { - return -1; - } - if (target.componentInstance.value.contents) { - if (sibling && sibling.componentInstance) { - if (!sibling.getAttribute('data-noattach')) { - // 定位目标位置 - const siblingComponentSchema = sibling.componentInstance.value.schema; - let locatePredicate: any = { id: siblingComponentSchema.id }; - if (siblingComponentSchema.type === 'component') { - locatePredicate = { component: siblingComponentSchema.id }; - } - - index = findIndex(target.componentInstance.value.contents, locatePredicate); - index = (index === -1) ? 0 : index; - } else { - index = Number(sibling.getAttribute('data-position')); - } - if (index !== -1) { - target.componentInstance.value.contents.splice(index, 0, sourceControlSchema); - } - } else { - target.componentInstance.value.contents.push(sourceControlSchema); - } - } - return index; - } - - /** - * 从控件工具箱中拖拽新建控件 - * @param element 拖拽的元素 - * @param target 目标容器元素 - * @param source 原容器元素 - * @param sibling 目标位置的下一个同级元素 - */ - function createControlFromOutside( - element: DesignerHTMLElement, - target: DesignerHTMLElement, - source: DesignerHTMLElement, - sibling: DesignerHTMLElement - ) { - const dragResolveUtil = dragResolveService(designerHostService); - dragResolveUtil.resolveComponentCreationContextByDrop(element, source, target).then(componentResolveContext => { - if (!componentResolveContext) { - return; - } - const sourceControlSchema = componentResolveContext.componentSchema; - if (sourceControlSchema) { - addNewControlToTarget(target, sourceControlSchema, sibling); - } - }); - // 移除拷贝生成的源DOM - if (target.contains(element)) { - target.removeChild(element); - } - } - /** - * 在现有的表单中拖拽移动控件位置 - * @param element 拖拽的元素 - * @param target 目标容器元素 - * @param source 源容器元素 - * @param sibling 目标位置的下一个同级元素 - */ - function dragBetweenCurrentForm( - element: DesignerHTMLElement, - target: DesignerHTMLElement, - source: DesignerHTMLElement, - sibling: DesignerHTMLElement - ) { - let sourceControlSchema; - let index = -1; - // Form、DataGrid等控件在拖拽时,需要连同所属Component一起拖拽。 - if (element.componentInstance && element.componentInstance.value.triggerBelongedComponentToMoveWhenMoved) { - const cmpInstance = element.componentInstance.value.getBelongedComponentInstance(element.componentInstance); - if (cmpInstance) { - // 将拖拽元素替换为所属Component - element = ref(cmpInstance.elementRef).value.parentElement as DesignerHTMLElement; - // 将源容器元素替换为所属Component的父级元素 - source = element.parentElement as DesignerHTMLElement; - } - - } - const elementComponentSchema = element.componentInstance && element.componentInstance.value.schema; - - let locatePredicate: any = { id: elementComponentSchema && elementComponentSchema.id }; - if (elementComponentSchema.type === 'component') { - locatePredicate = { component: elementComponentSchema && elementComponentSchema.id }; - } - - index = findIndex(source.componentInstance.value.contents, locatePredicate); - - // 从源容器schema json中移除 - if (index !== -1 && source.componentInstance.value.contents) { - sourceControlSchema = source.componentInstance.value.contents.splice(index, 1); - sourceControlSchema = sourceControlSchema[0]; - } - - addNewControlToTarget(target, sourceControlSchema as ComponentSchema, sibling); - - // 源容器的控件被移除掉 - if (source.componentInstance && source.componentInstance.value.onChildElementMovedOut) { - source.componentInstance.value.onChildElementMovedOut(element); - } - - // 目标容器接收新控件 - if (target.componentInstance && target.componentInstance.value.onAcceptMovedChildElement) { - target.componentInstance.value.onAcceptMovedChildElement(element, source); - } - } - - /** - * 拖拽结束 - * @param element 拖拽的元素 - * @param target 目标容器元素 - * @param source 原容器元素 - * @param sibling 目标位置的下一个同级元素 - */ - function onDrop(element: DesignerHTMLElement, target: DesignerHTMLElement, source: DesignerHTMLElement, sibling: DesignerHTMLElement) { - if (!target) { - return; - } - if (element.contains(target)) { - return; - } - const sourceType = element.getAttribute('data-sourceType'); - - switch (sourceType) { - case 'control': case 'field': case 'entity': { - createControlFromOutside(element, target, source, sibling); - break; - } - default: { - if (source.componentInstance.value.contents) { - dragBetweenCurrentForm(element, target, source, sibling); - } else { - // 移除拷贝生成的源DOM - if (target.contains(element)) { - target.removeChild(element); - } - } - } - } - canvasChanged.value++; - - } - - function initializeDragula(containerElement: DesignerHTMLElement) { - if (dragulaInstance) { - dragulaInstance.destroy(); - } - - if (!dragula) { - return; - } - - dragulaInstance = dragula([], { - // 镜像容器 - mirrorContainer: containerElement, - direction: 'mixed', - revertOnSpill: true, - // 判断是否可移动 - moves(element: DesignerHTMLElement, container: DesignerHTMLElement, handle: DesignerHTMLElement): boolean { - let moves = true; - - // 包含no-drag样式的元素不允许拖动 - if (element.classList.contains('no-drag')) { - moves = false; - } - // 为防止误操作,可视化区域的控件只能通过移动图标来拖拽 - if (element.componentInstance) { - moves = !!handle.getAttribute('data-dragging-icon'); - } - return moves; - }, - // 判断是否可拷贝 - copy(element: HTMLElement): boolean { - // 工具箱里的div需要配置drag-copy - return element.classList.contains('drag-copy'); - }, - // 获取镜像元素的文本内容 - getMirrorText(element: DesignerHTMLElement): string { - if (element.componentInstance && element.componentInstance.value.getDraggingDisplayText) { - return element.componentInstance.value.getDraggingDisplayText(); - } - return element.innerText || '控件'; - }, - // 判断目标区域是否可接收拖拽的控件 - accepts(element: DesignerHTMLElement, target: DesignerHTMLElement, source: DesignerHTMLElement): boolean { - const canAccept = checkCanAcceptDrops(element, target, source); - const guMirrotElement = containerElement.lastElementChild as Element; - if (canAccept) { - guMirrotElement.className = guMirrotElement.className.replace('undroppable', ''); - } else if (!guMirrotElement.className.includes('undroppable')) { - guMirrotElement.className += ' undroppable'; - } - return canAccept; - } - }).on('over', (el: DesignerHTMLElement, container: DesignerHTMLElement) => { - container.className += ' drag-over'; - }).on('out', (el: DesignerHTMLElement, container: DesignerHTMLElement) => { - container.className = container.className.replace('drag-over', '').replace(' ', ''); - }).on('drop', ( - element: DesignerHTMLElement, target: DesignerHTMLElement, source: DesignerHTMLElement, sibling: DesignerHTMLElement - ) => { - onDrop(element, target, source, sibling); - }).on('dragend', (element: HTMLElement, scrollHeight: number) => { - scrollInDragging(element, scrollHeight); - }); - } - - /** - * 子组件JSON结构和当前组件的实例添加到DOM中并注册拖拽容器。节点class= 'builder-components...' - * @param element dom元素 - * @param childrenComponents 容器内的子组件实例集合 - * @param childrenContents 子组件JSON schema集合 - * @param component 容器组件实例 - * @returns 容器类组件的子组件集合 - */ - function attachComponents(element: HTMLElement, component: Record) { - - // don't attach if no element was found or component doesn't participate in drag'n'drop. - if (!element) { - return; - } - if (component.noDragDrop) { - return element; - } - // 获取容器中的子组件集合节点 - const containerElement: HTMLElement = element.querySelector(`[data-dragref='${component.id}-container']`) || element; - - // 将容器添加到拖拽列表中,dragula控件会监听容器中元素的拖动事件 - if (dragulaInstance && containerElement) { - // containerElement 为页面中的容器节点的builder-components层级 - dragulaInstance.containers.push(containerElement); - } - } - - /** - * 将工具箱各容器添加到dragula的拖拽列表中 - */ - function attachToolbox() { - if (!dragulaInstance) { - return; - } - const controlPanels = document.getElementsByClassName('controlCategory'); - if (!controlPanels) { - return; - } - - dragulaInstance.containers = dragulaInstance.containers.filter( - (element: HTMLElement) => !element.className.includes('controlCategory') - ); - - Array.from(controlPanels).forEach((panelElement) => { - dragulaInstance.containers.push(panelElement); - }); - - } - - function getDragulaInstance() { - return dragulaInstance; - } - - return { attachComponents, initializeDragula,getDragulaInstance }; - -} diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/props/designer-canvas.props.ts b/packages/mobile-ui-vue/components/designer-canvas/src/composition/props/designer-canvas.props.ts deleted file mode 100644 index e07d95a7ac998de22c81ccbd545eb0443f2ada7e..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/props/designer-canvas.props.ts +++ /dev/null @@ -1,13 +0,0 @@ -import { ExtractPropTypes } from 'vue'; - -export const designerCanvasProps = { - /** - * 组件值 - */ - modelValue: { type: Object, default: {} }, - componentId: { type: String, default: '' }, - components: { type: Array, default: null }, - -} as Record; - -export type DesignerCanvasPropsType = ExtractPropTypes; diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/props/designer-inner-item.props.ts b/packages/mobile-ui-vue/components/designer-canvas/src/composition/props/designer-inner-item.props.ts deleted file mode 100644 index 9c449ec8854f48ad5dc61f0a6dbfcb9ec2a0dfd2..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/props/designer-inner-item.props.ts +++ /dev/null @@ -1,18 +0,0 @@ -import { ExtractPropTypes } from "vue"; - -export const designerInnerItemProps = { - id: { type: String, default: '' }, - componentId: { type: String, default: '' }, - canAdd: { type: Boolean, default: false }, - canDelete: { type: Boolean, default: false }, - canMove: { type: Boolean, default: false }, - contentKey: { type: String, default: 'contents' }, - childLabel: { type: String, default: '' }, - childType: { type: String, default: '' }, - /** - * 组件值 - */ - modelValue: { type: Object }, -} as Record; - -export type DesignerInnerItemPropsType = ExtractPropTypes; diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/props/designer-item.props.ts b/packages/mobile-ui-vue/components/designer-canvas/src/composition/props/designer-item.props.ts deleted file mode 100644 index a674600f00b8102af205824a112d4e6dc8db5238..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/props/designer-item.props.ts +++ /dev/null @@ -1,20 +0,0 @@ -import { ExtractPropTypes } from "vue"; - -export const designerItemProps = { - id: { type: String, default: '' }, - componentId: { type: String, default: '' }, - type: { type: String, default: '' }, - canDelete: { type: Boolean, default: true }, - canMove: { type: Boolean, default: true }, - canSelectParent: { type: Boolean, default: true }, - customButtons: { type: Array, default: [] }, - customClass: { type: String, default: '' }, - customStyle: { type: String, default: '' }, - /** - * 组件值 - */ - modelValue: { type: Object }, - ignore: { type: Boolean, default: false } -} as Record; - -export type DesignerItemPropsType = ExtractPropTypes; diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/props/designer-placeholder.props.ts b/packages/mobile-ui-vue/components/designer-canvas/src/composition/props/designer-placeholder.props.ts deleted file mode 100644 index 3bde9b168af28b319722ce0dc732bcf312a9455b..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/props/designer-placeholder.props.ts +++ /dev/null @@ -1,7 +0,0 @@ -import { ExtractPropTypes } from "vue"; - -export const designerPlaceholderProps = { - id: { type: String } -}; - -export type DesignerPlaceholderPropsType = ExtractPropTypes; diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/rule/drag-drop-rules.schema.json b/packages/mobile-ui-vue/components/designer-canvas/src/composition/rule/drag-drop-rules.schema.json deleted file mode 100644 index f524134d361ffe176334dc26ae2eb8e6a665c0cf..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/rule/drag-drop-rules.schema.json +++ /dev/null @@ -1,646 +0,0 @@ -{ - "$schema": "https://json-schema.org/draft/2020-12/schema", - "$id": "https://farris-design.gitee.io/dragging-rules.schema.json", - "title": "Dragging Rules", - "description": "The rules of designer canvas", - "type": "object", - "properties": { - "f-page": { - "description": "The root class of page designed by farris.", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-page-header": { - "description": "The class of page header designed by farris.", - "type": "string" - }, - "f-page-main": { - "description": "The class of page body designed by farris.", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-struct-like-card": { - "description": "", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-struct-form": { - "description": "The class of form component which has a hierarchical structure of component -> section -> respnse-form.", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-section-form": { - "description": "The class of section which has wrapped a reponse-form component.", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-form-layout": { - "description": "The class of reponse form", - "type": "object", - "properties": { - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": true - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": false - } - } - } - } - } - } - }, - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - } - } - }, - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": false - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - }, - "f-struct-wrapper": { - "description": "", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-section-tabs": { - "description": "The class of section which has wrapped sub-grid tabs.", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-tabs-in-card": { - "description": "The class of tabs which contains sub-grid.", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-struct-data-grid-in-card": { - "description": "The class of sub-grid component", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-grid-is-sub": { - "description": "The class of sub-grid", - "type": "object", - "properties": { - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": true - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": false - } - } - } - } - } - } - }, - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": false - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - } - } - }, - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - } - } - }, - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - }, - "f-section-in-main": { - "description": "The class of section which has wrapped a reponse-form component.", - "type": "object", - "properties": { - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": true - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": false - } - } - } - } - } - } - }, - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": false - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - } - } - }, - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": true - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "object", - "const": { - "allOf": [ - { - "sibling": 0, - "parent": { - "f-page-main": true - } - } - ] - } - } - } - } - } - }, - "f-struct-data-grid": { - "description": "", - "type": "object", - "properties": { - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "object", - "const": true - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - }, - "f-page-main-content": { - "description": "", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-page-content-nav": { - "description": "", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-struct-data-grid-in-nav": { - "description": "", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-page-content-nav-extend": { - "description": "", - "type": "object" - }, - "f-section-in-nav": { - "description": "", - "type": "object", - "properties": { - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": false - } - } - } - } - } - } - }, - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": true - }, - "fixed": { - "type": "boolean", - "const": false - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - } - } - } - } - }, - "f-page-content-main": { - "description": "", - "type": "object", - "properties": {} - } - } - } - } - }, - "f-page-content": { - "description": "", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-page-content-nav": { - "description": "", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-list-nav": { - "description": "", - "type": "object" - }, - "f-list-nav-left": { - "description": "", - "type": "object" - }, - "f-struct-data-grid-in-nav": { - "description": "", - "type": "object", - "properties": { - "contents": { - "type": "object", - "properties": { - "f-section-form": { - "description": "", - "type": "object", - "properties": { - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - }, - "f-section-grid": { - "description": "", - "type": "object", - "properties": { - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - } - } - }, - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - } - } - } - }, - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - }, - "f-page-content-main": { - "description": "", - "type": "object", - "properties": { - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": false - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - } - } - }, - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - } - } - }, - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "object", - "const": { - "anyOf": [ - { - "children": 0 - }, - { - "children": { - "length": { - "not": 1 - }, - "f-struct-like-card": true - } - }, - { - "children": { - "scroll-spy": false, - "f-page-content": false, - "f-struct-like-card": false - } - } - ] - } - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - }, - "f-page-footer": { - "description": "The class of page footer designed by farris.", - "type": "string" - } - } - }, - "rules": { - "type": "object", - "properties": { - "canAccept": { - "type": "boolean", - "const": false - }, - "fixed": { - "type": "boolean", - "const": true - }, - "hidePadding": { - "type": "boolean", - "const": true - } - } - } - } - }, - "f-page-is-managelist": { - "description": "The root class of mangement list page.", - "type": "string" - }, - "f-page-card": { - "description": "", - "type": "object" - }, - "f-page-is-mainsubcard": { - "description": "", - "type": "object" - } - } -} \ No newline at end of file diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/rule/use-drag-drop-rules.ts b/packages/mobile-ui-vue/components/designer-canvas/src/composition/rule/use-drag-drop-rules.ts deleted file mode 100644 index 7af83dea3ad9450ebf4e74b64c2708c7d6335e03..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/rule/use-drag-drop-rules.ts +++ /dev/null @@ -1,196 +0,0 @@ -import dragAndDropRules from './drag-drop-rules.schema.json'; - -interface DragDropRule { - canAccept: boolean; - fixed: boolean; - hidePadding: boolean; - [index: string]: boolean; -} - -interface Expression { - target: string; - operator: string; - param: any; - value: any; -} - -interface DragAndDropContext { - children: any; - parent: any; - slibing: any; - [index: string]: any; -} - -export type CalculateFunction = (target: string, param: any, value: any, context: DragAndDropContext) => boolean; - -export type RuleFunction = (context: DragAndDropContext) => DragDropRule; - -export interface UseDragAndDropRule { - getRuleValue: (componentToken: string, context: DragAndDropContext) => DragDropRule; -} - -const ruleMap = new Map(); - -export function useDragAndDropRules(): UseDragAndDropRule { - - function judgingElementCount(target: string, param: any, value: any, context: DragAndDropContext) { - if (typeof value === 'number') { - return context[target]?.length === value; - } - if (typeof value === 'object') { - const compare = Object.keys(value)[0]; - const targetValue = value[compare]; - if (compare === 'not') { - return Number(context[target].length) !== Number(targetValue); - } - if (compare === 'moreThan') { - return Number(context[target].length) >= Number(targetValue); - } - if (compare === 'lessThan') { - return Number(context[target].length) <= Number(targetValue); - } - } - return false; - } - - function hasChildren(target: string, param: any, value: any, context: DragAndDropContext) { - if (typeof value === 'boolean') { - return context.childrenClassList.includes(param) === Boolean(value); - } - return false; - } - - function hasParent(target: string, param: any, value: any, context: DragAndDropContext) { - if (typeof value === 'boolean') { - return context.parentClassList.includes(param) === Boolean(value); - } - return false; - } - - function hasSibling(target: string, param: any, value: any, context: DragAndDropContext) { - if (typeof value === 'boolean') { - return context.parentClassList.includes(param) === Boolean(value); - } - return false; - } - - const expressionCalculateFunctions = new Map([ - ['length', judgingElementCount], - ['hasChildren', hasChildren], - ['hasSibling', hasSibling], - ['hasParent', hasParent] - ]); - - function parseExpression(token: string, expression: Record): Expression[] { - const target = token; - if (typeof expression === 'number') { - return [{ target, operator: 'length', param: null, value: Number(expression) }]; - } - if (typeof expression === 'object') { - return Object.keys(expression).map((key: string) => { - if (key === 'length') { - return { target, operator: 'length', param: null, value: expression[key] }; - } - const param = key; - const value = expression[key]; - const operator = token === 'children' ? 'hasChildren' : (token === 'parent' ? 'hasParent' : 'hasSibling'); - return { target, operator, param, value }; - }); - } - return []; - } - - function calculateExpression(expression: Expression, context: DragAndDropContext) { - if (expressionCalculateFunctions.has(expression.operator)) { - const calculateFunction = expressionCalculateFunctions.get(expression.operator); - return calculateFunction && calculateFunction(expression.target, expression.param, expression.value, context) || false; - } - return false; - } - - function calculate(expression: Record, context: DragAndDropContext): boolean { - const expressionTokens = Object.keys(expression); - - const parsedExpression = expressionTokens.reduce((expressions: Expression[], token: string) => { - const result = parseExpression(token, expression[token]); - expressions.push(...result); - return expressions; - }, []); - const result = parsedExpression.reduce((parsingResult: boolean, expression: Expression) => { - return parsingResult && calculateExpression(expression, context); - }, true); - - return result; - } - - function parseValueSchema(valueSchema: Record, context: DragAndDropContext): boolean { - const schemaKeys = Object.keys(valueSchema); - const allOf = schemaKeys.includes('allOf'); - const anyOf = schemaKeys.includes('anyOf'); - const hasLogicalOperatorsInSchemaKey = allOf || anyOf; - const logicalOperator = hasLogicalOperatorsInSchemaKey ? (allOf ? 'allOf' : 'anyOf') : 'allOf'; - const expressions = (hasLogicalOperatorsInSchemaKey ? valueSchema[logicalOperator] : [valueSchema]) as Record[]; - const expressionValues = expressions.map((expression: Record) => calculate(expression, context)); - const result = allOf ? !expressionValues.includes(false) : expressionValues.includes(true); - return result; - } - - function resolveRuleValue(ruleValueSchema: Record, context: DragAndDropContext): boolean { - const valueSchema = ruleValueSchema.const; - if (!valueSchema) { - return false; - } - if (typeof valueSchema === 'boolean') { - return valueSchema; - } - if (typeof valueSchema === 'object') { - return parseValueSchema(valueSchema, context); - } - return false; - } - - function generateRuleFunction(rulesSchema: Record): RuleFunction { - return (context: DragAndDropContext) => { - const rulesInstance = { canAccept: true, fixed: false, hidePadding: false } as DragDropRule; - rulesSchema && rulesSchema.properties && - Object.keys(rulesSchema.properties).reduce((compoentRulesMap: DragDropRule, ruleItemKey: string) => { - const ruleItemSchema = rulesSchema.properties[ruleItemKey]; - compoentRulesMap[ruleItemKey] = resolveRuleValue(ruleItemSchema, context); - return compoentRulesMap; - }, rulesInstance); - return rulesInstance; - }; - } - - function resolveComponentRule(componentToken: string, componentSchema: Record, ruleMap: Map) { - if (componentSchema.type === 'object' && componentSchema.properties) { - const { rules: rulesSchema, contents } = componentSchema.properties; - ruleMap.set(componentToken, generateRuleFunction(rulesSchema)); - if (contents) { - Object.keys(contents.properties).forEach((subComponentToken: string) => - resolveComponentRule(subComponentToken, contents.properties[subComponentToken], ruleMap) - ); - } - } - } - - function resolveRuleSchema() { - const { properties: componentsSchema } = dragAndDropRules as Record; - Object.keys(componentsSchema).forEach((componentToken: string) => { - resolveComponentRule(componentToken, componentsSchema[componentToken], ruleMap); - }); - } - - function getRuleValue(componentToken: string, context: DragAndDropContext): DragDropRule { - const rulesInstance = { canAccept: true, fixed: false, hidePadding: true } as DragDropRule; - if (ruleMap.has(componentToken)) { - const ruleFuntions = ruleMap.get(componentToken) as RuleFunction; - return ruleFuntions(context); - } - return rulesInstance; - } - - resolveRuleSchema(); - - return { getRuleValue }; -} diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/rule/use-dragula-common-rule.ts b/packages/mobile-ui-vue/components/designer-canvas/src/composition/rule/use-dragula-common-rule.ts deleted file mode 100644 index 7f6131d69135a84bbe457b8f63572c3598340a36..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/rule/use-dragula-common-rule.ts +++ /dev/null @@ -1,51 +0,0 @@ -import { DgControl } from "../dg-control"; -import { DesignerHostService, DraggingResolveContext } from "../types"; - -export function useDragulaCommonRule() { - - /** - * 容器类控件的基础控制规则 - */ - function basalDragulaRuleForContainer(draggingContext: DraggingResolveContext, designerHostService?: DesignerHostService): boolean { - if (!draggingContext) { - return false; - } - - /** 目标容器的组件实例 */ - const targetCmpInstance = draggingContext.targetContainer?.componentInstance && - draggingContext.targetContainer.componentInstance.value; - - if (!targetCmpInstance) { - return false; - } - const targetContainerType = targetCmpInstance.schema.type; - const belongedComponent = designerHostService?.formSchemaUtils.getComponentById(targetCmpInstance.belongedComponentId); - - // 限制输入类控件的可接收容器 - if (draggingContext.componentCategory === 'input' || draggingContext.componentType === 'form-group') { - if (![DgControl['response-layout-item'].type, DgControl['response-form'].type].includes(targetContainerType)) { - return false; - } - } - - // 限制标签页区域、分组面板的可接收容器 - if (draggingContext.componentType === DgControl.tabs.type || draggingContext.componentType === DgControl.section.type) { - const belongedComponentType = belongedComponent?.componentType; - if (belongedComponentType !== 'frame') { - return false; - } - if (![DgControl['content-container'].type, DgControl['splitter-pane'].type, DgControl['response-layout-item'].type].includes(targetContainerType)) { - return false; - } - } - // 限制筛选方案 - if (draggingContext.componentType === DgControl['query-solution'].type) { - return false; - } - return true; - } - - return { - basalDragulaRuleForContainer - }; -} diff --git a/packages/mobile-ui-vue/components/designer-canvas/src/composition/rule/use-template-rule.ts b/packages/mobile-ui-vue/components/designer-canvas/src/composition/rule/use-template-rule.ts deleted file mode 100644 index 93c1c87835d2f8ac2f0d07ad33aa969e4d5f06b7..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-canvas/src/composition/rule/use-template-rule.ts +++ /dev/null @@ -1,151 +0,0 @@ -import { DesignerItemContext } from "../../types"; -import { DesignerHostService } from "../types"; - -export interface DragDropRule { - canAccept: boolean; - canMove: boolean; - canDelete: boolean; - [index: string]: boolean; -} - -/** - * 解析模板拖拽控制规则 - */ -export class UseTemplateDragAndDropRules { - public getTemplateRule(designItemContext: DesignerItemContext, designerHostService?: DesignerHostService): DragDropRule { - - const formSchemaUtils = designerHostService?.formSchemaUtils; - const dragTemplateRules = formSchemaUtils?.getFormTemplateRule(); - const dragDropRule = { canAccept: true, canDelete: true, canMove: true }; - if (!dragTemplateRules) { - return dragDropRule; - } - const componentContext = this.getComponentContext(designItemContext); - const { componentClassList } = componentContext; - - componentClassList.forEach(componentClass => { - if (!componentClass || !dragTemplateRules[componentClass]) { - return; - } - - const { canMove: moveRule, canDelete: deleteRule, canAccept: acceptRule } = dragTemplateRules[componentClass]; - dragDropRule.canMove = dragDropRule.canMove && this.resolveRuleValue(moveRule, componentContext); - dragDropRule.canDelete = dragDropRule.canDelete && this.resolveRuleValue(deleteRule, componentContext); - dragDropRule.canAccept = dragDropRule.canAccept && this.resolveRuleValue(acceptRule, componentContext); - }); - - return dragDropRule; - } - - private resolveRuleValue(ruleSchema: any, componentContext: any): boolean { - - if (typeof ruleSchema === 'boolean') { - return ruleSchema; - } else { - return this.parseRuleValueSchema(ruleSchema, componentContext); - } - } - - private parseRuleValueSchema(ruleSchema: any, componentContext: any) { - const invalidContext = ruleSchema.invalidContext || []; - let isMatched = true; - for (const ruleContext of invalidContext) { - - // 判断子级节点是否匹配 - if (ruleContext.firstLevelChild) { - if (ruleContext.firstLevelChild.class) { - const { firstLevelChildClassList } = componentContext; - if (firstLevelChildClassList && !firstLevelChildClassList.includes(ruleContext.firstLevelChild.class)) { - isMatched = false; - continue; - } - } - if (ruleContext.firstLevelChild.type) { - const { firstLevelChildSchema } = componentContext; - if (!firstLevelChildSchema || firstLevelChildSchema.type !== ruleContext.firstLevelChild.type) { - isMatched = false; - continue; - } - } - - } - // 判断孙子节点是否匹配 - if (ruleContext.secondLevelChild) { - if (ruleContext.secondLevelChild.class) { - const { secondLevelChildClassList } = componentContext; - if (secondLevelChildClassList && !secondLevelChildClassList.includes(ruleContext.secondLevelChild.class)) { - isMatched = false; - continue; - } - } - if (ruleContext.secondLevelChild.type) { - const { secondLevelChildSchema } = componentContext; - if (!secondLevelChildSchema || secondLevelChildSchema.type !== ruleContext.secondLevelChild.type) { - isMatched = false; - continue; - } - } - - } - // 判断父级节点是否匹配 - if (ruleContext.parent) { - if (ruleContext.parent.class) { - const { parentClassList } = componentContext; - if (parentClassList && !parentClassList.includes(ruleContext.parent.class)) { - isMatched = false; - continue; - } - } - if (ruleContext.parent.type) { - const { parentSchema } = componentContext; - if (parentSchema && parentSchema.type !== ruleContext.parent.type) { - isMatched = false; - continue; - } - } - } - isMatched = true; - break; - } - return !isMatched; - - } - public getComponentContext(designItemContext: DesignerItemContext) { - const component = designItemContext.schema; - - // 控件本身 - const componentClass = component.appearance && component.appearance.class || ''; - const componentClassList = componentClass.split(' ') || []; - - // 控件子级节点 - const childContents = component.contents || []; - const firstLevelChildSchema = childContents.length ? childContents[0] : null; - const firstLevelChildClass = firstLevelChildSchema && firstLevelChildSchema.appearance ? firstLevelChildSchema.appearance.class : ''; - const firstLevelChildClassList = firstLevelChildClass ? firstLevelChildClass.split(' ') : []; - - // 控件孙子级节点 - const secondLevelChildSchema = firstLevelChildSchema?.contents?.length ? firstLevelChildSchema?.contents[0] : null; - const secondLevelChildClass = secondLevelChildSchema && secondLevelChildSchema.appearance ? secondLevelChildSchema.appearance.class : ''; - const secondLevelChildClassList = secondLevelChildClass ? secondLevelChildClass.split(' ') : []; - - // 控件父级节点 - const parentSchema = component.type === 'component' ? designItemContext.parent?.parent?.schema : designItemContext.parent?.schema; - const parentClass = parentSchema && parentSchema.appearance && parentSchema.appearance.class || ''; - const parentClassList = parentClass ? parentClass.split(' ') : []; - - return { - componentClass, - componentClassList, - childContents, - firstLevelChildSchema, - firstLevelChildClass, - firstLevelChildClassList, - secondLevelChildSchema, - secondLevelChildClass, - secondLevelChildClassList, - parentSchema, - parentClass, - parentClassList - }; - } -} diff --git a/packages/mobile-ui-vue/components/designer-toolbox/index.ts b/packages/mobile-ui-vue/components/designer-toolbox/index.ts deleted file mode 100644 index 6616581e20bfa48ed03e175249a0639d29b3445c..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-toolbox/index.ts +++ /dev/null @@ -1,5 +0,0 @@ -import FDesignerToolbox from './src/toolbox.component'; - -export * from './src/types'; - -export { FDesignerToolbox }; diff --git a/packages/mobile-ui-vue/components/designer-toolbox/src/toolbox.component.tsx b/packages/mobile-ui-vue/components/designer-toolbox/src/toolbox.component.tsx deleted file mode 100644 index b28fc46df04c79399c94d3ae8767d63ee4d793b8..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-toolbox/src/toolbox.component.tsx +++ /dev/null @@ -1,153 +0,0 @@ -import { defineComponent, ref, watch } from 'vue'; -import { ToolboxPropsType, toolboxProps } from './toolbox.props'; -import { ToolboxCategory, ToolboxItem } from './types'; - -import toolboxItems from './toolbox.json'; -import './toolbox.css'; - -export default defineComponent({ - name: 'FDesignerToolbox', - props: toolboxProps, - emits: [], - setup(props: ToolboxPropsType) { - const controlCategoryList = props.toolboxItems ? ref(props.toolboxItems as ToolboxCategory[]) : ref(toolboxItems); - const dragularCompostion = ref(props.dragula); - - function onClickCardHeader(payload: MouseEvent, category: any) { - category.isHide = !category.isHide; - } - - function getCardHeaderIconClass(category: any) { - const classObject = { - 'f-icon': true, - 'f-icon-arrow-60-down': !category.isHide, - 'f-icon-arrow-e': category.isHide - } as Record; - return classObject; - } - - function renderCategoryCardHeader(category: ToolboxCategory) { - return ( -
onClickCardHeader(payload, category)}> -
-
-
-
- -
-
- {category.name} -
-
-
-
-
- ); - } - - function getControlTileClass(toolboxItem: ToolboxItem) { - const classObject = { - 'd-none': toolboxItem.dependentParent || toolboxItem.hideInControlBox, - controlPanel: true, - 'drag-copy': true, - 'no-drag': toolboxItem.disable, - 'updating': toolboxItem.updating - } as Record; - return classObject; - } - - function getToolboxItemClass(toolboxItem: ToolboxItem) { - const classObject = { - farrisControlIcon: true, - 'fd-i-Family': true - } as Record; - const toolboxItemTypicalClassName = `fd_pc-${toolboxItem.icon || toolboxItem.type}`; - classObject[toolboxItemTypicalClassName] = true; - return classObject; - } - - function renderControlTile(toolboxItem: ToolboxItem, category: ToolboxCategory) { - return ( - - ); - } - - function renderCategoryCardBody(category: ToolboxCategory) { - return ( -
- {category.items.map((toolboxItem: any) => renderControlTile(toolboxItem, category))} -
- ); - } - - function renderCategoryCard(category: ToolboxCategory) { - return ( - !category.hideInControlBox && ( -
- {renderCategoryCardHeader(category)} - {renderCategoryCardBody(category)} -
- ) - ); - } - - /** - * 将工具箱各容器添加到dragula的拖拽列表中 - */ - function attachToolboxToDragulaContainer(dragulaInstance: any) { - if (!dragulaInstance) { - return; - } - const controlPanels = document.getElementsByClassName('controlCategory'); - if (!controlPanels) { - return; - } - - dragulaInstance.containers = dragulaInstance.containers.filter( - (element: HTMLElement) => !element.className.includes('controlCategory') - ); - - Array.from(controlPanels).forEach((panelElement) => { - dragulaInstance.containers.push(panelElement); - }); - - } - - watch( - () => props.dragula, - (newValue: any) => { - dragularCompostion.value = newValue; - if (dragularCompostion.value?.getDragulaInstance) { - attachToolboxToDragulaContainer(dragularCompostion.value?.getDragulaInstance()); - } - } - ); - - return () => { - return ( -
-
- {controlCategoryList.value.map((category: any) => { - return renderCategoryCard(category); - })} -
-
- ); - }; - } -}); diff --git a/packages/mobile-ui-vue/components/designer-toolbox/src/toolbox.css b/packages/mobile-ui-vue/components/designer-toolbox/src/toolbox.css deleted file mode 100644 index bdc92e873071b54035094c2b119bce297452f7b2..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-toolbox/src/toolbox.css +++ /dev/null @@ -1,75 +0,0 @@ -.controlBox { - font-size: 13px !important; -} - -.controlBox .farris-panel { - border: none; -} - -.controlBox .farris-panel .card-header { - padding: 10px 0px !important; - background-color: #fcfdff !important; -} - -.controlBox .farris-panel .card-header .col-form-label { - font-size: 13px; - margin-bottom: 0px; - color: #3f4764; - opacity: 0.65; -} - -.controlBox .farris-panel .card-header .col-form-label .f-icon { - font-size: 10.8px; - color: #3f4764; -} - -.controlBox .farris-panel .card-body { - display: flex; - flex-wrap: wrap; - background: #fcfdff !important; -} - -.controlPanel:nth-child(-n + 3) { - margin-top: 0 !important; -} - -.controlPanel .farrisControlIcon { - font-size: 27px; -} - -.controlPanel { - font-size: 13px; - cursor: grab; - display: flex; - background: #fff; - align-items: center; - width: 33.333%; - background-color: #fcfdff; - border: 1px solid #edf1f5; - height: 76px !important; - text-align: center; - margin: -1px 0 0 -1px !important; - color: #6080ad; - /* overflow: hidden; */ - text-overflow: ellipsis; - word-break: keep-all; - -webkit-user-select: none; - user-select: none; -} - -.controlPanel.updating { - color: #707070; -} - -.controlPanel > div { - margin: auto; - overflow: hidden; -} - -.gu-mirror.undroppable.controlPanel { - cursor: no-drop; -} - -.controlBox .farris-panel .card-header .col-form-label .icon-panel .f-icon { - font-size: 16px; -} diff --git a/packages/mobile-ui-vue/components/designer-toolbox/src/toolbox.json b/packages/mobile-ui-vue/components/designer-toolbox/src/toolbox.json deleted file mode 100644 index e160cd632e857b784a0e9897dd3412aa280a72b3..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-toolbox/src/toolbox.json +++ /dev/null @@ -1,165 +0,0 @@ -[ - { - "type": "basic", - "name": "基础类控件", - "items": [ - { - "id": "Button", - "type": "button", - "name": "按钮", - "category": "basic", - "icon": "button" - }, - { - "id": "ButtonGroup", - "type": "button-group", - "name": "按钮组", - "category": "basic", - "icon": "button-group" - } - ] - }, - { - "type": "input", - "name": "输入类控件", - "items": [ - { - "id": "TextBox", - "type": "input-group", - "name": "文本框", - "category": "input", - "icon": "input-group" - }, - { - "id": "MultiTextBox", - "type": "textarea", - "name": "多行文本", - "category": "input", - "icon": "textarea" - }, - { - "id": "DateBox", - "type": "date-picker", - "name": "日期选择", - "category": "input", - "icon": "date-picker" - }, - { - "id": "EnumField", - "type": "enum-field", - "name": "选择器", - "category": "input", - "icon": "input-group" - }, - { - "id": "NumericBox", - "type": "number-spinner", - "name": "数值", - "category": "input", - "icon": "number-spinner" - }, - { - "id": "RadioGroup", - "type": "radio-group", - "name": "单选组", - "category": "input", - "icon": "radio-group" - }, - { - "id": "CheckBoxGroup", - "type": "check-group", - "name": "复选框组", - "category": "input", - "icon": "check-group" - }, - { - "id": "SwitchField", - "type": "switch", - "name": "开关", - "category": "input", - "icon": "switch" - } - ] - }, - { - "type": "navigation", - "name": "导航类控件", - "items": [ - { - "id": "NavigationBar", - "type": "navigation-bar", - "name": "导航栏", - "category": "navigation", - "icon": "nav-tab" - } - ] - }, - { - "type": "container", - "name": "容器类控件", - "items": [ - { - "id": "PageHeaderContainer", - "type": "page-header-container", - "name": "页头容器", - "category": "container", - "icon": "content-container" - }, - { - "id": "PageBodyContainer", - "type": "page-body-container", - "name": "页面主体容器", - "category": "container", - "icon": "content-container" - }, - { - "id": "PageFooterContainer", - "type": "page-footer-container", - "name": "页尾容器", - "category": "container", - "icon": "content-container" - }, - { - "id": "ContentContainer", - "type": "content-container", - "name": "通用容器", - "category": "container", - "icon": "content-container" - }, - { - "id": "FloatContainer", - "type": "float-container", - "name": "浮动容器", - "category": "container", - "icon": "content-container" - }, - { - "id": "Form", - "type": "form", - "name": "字段卡片", - "category": "container", - "icon": "response-form" - }, - { - "id": "Card", - "type": "card", - "name": "卡片", - "category": "container", - "icon": "section" - } - ] - }, - { - "type": "display", - "name": "展示类控件", - "items": [ - { - "id": "ListView", - "type": "list-view", - "name": "列表", - "category": "display", - "icon": "list-view" - } - ] - } -] \ No newline at end of file diff --git a/packages/mobile-ui-vue/components/designer-toolbox/src/toolbox.props.ts b/packages/mobile-ui-vue/components/designer-toolbox/src/toolbox.props.ts deleted file mode 100644 index ddf9559cc143543589252b546eeb68e7e25dd251..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-toolbox/src/toolbox.props.ts +++ /dev/null @@ -1,10 +0,0 @@ -import { ExtractPropTypes } from 'vue'; - -export const toolboxProps = { - id: { type: String, default: '' }, - dragula: { type: Object }, - toolboxItems: { type: Object } - -}; - -export type ToolboxPropsType = ExtractPropTypes; diff --git a/packages/mobile-ui-vue/components/designer-toolbox/src/types.ts b/packages/mobile-ui-vue/components/designer-toolbox/src/types.ts deleted file mode 100644 index 52436075af57540988492f1f7cca86ef4aaeb42b..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/designer-toolbox/src/types.ts +++ /dev/null @@ -1,22 +0,0 @@ -export interface ToolboxItem { - id: string; - type: string; - name: string; - category: string; - icon?: string; - feature?: any; - dependentParent?: boolean; - hideInControlBox?: boolean; - disable?: boolean; - fieldType?: string; - templateCategory?: string; - updating?: boolean; -} - -export interface ToolboxCategory { - type: string; - name: string; - items: ToolboxItem[]; - hideInControlBox?: boolean; - isHide?: boolean; -}; diff --git a/packages/mobile-ui-vue/components/designer.ts b/packages/mobile-ui-vue/components/designer.ts index 81ea1c807dd4ec3f81bcbbce6a19d3d20cdeac68..49fc635cbdab0f73fd543dff42840fecbc683c07 100644 --- a/packages/mobile-ui-vue/components/designer.ts +++ b/packages/mobile-ui-vue/components/designer.ts @@ -1,6 +1,3 @@ -export * from './designer-canvas'; export * from './dynamic-resolver'; -export { FDesignerToolbox } from './designer-toolbox'; -export { default as FModal, FModalService, FM_MODAL_SERVICE_TOKEN } from './modal'; -export { FM_UI_PROVIDER_SERVICE_TOKEN } from './common'; export * from './register-designer'; +export { LookupSchemaRepositoryToken, FieldSelectorRepositoryToken } from './lookup'; diff --git a/packages/mobile-ui-vue/components/dynamic-form/index.ts b/packages/mobile-ui-vue/components/dynamic-form/index.ts deleted file mode 100644 index 4eee3a7964841de2fd0304225a0b81de5b707ff2..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/dynamic-form/index.ts +++ /dev/null @@ -1,4 +0,0 @@ - - -export * from './src/types'; -export * from './src/composition/types'; diff --git a/packages/mobile-ui-vue/components/dynamic-form/src/composition/response-form-component-creator.service.ts b/packages/mobile-ui-vue/components/dynamic-form/src/composition/response-form-component-creator.service.ts deleted file mode 100644 index 296ef9ed7657279978d3ede36021c65900dc636e..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/dynamic-form/src/composition/response-form-component-creator.service.ts +++ /dev/null @@ -1,196 +0,0 @@ -import { inject } from 'vue'; -import { DesignerHostService } from '../../../designer-canvas/src/composition/types'; -import { DynamicResolver } from '../../../../components/dynamic-resolver'; -import { ComponentBuildInfo } from '../../../component/src/composition/inner-component-build-info'; -import { ComponentSchema } from '../../../../components/designer-canvas'; -import { FormSchemaEntityFieldTypeName } from '../../../common/entity/entity-schema'; -import { cloneDeep } from 'lodash-es'; - -const ROOT_VIEW_MODEL_ID = 'root-viewmodel'; -/** - * 创建卡片类组件服务类 - */ -export class ResponseFormComponentCreatorService { - - private formSchemaUtils: any; - private controlCreatorUtils: any; - private designViewModelUtils: any; - - constructor( - private resolver: DynamicResolver, - private designerHostService: DesignerHostService - ) { - this.formSchemaUtils = this.designerHostService.formSchemaUtils; - this.controlCreatorUtils = this.designerHostService.controlCreatorUtils; - this.designViewModelUtils = this.designerHostService.designViewModelUtils; - } - - public createComponent(buildInfo: ComponentBuildInfo) { - const componentRefNode = this.createComponentRefNode(buildInfo); - - const componentNode = this.createComponentNode(buildInfo); - - const viewModelNode = this.createViewModeNode(buildInfo); - - const formSchema = this.formSchemaUtils.getFormSchema(); - formSchema.module.viewmodels.push(viewModelNode); - formSchema.module.components.push(componentNode); - - this.designViewModelUtils.assembleDesignViewModel(); - - return componentRefNode; - } - createComponentRefNode(buildInfo: ComponentBuildInfo): any { - const componentRefNode = this.resolver.getSchemaByType('component-ref') as ComponentSchema; - Object.assign(componentRefNode, { - id: `${buildInfo.componentId}-component-ref`, - component: `${buildInfo.componentId}-component`, - }); - return componentRefNode; - } - - createComponentNode(buildInfo: ComponentBuildInfo): any { - const componentNode = this.resolver.getSchemaByType('component') as ComponentSchema; - const contents = this.createFormComponentContents(buildInfo); - Object.assign(componentNode, { - id: `${buildInfo.componentId}-component`, - viewModel: `${buildInfo.componentId}-component-viewmodel`, - componentType: buildInfo.componentType, - appearance: { - class: this.getFormComponentClass() - }, - formColumns: buildInfo.formColumns, - contents - }); - return componentNode; - } - - - /** - * 获取卡片组件层级的class样式 - */ - private getFormComponentClass(): string { - const {templateId} = this.formSchemaUtils.getFormSchema().module; - - // 双列表标签页模板中拖入卡片 - if (templateId === 'double-list-in-tab-template') { - return 'f-struct-wrapper f-utils-fill-flex-column'; - } - return 'f-struct-wrapper'; - - } - - private createFormComponentContents(buildInfo: ComponentBuildInfo) { - // 1、创建section - const section = this.resolver.getSchemaByType('section') as ComponentSchema; - Object.assign(section, { - id: buildInfo.componentId + '-form-section', - appearance: { - class: 'f-section-form f-section-in-mainsubcard' - }, - mainTitle: buildInfo.componentName - }); - - // 2、创建form(默认控件标签独占一列) - const responseForm = this.resolver.getSchemaByType('response-form') as ComponentSchema; - const controls: any[] = []; - Object.assign(responseForm, { - id: buildInfo.componentId + '-form', - appearance: { - class: 'f-form-layout farris-form farris-form-controls-inline' - }, - contents: controls - }); - section.contents = [responseForm]; - - // 3、创建字段 - const { selectedFields } = buildInfo; - selectedFields?.forEach(field => { - const dgVMField = cloneDeep(field); - const resolvedControlClass = this.resolveControlClassByFormColumns(buildInfo); - const fieldMetadata = this.controlCreatorUtils.setFormFieldProperty(dgVMField, '', resolvedControlClass); - - if (fieldMetadata) { - controls.push(fieldMetadata); - } - }); - - // 双列表标签页模板中拖入卡片,要求卡片要填充 - const {templateId} = this.formSchemaUtils.getFormSchema().module; - if (templateId === 'double-list-in-tab-template') { - section.appearance.class = 'f-section-grid f-section-in-main px-0 pt-0'; - section.fill = true; - } - - return [section]; - } - - private resolveControlClassByFormColumns(buildInfo: ComponentBuildInfo) { - let className = ''; - switch (buildInfo.formColumns) { - case 1: { - className = 'col-12'; - break; - } - case 2: { - className = 'col-12 col-md-6 col-xl-6 col-el-6'; - break; - } - case 3: { - className = 'col-12 col-md-6 col-xl-4 col-el-4'; - break; - } - case 4: { - className = 'col-12 col-md-6 col-xl-3 col-el-2'; - break; - } - } - - return className; - } - /** - * 添加viewModel节点 - */ - createViewModeNode(buildInfo: ComponentBuildInfo): any { - const viewModelNode = { - id: `${buildInfo.componentId}-component-viewmodel`, - code: `${buildInfo.componentId}-component-viewmodel`, - name: buildInfo.componentName, - bindTo: buildInfo.bindTo, - parent: ROOT_VIEW_MODEL_ID, - fields: this.assembleViewModelFields(buildInfo), - commands: [], - states: [], - enableValidation: true - }; - return viewModelNode; - } - - /** - * 组装viewModel fields 节点 - */ - private assembleViewModelFields(buildInfo: ComponentBuildInfo) { - - const vmFields: any[] = []; - const { selectedFields } = buildInfo; - selectedFields?.forEach(field => { - let updateOn = 'blur'; - const type = field.type.name; - if (type === FormSchemaEntityFieldTypeName.Enum || type === FormSchemaEntityFieldTypeName.Boolean) { - updateOn = 'change'; - } - - vmFields.push({ - type: 'Form', - id: field.id, - fieldName: field.bindingField, - groupId: null, - groupName: null, - updateOn, - fieldSchema: {} - }); - }); - return vmFields; - } - -} diff --git a/packages/mobile-ui-vue/components/dynamic-form/src/types.ts b/packages/mobile-ui-vue/components/dynamic-form/src/types.ts deleted file mode 100644 index e5029eeff4ca03ccb65d39d4ba1832f9333342bd..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/dynamic-form/src/types.ts +++ /dev/null @@ -1,33 +0,0 @@ -export type EditorType = 'button-edit' | 'check-box' | 'check-group' | 'combo-list' | 'combo-lookup' | 'combo-tree' | - 'date-picker' | 'date-range' | 'datetime-picker' | 'datetime-range' | 'events-editor' | 'month-picker' | 'month-range' | - 'year-picker' | 'year-range' | 'input-group' | 'lookup' | 'number-range' | 'number-spinner' | 'radio-group' | 'text' | - 'response-layout-editor-setting' | 'switch' | 'grid-field-editor' | 'field-selector' | 'schema-selector' | 'mapping-editor' | - 'textarea' | 'response-form-layout-setting'|'binding-selector' | 'query-solution-config' | 'solution-preset' | 'item-collection-editor'; - -export interface EditorConfig { - /** 编辑器类型 */ - type: EditorType; - /** 自定义样式 */ - customClass?: string; - /** 禁用 */ - disabled?: boolean; - /** 只读 */ - readonly?: boolean; - /** 必填 */ - required?: boolean; - /** 提示文本 */ - placeholder?: string; - /** 其他属性 */ - [key: string]: any; -} -export interface FormUnifiedColumnLayout { - uniqueColClassInSM: number; - uniqueColClassInMD: number; - uniqueColClassInLG: number; - uniqueColClassInEL: number; -} -export interface UseResponseFormLayoutSetting { - checkIsInFormComponent: (componentId: string) => boolean; - assembleUnifiedLayoutContext: (propertyData: any) => FormUnifiedColumnLayout; - changeFormControlsByUnifiedLayoutConfig: (formNode: any, unifiedLayout: FormUnifiedColumnLayout, formSchemaId: string) => void; -} diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/index.ts b/packages/mobile-ui-vue/components/dynamic-resolver/index.ts index bab138a779328625c97c8a36a46d55602de13e13..e53b6e8e712046aebdad579a11cb18db9d77071f 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/index.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/index.ts @@ -12,5 +12,9 @@ export * from './src/event-handler-resolver'; export * from './src/resolver/schema/schema-resolver'; export * from './src/resolver/schema/schema-resolver-design'; export * from './src/update-columns-resolver'; +export * from './src/resolver/type-resolver/types'; +export * from './src/resolver/type-resolver/use-type-resolver-design'; +export * from './src/resolver/type-resolver/use-type-resolver'; + export { propertyConfigSchemaMap, getPropertyConfigBySchema } from './src/resolver/property-config/property-config-resolver'; export { propertyConfigSchemaMapForDesigner, getPropertyConfigBySchemaForDesigner } from './src/resolver/property-config/property-config-resolver-design'; diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/appearance.converter.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/appearance.converter.ts index b6ca97b8dff89c0bce1fd44020c8388e552d2428..b197eb6c32c85d949dda840205b16376c7e30722 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/appearance.converter.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/appearance.converter.ts @@ -1,4 +1,4 @@ -import { ComponentSchema } from "../../../designer-canvas/src/types"; +import { ComponentSchema } from "@farris/mobile-ui-vue/common"; import { PropertyConverter, SchemaService } from "../types"; export default { diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/buttons.converter.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/buttons.converter.ts index abfb60a4d295ffa47437e918cd566e80e7908a4d..1eb5a9f3b6d22c9415a20a4bf91bad058977b592 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/buttons.converter.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/buttons.converter.ts @@ -1,4 +1,4 @@ -import { ComponentSchema } from "../../../designer-canvas/src/types"; +import { ComponentSchema } from "@farris/mobile-ui-vue/common"; import { PropertyConverter, SchemaService } from "../types"; export default { diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/change-editor.converter.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/change-editor.converter.ts index 61e5ef06b48fb0060091dc693d490bb44c31df24..72f511cefe1b2ebbb460330f042b5a2837def0be 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/change-editor.converter.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/change-editor.converter.ts @@ -1,4 +1,4 @@ -import { ComponentSchema } from "../../../designer-canvas/src/types"; +import { ComponentSchema } from "@farris/mobile-ui-vue/common"; import { PropertyConverter, SchemaService } from "../types"; export default { diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/enum-data.converter.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/enum-data.converter.ts index 3b1a445ef2fa3bf474069910e903c293a16c3266..aec811359a71ae0e65201aca313583ef1c75b282 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/enum-data.converter.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/enum-data.converter.ts @@ -1,4 +1,4 @@ -import { ComponentSchema } from "../../../designer-canvas/src/types"; +import { ComponentSchema } from "@farris/mobile-ui-vue/common"; import { PropertyConverter, SchemaService } from "../types"; export default { convertTo: (schema: ComponentSchema, propertyKey: string, propertyValue: any, schemaService: SchemaService) => { diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/grid-selection.converter.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/grid-selection.converter.ts index b37faa1b46e3dd9b97dd5b8c7183e7202b03f226..7c5e0797417cbe4db98bba063fbc5ce12aa4982f 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/grid-selection.converter.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/grid-selection.converter.ts @@ -1,4 +1,4 @@ -import { ComponentSchema } from "../../../designer-canvas/src/types"; +import { ComponentSchema } from "@farris/mobile-ui-vue/common"; import { PropertyConverter, SchemaService } from "../types"; export default { convertTo: (schema: ComponentSchema, propertyKey: string, propertyValue: any, schemaService: SchemaService) => { diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/items-count.converter.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/items-count.converter.ts index 288438ef0f2b17a5b63d26388c4f6ec65589a75e..b23f948d25d240e52160612eecc78a49d7f341b9 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/items-count.converter.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/items-count.converter.ts @@ -1,4 +1,4 @@ -import { ComponentSchema } from "../../../designer-canvas/src/types"; +import { ComponentSchema } from "@farris/mobile-ui-vue/common"; import { PropertyConverter, SchemaService } from "../types"; export default { diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/pagination.converter.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/pagination.converter.ts index ebf0e2bb56a5c1011f6ff81f0dffdd9aebe1a5d4..6cdde30711a4a02d2580e005d16a04c6714a4f01 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/pagination.converter.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/pagination.converter.ts @@ -1,4 +1,4 @@ -import { ComponentSchema } from "../../../designer-canvas/src/types"; +import { ComponentSchema } from "@farris/mobile-ui-vue/common"; import { PropertyConverter, SchemaService } from "../types"; /** * NG版,此处pagination类型是布尔 diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/property-editor.converter.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/property-editor.converter.ts index e6e83cae987d6437ee8e7a1879641f845a0b9f0d..4c724568e9f65ce3f198fefc77cbf8925bd33d49 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/property-editor.converter.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/property-editor.converter.ts @@ -1,4 +1,4 @@ -import { ComponentSchema } from "../../../designer-canvas/src/types"; +import { ComponentSchema } from "@farris/mobile-ui-vue/common"; import { PropertyConverter, SchemaService } from "../types"; export default { diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/row-number.converter.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/row-number.converter.ts index 929fb4e037af6a0ecd1de5b07549c82212a7d849..94a4e5c8711002e22cab3abc23f7d4303fdf0f07 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/row-number.converter.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/row-number.converter.ts @@ -1,4 +1,4 @@ -import { ComponentSchema } from "../../../designer-canvas/src/types"; +import { ComponentSchema } from "@farris/mobile-ui-vue/common"; import { PropertyConverter, SchemaService } from "../types"; export default { convertTo: (schema: ComponentSchema, propertyKey: string, propertyValue: any, schemaService: SchemaService) => { diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/type.converter.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/type.converter.ts index f3e2f4c71f0671f8aca0b0dd26fba07948ed1648..805dabf1907bb3469c1ad4ebc3a7a819a703fa55 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/type.converter.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/converter/type.converter.ts @@ -1,5 +1,5 @@ -import { ComponentSchema } from "../../../designer-canvas/src/types"; -import { DgControl } from "../../../designer-canvas/src/composition/dg-control"; +import { ComponentSchema } from "@farris/mobile-ui-vue/common"; +import { DgControl } from "../../../common/src/properties/dg-control"; import { PropertyConverter, SchemaService } from "../types"; export default { diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/property-config-resolver.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/property-config-resolver.ts index 78dc7485bf39d0188860cf206a9314eebfa17ab9..ccf969fd64af0944e0a3af6c2baf06d6478caaab 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/property-config-resolver.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/property-config-resolver.ts @@ -1,9 +1,8 @@ import { computed, ref } from "vue"; import { EffectFunction, PropertyConverter, SchemaService } from './types'; -import { EditorConfig } from "../../dynamic-form"; +import { resolveSchemaWithDefaultValue } from "@farris/mobile-ui-vue/dynamic-resolver"; import { useObjectExpression } from './object-expression'; -import { ComponentSchema } from "../../designer-canvas/src/types"; -import { resolveSchemaWithDefaultValue } from "./schema-resolver"; +import { ComponentSchema, EditorConfig } from "@farris/mobile-ui-vue/common"; import appearanceConverter from './converter/appearance.converter'; import buttonsConverter from "./converter/buttons.converter"; import propertyEditorConverter from "./converter/property-editor.converter"; @@ -16,7 +15,7 @@ import gridSelectionConverter from "./converter/grid-selection.converter"; import itemsCountConverter from "./converter/items-count.converter"; import enumDataConverter from "./converter/enum-data.converter"; import formGroupLabelConverter from "./converter/form-group-label.converter"; -import { ElementPropertyConfig, PropertyEntity } from "@farris/mobile-ui-vue/property-panel"; +import { ElementPropertyConfig, PropertyEntity } from "@farris/mobile-ui-vue/common"; const propertyConfigSchemaMap = {} as Record; const propertyConverterMap = new Map([ diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/props-resolver.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/props-resolver.ts index ad0cbb6f00d7c6f004487c1525dd639670cb910e..7610eb7c00fdd5c08f0e2d88421a7c6841173653 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/props-resolver.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/props-resolver.ts @@ -1,4 +1,4 @@ -import { DesignerHostService } from './../../designer-canvas/src/composition/types'; +import { DesignerHostService } from '@farris/mobile-ui-vue/common'; import { resolveSchemaToProps } from './resolver/schema/schema-resolver'; import { DynamicResolver, EffectFunction, MapperFunction, SchemaResolverFunction } from './types'; import { RegisterContext } from '@farris/mobile-ui-vue/common'; @@ -44,6 +44,6 @@ export function getPropsResolverGenerator>( return propsObject; }, {}); return Object.assign(defaultProps, resolvedPropsValue); - } + }; }; } diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/property-config/use-property-config-resolver.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/property-config/use-property-config-resolver.ts index 022933345d633367bc973bf8d957157b052227c1..c2ca508936d7df88967ae9f2750cd9c9bdec4468 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/property-config/use-property-config-resolver.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/property-config/use-property-config-resolver.ts @@ -1,8 +1,7 @@ import { computed, ref } from "vue"; import { EffectFunction, PropertyConverter, SchemaService } from '../../types'; -import { EditorConfig } from "../../../../dynamic-form"; import { useObjectExpression } from '../../object-expression'; -import { ComponentSchema } from "../../../../designer-canvas/src/types"; +import { ComponentSchema,EditorConfig } from "@farris/mobile-ui-vue/common"; import { resolveSchemaWithDefaultValue } from "../schema/schema-resolver"; import appearanceConverter from '../../converter/appearance.converter'; import buttonsConverter from "../../converter/buttons.converter"; @@ -13,7 +12,7 @@ import fieldSelectorConverter from "../../converter/field-selector.converter"; import paginationConverter from "../../converter/pagination.converter"; import rowNumberConverter from "../../converter/row-number.converter"; import gridSelectionConverter from "../../converter/grid-selection.converter"; -import { ElementPropertyConfig, PropertyEntity } from "../../../../property-panel/src/composition/entity/property-entity"; +import { ElementPropertyConfig, PropertyEntity } from "@farris/mobile-ui-vue/common"; import itemsCountConverter from "../../converter/items-count.converter"; import formGroupLabelConverter from "../../converter/form-group-label.converter"; diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/schema/use-schema-resolver.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/schema/use-schema-resolver.ts index 24e765c8fbe39d8ab80dc743a4c95ae9ae42254d..15a77a4a2251c1000fbf49a86db0535911d2340a 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/schema/use-schema-resolver.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/schema/use-schema-resolver.ts @@ -1,6 +1,6 @@ import { cloneDeep, isPlainObject } from "lodash-es"; import { MapperFunction, SchemaResolverFunction } from "../../types"; -import { DesignerHostService } from "@farris/mobile-ui-vue/designer-canvas"; +import { DesignerHostService } from "@farris/mobile-ui-vue/common"; export function useSchemaResolver(schemaMap: Record, schemaResolverMap: Record) { diff --git a/packages/mobile-ui-vue/components/dynamic-form/src/composition/types.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/type-resolver/types.ts similarity index 79% rename from packages/mobile-ui-vue/components/dynamic-form/src/composition/types.ts rename to packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/type-resolver/types.ts index 6963eb1869721853f90e07126f2d450f0aeca887..1ad88afe1e06c6ac45803b01d679188a7b934333 100644 --- a/packages/mobile-ui-vue/components/dynamic-form/src/composition/types.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/type-resolver/types.ts @@ -1,4 +1,5 @@ -import { EditorConfig } from "../types"; +import { EditorConfig } from "@farris/mobile-ui-vue/common"; + export interface UseTypeResolver { @@ -9,4 +10,4 @@ export interface UseTypeResolver { getChangeFunctionName(type: string): any; getClearFunctionName(type: string): any; -} +}; diff --git a/packages/mobile-ui-vue/components/dynamic-form/src/composition/use-type-resolver-design.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/type-resolver/use-type-resolver-design.ts similarity index 57% rename from packages/mobile-ui-vue/components/dynamic-form/src/composition/use-type-resolver-design.ts rename to packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/type-resolver/use-type-resolver-design.ts index ae5bdac3857c039a0b7db6074b49f19bd299c59e..d29ea4e8b2a5f3bf5d868037bcd0a6f7de526b75 100644 --- a/packages/mobile-ui-vue/components/dynamic-form/src/composition/use-type-resolver-design.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/type-resolver/use-type-resolver-design.ts @@ -1,18 +1,18 @@ -import { componentMap,componentPropsConverter } from '@farris/mobile-ui-vue/register-designer'; -import FInputGroupDesign from '../../../input-group/src/designer/input-group.design.component'; -import { EditorType, EditorConfig } from "../types"; +import { componentMapForDisngner,componentPropsConverterForDesigner } from '@farris/mobile-ui-vue/register-designer'; +import FInputGroupDesign from '../../../../input-group/src/designer/input-group.design.component'; import { UseTypeResolver } from "./types"; +import { EditorConfig, EditorType } from '@farris/mobile-ui-vue/common'; export function useTypeResolverDesign(): UseTypeResolver { function resolveEditorProps(type: EditorType, config: EditorConfig): Record { - const propsConverter = componentPropsConverter[type]; + const propsConverter = componentPropsConverterForDesigner[type]; const viewProps = propsConverter ? propsConverter(config) : {}; return viewProps; } function resolveEditorType(type: EditorType) { - return componentMap[type] || FInputGroupDesign; + return componentMapForDisngner[type] || FInputGroupDesign; } function getChangeFunctionName(type: EditorType) { diff --git a/packages/mobile-ui-vue/components/dynamic-form/src/composition/use-type-resolver.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/type-resolver/use-type-resolver.ts similarity index 94% rename from packages/mobile-ui-vue/components/dynamic-form/src/composition/use-type-resolver.ts rename to packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/type-resolver/use-type-resolver.ts index 2845948f29e29b93bde7cd46555c1a674e997f77..4c24af16a5cd1a2fb6e43dd49266016e6b311244 100644 --- a/packages/mobile-ui-vue/components/dynamic-form/src/composition/use-type-resolver.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/resolver/type-resolver/use-type-resolver.ts @@ -1,8 +1,7 @@ -import FInputGroup from '../../../input-group/src/input-group.component'; -import { EditorType, EditorConfig } from "../types"; -import { UseTypeResolver } from "./types"; +import FInputGroup from '../../../../input-group/src/input-group.component'; +import { EditorConfig, EditorType, UseTypeResolver } from "./types"; -import { componentMap, propsConverterMap, registerComponents } from '../../../register'; +import { componentMap, propsConverterMap, registerComponents } from '../../../../register'; export function useTypeResolver(): UseTypeResolver { diff --git a/packages/mobile-ui-vue/components/dynamic-resolver/src/types.ts b/packages/mobile-ui-vue/components/dynamic-resolver/src/types.ts index c82d887f40275fab8f939ec07e52a24219feb9f5..6eeaa174453212eaf24b02ecef027aab41dadea0 100644 --- a/packages/mobile-ui-vue/components/dynamic-resolver/src/types.ts +++ b/packages/mobile-ui-vue/components/dynamic-resolver/src/types.ts @@ -1,5 +1,5 @@ -import { DesignerHostService } from "../../designer-canvas/src/composition/types"; +import { DesignerHostService } from "@farris/mobile-ui-vue/common"; export type MapperFunction = (key: string, value: any, resolvedSchema?: any) => Record; diff --git a/packages/mobile-ui-vue/components/float-container/index.ts b/packages/mobile-ui-vue/components/float-container/index.ts index 0a6b3139a450c33dd39b43cea7fa34bf42f3d1d5..0c1d2ef206fb80568a66c052033707c1a5737179 100644 --- a/packages/mobile-ui-vue/components/float-container/index.ts +++ b/packages/mobile-ui-vue/components/float-container/index.ts @@ -27,4 +27,4 @@ FloatContainer.registerDesigner = ( export * from './src/float-container.props'; export { FloatContainer }; -export default FloatContainer as typeof FloatContainer & Plugin; +export default FloatContainer; diff --git a/packages/mobile-ui-vue/components/float-container/src/designer/float-container.design.component.tsx b/packages/mobile-ui-vue/components/float-container/src/designer/float-container.design.component.tsx index aa144d9a4b00c310123d4dd7eb90e410bbcfed4f..9188260bc53fe2801b6b1bf536db575c7004b7fe 100644 --- a/packages/mobile-ui-vue/components/float-container/src/designer/float-container.design.component.tsx +++ b/packages/mobile-ui-vue/components/float-container/src/designer/float-container.design.component.tsx @@ -1,7 +1,7 @@ import { SetupContext, defineComponent, inject, onMounted, ref } from 'vue'; import { FloatContainerProps, floatContainerProps } from '../float-container.props'; import { useDesignerRules } from './use-designer-rules'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/common';; export default defineComponent({ name: 'FmFloatContainerDesign', diff --git a/packages/mobile-ui-vue/components/float-container/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/float-container/src/designer/use-designer-rules.ts index 4de48fa61ffdb42b416c08f8e61110fdb662a9bd..c87ca756deee4a873a6454b015224c5a64d3c2a3 100644 --- a/packages/mobile-ui-vue/components/float-container/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/float-container/src/designer/use-designer-rules.ts @@ -15,8 +15,8 @@ * limitations under the License. */ import { ref } from "vue"; -import { ComponentSchema, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; -import { DraggingResolveContext } from "@farris/mobile-ui-vue/designer-canvas/src/composition/types"; +import { DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; +import { DraggingResolveContext } from "@farris/mobile-ui-vue/common"; import { FloatContainerProperty } from "../property-config/float-container.property-config"; export function useDesignerRules(designItemContext: DesignerItemContext, designerHostService): UseDesignerRules { diff --git a/packages/mobile-ui-vue/components/float-container/src/float-container.component.tsx b/packages/mobile-ui-vue/components/float-container/src/float-container.component.tsx index c2718fcdc86a3a178acfbc0359c05872c88b9f73..159f9933d50375f86b6d34ab12629f24494eb9a2 100644 --- a/packages/mobile-ui-vue/components/float-container/src/float-container.component.tsx +++ b/packages/mobile-ui-vue/components/float-container/src/float-container.component.tsx @@ -1,5 +1,5 @@ import { SetupContext, defineComponent, computed } from 'vue'; -import { useBem } from '@farris/mobile-ui-vue/common/index'; +import { useBem } from '@farris/mobile-ui-vue/common'; import { FLOAT_CONTAINER_NAME, floatContainerProps, FloatContainerProps } from './float-container.props'; export default defineComponent({ diff --git a/packages/mobile-ui-vue/components/float-container/src/property-config/float-container.property-config.ts b/packages/mobile-ui-vue/components/float-container/src/property-config/float-container.property-config.ts index ba88af4a427d0015bf35019d8130a669f1131e1f..fd661a5ff67602d28c5c7512f8a0f92a71b91cde 100644 --- a/packages/mobile-ui-vue/components/float-container/src/property-config/float-container.property-config.ts +++ b/packages/mobile-ui-vue/components/float-container/src/property-config/float-container.property-config.ts @@ -1,4 +1,4 @@ -import { BaseControlProperty } from "@farris/mobile-ui-vue/property-panel"; +import { BaseControlProperty } from "@farris/mobile-ui-vue/common"; export class FloatContainerProperty extends BaseControlProperty { constructor(componentId: string, designerHostService: any) { diff --git a/packages/mobile-ui-vue/components/form-item/src/designer/form-item-use-designer-rules.ts b/packages/mobile-ui-vue/components/form-item/src/designer/form-item-use-designer-rules.ts index 0c2b13181ad0c38332593435436ce532446e58ea..6a9344e98d4b39267438febafef14c44e12211fc 100644 --- a/packages/mobile-ui-vue/components/form-item/src/designer/form-item-use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/form-item/src/designer/form-item-use-designer-rules.ts @@ -1,4 +1,4 @@ -import { DesignerItemContext, DesignerHostService, UseDesignerRules, DesignerComponentInstance, ComponentSchema } from "@farris/mobile-ui-vue/designer-canvas"; +import { DesignerItemContext, DesignerHostService, UseDesignerRules, DesignerComponentInstance, ComponentSchema } from "@farris/mobile-ui-vue/common"; import { FormGroupProperty } from "../property-config/form-group.property-config"; export function useDesignerRulesForFormItem(designItemContext: DesignerItemContext, designerHostService?: DesignerHostService): UseDesignerRules { diff --git a/packages/mobile-ui-vue/components/form-item/src/designer/form-item.design.component.tsx b/packages/mobile-ui-vue/components/form-item/src/designer/form-item.design.component.tsx index 4130da830904b5229c3a0c8873c09632b9186cbf..6164f934fb19e101267fa3a782ae966c14f04599 100644 --- a/packages/mobile-ui-vue/components/form-item/src/designer/form-item.design.component.tsx +++ b/packages/mobile-ui-vue/components/form-item/src/designer/form-item.design.component.tsx @@ -1,38 +1,20 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -import { computed, defineComponent, inject, onMounted, ref, SetupContext, watch } from 'vue'; -import { useBem } from '@farris/mobile-ui-vue/common'; -import FmCell from '@farris/mobile-ui-vue/cell'; -import { FORM_ITEM_NAME, FormItemProps, formItemProps } from '../form-item.props'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; -import { propertyConfigSchemaMapForDesigner } from '@farris/mobile-ui-vue/dynamic-resolver'; +import { computed, defineComponent, inject, onMounted, PropType, ref } from 'vue'; +import { DesignerHostService, DesignerItemContext, extractProperties, useDesignerComponent } from '@farris/mobile-ui-vue/common';; +import { propertyConfigSchemaMapForDesigner, useTypeResolverDesign } from '@farris/mobile-ui-vue/dynamic-resolver'; import { useDesignerRulesForFormItem } from './form-item-use-designer-rules'; -import { useTypeResolverDesign } from '@farris/mobile-ui-vue/dynamic-form/src/composition/use-type-resolver-design'; +import { formItemProps } from '../form-item.props'; +import FormItem from '../form-item.component'; export default defineComponent({ name: 'FmFormItemDesign', - props: formItemProps, + inheritAttrs: false, + props: { + ...extractProperties(formItemProps, ['label', 'labelAlign', 'labelWidth']), + editor: { type: Object as PropType, default: ()=>({}) } + }, + setup(props, context) { + const { slots } = context; - setup(props: FormItemProps, context: SetupContext) { - const { slots, expose } = context; - - const labelAlign = ref(props.labelAlign); - const shouldShowRequired = ref(props.required); - const { bem } = useBem(FORM_ITEM_NAME); - const editor = ref(props.editor); const { resolveEditorProps, resolveEditorType } = useTypeResolverDesign(); const elementRef = ref(); @@ -43,53 +25,6 @@ export default defineComponent({ const designerRulesComposition = useDesignerRulesForFormItem(designItemContext, designerHostService); const componentInstance = useDesignerComponent(elementRef, designItemContext, designerRulesComposition); - - const renderLabel = () => { - if (slots.label) { - return [slots.label()]; - } - return ; - }; - - const contentClass = computed(() => { - let contentAlign = props.contentAlign || 'right'; - if (labelAlign.value === 'top') { - contentAlign = 'left'; - } - return { - [bem('content')]: true, - [bem('content', contentAlign)]: true - }; - }); - const renderContent = () => { - const renderConditionEditor = computed(() => { - const editorType = editor.value.type || 'input-group'; - const Component = resolveEditorType(editorType); - const editorProps = resolveEditorProps(editorType, editor.value); - return () => ; - }); - - - return
{renderConditionEditor.value()}
; - }; - - - const formItemClass = computed(() => { - const direction = labelAlign.value === 'top' ? 'vertical' : 'horizontal'; - return { - [bem()]: true, - [bem('', direction)]: true - }; - }); - - const labelClass = computed(() => { - const labelClasses = [bem('label'), bem('label', labelAlign.value)]; - if (shouldShowRequired.value === true) { - labelClasses.push(bem('label', 'required')); - } - return labelClasses.join(' '); - }); - onMounted(() => { elementRef.value.componentInstance = componentInstance; @@ -103,26 +38,38 @@ export default defineComponent({ }; }); - context.expose(componentInstance.value); - return () => { - const innerSlots = { - title: renderLabel, - default: renderContent, - leftIcon: slots.leftIcon, - rightIcon: slots.rightIcon, - extra: slots.extra - }; + const editorProps = computed(()=>{ + const editorType = props.editor.type || 'input-group'; + return resolveEditorProps(editorType, props.editor); + }); + + const renderConditionEditor = () => { + const editorType = props.editor.type || 'input-group'; + const Component = resolveEditorType(editorType); + return ; + }; - return ( - - - ); + const innerSlots = { + ...slots, + default: renderConditionEditor, }; + const formItemProps = computed(()=>{ + return { + ...props, + required: editorProps.value.required + }; + }); + + return () => ( + + + ); + } }); diff --git a/packages/mobile-ui-vue/components/form-item/src/designer/response-form-use-designer-rules.ts b/packages/mobile-ui-vue/components/form-item/src/designer/response-form-use-designer-rules.ts index a3d2c40fb6fd35d090b531197c06b6a38ec61088..0d3fcd6504b50fea6016b978d911a8bf65d5ee12 100644 --- a/packages/mobile-ui-vue/components/form-item/src/designer/response-form-use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/form-item/src/designer/response-form-use-designer-rules.ts @@ -1,5 +1,5 @@ -import { ComponentSchema, DesignerComponentInstance, DesignerHostService, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; -import { DraggingResolveContext } from "@farris/mobile-ui-vue/designer-canvas/src/composition/types"; +import { ComponentSchema, DesignerComponentInstance, DesignerHostService, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; +import { DraggingResolveContext } from "@farris/mobile-ui-vue/common"; import { getSchemaByTypeForDesigner } from "@farris/mobile-ui-vue/dynamic-resolver"; import { ref } from "vue"; import { ResponseFormProperty } from "../property-config/response-form.property-config"; diff --git a/packages/mobile-ui-vue/components/form-item/src/designer/response-form.design.component.tsx b/packages/mobile-ui-vue/components/form-item/src/designer/response-form.design.component.tsx index 117799bedbcd0835fa36e4c2ddd1e67ccd2ae2f8..fdfcaacb9327ec94b37b2269456e14754ce14b3c 100644 --- a/packages/mobile-ui-vue/components/form-item/src/designer/response-form.design.component.tsx +++ b/packages/mobile-ui-vue/components/form-item/src/designer/response-form.design.component.tsx @@ -1,46 +1,50 @@ import { computed, defineComponent, inject, onMounted, ref } from 'vue'; +import { + DesignerHostService, + DesignerItemContext, + extractProperties, + useDesignerComponent +} from '@farris/mobile-ui-vue/common'; import { useDesignerRules } from './response-form-use-designer-rules'; -import { FormProps, formProps } from '../form.props'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import { formProps } from '../form.props'; +import Form from '../form.component'; export default defineComponent({ - name: 'FResponseFormDesign', - props: formProps, - emits: [], - setup(props: FormProps, context) { - const elementRef = ref(); - const designItemContext = inject('design-item-context') as DesignerItemContext; - const designerHostService = inject('designer-host-service'); - const designerRulesComposition = useDesignerRules(designItemContext, designerHostService); - const componentInstance = useDesignerComponent(elementRef, designItemContext, designerRulesComposition); - - onMounted(() => { - elementRef.value.componentInstance = componentInstance; - }); - - context.expose(componentInstance.value); - - const responseFormClass = computed(() => { - const customClassArray = []; - const classObject = { - 'drag-container': true - } as Record; - customClassArray.reduce((result: Record, classString: string) => { - result[classString] = true; - return result; - }, classObject); - return classObject; - }); - - - return () => { - return ( - -
- {context.slots.default && context.slots.default()} -
- - ); - }; - } + name: 'FResponseFormDesign', + inheritAttrs: false, + props: extractProperties(formProps, ['labelAlign', 'labelWidth']), + setup(props, context) { + const elementRef = ref(); + const designItemContext = inject( + 'design-item-context' + ) as DesignerItemContext; + const designerHostService = inject('designer-host-service'); + const designerRulesComposition = useDesignerRules(designItemContext, designerHostService); + const componentInstance = useDesignerComponent( + elementRef, + designItemContext, + designerRulesComposition + ); + + onMounted(() => { + elementRef.value.componentInstance = componentInstance; + }); + + context.expose(componentInstance.value); + + const formProps = computed(() => { + return { + ...props + }; + }); + + return () => ( +
+ ); + } }); diff --git a/packages/mobile-ui-vue/components/form-item/src/form-item.component.tsx b/packages/mobile-ui-vue/components/form-item/src/form-item.component.tsx index 4dfb55249a2d814a627a1a494c58829b571c570b..1627034d57f70c50aacefd5ad82d2e5928eaecd6 100644 --- a/packages/mobile-ui-vue/components/form-item/src/form-item.component.tsx +++ b/packages/mobile-ui-vue/components/form-item/src/form-item.component.tsx @@ -67,7 +67,7 @@ export default defineComponent({ }; }); const renderContent = () => { - return
{slots.default()}
; + return
{slots.default && slots.default()}
; }; const errorMessageClass = computed(() => { diff --git a/packages/mobile-ui-vue/components/form-item/src/form-item.props.ts b/packages/mobile-ui-vue/components/form-item/src/form-item.props.ts index 7c8c29a4f9a5111508d596715ba0a558af39c943..42952726e032549081340deb02599c3e0b9d3c42 100644 --- a/packages/mobile-ui-vue/components/form-item/src/form-item.props.ts +++ b/packages/mobile-ui-vue/components/form-item/src/form-item.props.ts @@ -35,9 +35,7 @@ export const formItemProps = { showErrorMessage: { type: Boolean, default: undefined }, /** 错误信息位置 */ - errorMessageAlign: { type: String as PropType, deafult: undefined }, - - editor: { type: Object as PropType, default: {} }, + errorMessageAlign: { type: String as PropType, deafult: undefined } }; diff --git a/packages/mobile-ui-vue/components/form-item/src/property-config/form-group.property-config.ts b/packages/mobile-ui-vue/components/form-item/src/property-config/form-group.property-config.ts index 1cb9cfe91a5a4089406d5aa09fd452c3f80f6dd9..a09b668a00e703074b130b1c31e39ae0cc386e09 100644 --- a/packages/mobile-ui-vue/components/form-item/src/property-config/form-group.property-config.ts +++ b/packages/mobile-ui-vue/components/form-item/src/property-config/form-group.property-config.ts @@ -1,5 +1,5 @@ -import { DesignerComponentInstance } from "@farris/mobile-ui-vue/designer-canvas"; -import { BaseControlProperty } from "@farris/mobile-ui-vue/property-panel"; +import { DesignerComponentInstance } from "@farris/mobile-ui-vue/common"; +import { BaseControlProperty } from "@farris/mobile-ui-vue/common"; export class FormGroupProperty extends BaseControlProperty { constructor(componentId: string, designerHostService: any) { diff --git a/packages/mobile-ui-vue/components/form-item/src/property-config/response-form.property-config.ts b/packages/mobile-ui-vue/components/form-item/src/property-config/response-form.property-config.ts index 5f1baea84114b12d5562bf9c219d89e18485976c..191cb96397eda9d2706f51e0404a6cf050525fa1 100644 --- a/packages/mobile-ui-vue/components/form-item/src/property-config/response-form.property-config.ts +++ b/packages/mobile-ui-vue/components/form-item/src/property-config/response-form.property-config.ts @@ -1,16 +1,44 @@ -import { DesignerComponentInstance } from "@farris/mobile-ui-vue/designer-canvas"; -import { BaseControlProperty } from "@farris/mobile-ui-vue/property-panel"; +import { DesignerComponentInstance } from '@farris/mobile-ui-vue/common'; +import { BaseControlProperty } from '@farris/mobile-ui-vue/common'; export class ResponseFormProperty extends BaseControlProperty { - constructor(componentId: string, designerHostService: any) { - super(componentId, designerHostService); - } - public getPropertyConfig(propertyData: any, componentInstance: DesignerComponentInstance) { - // 基本信息 - this.propertyConfig.categories['basic'] = this.getBasicPropConfig(propertyData); - // 外观 - this.propertyConfig.categories['appearance'] = this.getAppearanceConfig(propertyData); + constructor(componentId: string, designerHostService: any) { + super(componentId, designerHostService); + } + public getPropertyConfig(propertyData: any, componentInstance: DesignerComponentInstance) { + // 基本信息 + this.propertyConfig.categories['basic'] = this.getBasicPropConfig(propertyData); + // 外观 + this.propertyConfig.categories['appearance'] = this.getAppearanceConfig(propertyData); - return this.propertyConfig; - } + this.propertyConfig.categories['label'] = this.getLabelProperties(propertyData); + + return this.propertyConfig; + } + + getLabelProperties(propertyData: any) { + return { + description: '标签配置', + title: '标签', + properties: { + labelAlign: { + title: '标签排列方式', + type: 'string', + editor: { + type: 'combo-list', + data: [ + { id: 'left', name: '左侧' }, + { id: 'top', name: '上侧' } + ] + }, + refreshPanelAfterChanged: true + }, + labelWidth: { + title: "标签宽度", + type: "string", + visible: propertyData.labelAlign !== 'top' + } + } + }; + } } diff --git a/packages/mobile-ui-vue/components/form-item/src/schema/form-item.schema.json b/packages/mobile-ui-vue/components/form-item/src/schema/form-item.schema.json index 82f34c27ccf448a6c0bab0dc8eee66cc390b2758..bc07415d539e06c2503c4bb65df2ab1488c7be08 100644 --- a/packages/mobile-ui-vue/components/form-item/src/schema/form-item.schema.json +++ b/packages/mobile-ui-vue/components/form-item/src/schema/form-item.schema.json @@ -43,7 +43,8 @@ }, "labelAlign": { "description": "标签排列方式", - "type": "string" + "type": "string", + "default": "left" }, "editor": { "description": "编辑器", diff --git a/packages/mobile-ui-vue/components/form-item/src/schema/form.schema.json b/packages/mobile-ui-vue/components/form-item/src/schema/form.schema.json index 1052a2fc0346c68ce17dc9fe9980600843d5cd5b..c1f7489be07d500d9c0aba5f95389c0d44e8e587 100644 --- a/packages/mobile-ui-vue/components/form-item/src/schema/form.schema.json +++ b/packages/mobile-ui-vue/components/form-item/src/schema/form.schema.json @@ -27,6 +27,15 @@ }, "default": {} }, + "labelWidth": { + "description": "标签宽度", + "type": "number" + }, + "labelAlign": { + "description": "标签排列方式", + "type": "string", + "default": "left" + }, "contents": { "description": "", "type": "array", diff --git a/packages/mobile-ui-vue/components/form/index.ts b/packages/mobile-ui-vue/components/form/index.ts index b91f4f8ab504128ee10444cb60901b63ec843091..8df9ae7b199794fa71cff4dedfb9b4a91ca26bc0 100644 --- a/packages/mobile-ui-vue/components/form/index.ts +++ b/packages/mobile-ui-vue/components/form/index.ts @@ -29,4 +29,4 @@ withRegisterDesigner(Form, { name: FORM_REGISTERED_NAME, propsResolverGenerator, export * from '@farris/mobile-ui-vue/form-item/src/form.props'; export { Form }; -export default Form as typeof Form & Plugin; +export default Form; diff --git a/packages/mobile-ui-vue/components/index.ts b/packages/mobile-ui-vue/components/index.ts index 57ca6309e3deeee7f76bc5aa7951255231b5feba..8078076ff251d9bb9e626b02a26ef1d77e7ca5dd 100644 --- a/packages/mobile-ui-vue/components/index.ts +++ b/packages/mobile-ui-vue/components/index.ts @@ -32,6 +32,7 @@ import Loading from './loading'; import PullRefresh from './pull-refresh'; import List from './list'; import ListView from './list-view'; +import Lookup from './lookup'; import TabBar from "./tab-bar"; import SwipeCell from './swipe-cell'; import ActionSheet from './action-sheet'; @@ -48,13 +49,9 @@ import FloatContainer from './float-container'; import Filter from './filter'; import * as Utils from './common/src/utils'; -import Modal from './modal'; import DynamicView from './dynamic-view'; -import FDesignerCanvas from './designer-canvas'; - export * from './register'; export * from './designer'; -export { schemaMap } from './dynamic-resolver'; export { type DynamicViewContext, DYNAMIC_VIEW_CONTEXT, DefaultDynamicViewContext } from './dynamic-view'; const components = [ @@ -96,6 +93,7 @@ const components = [ PullRefresh, List, ListView, + Lookup, SwipeCell, ActionSheet, Tabs, @@ -110,10 +108,7 @@ const components = [ Component, ContentContainer, FloatContainer, - - Modal, - DynamicView, - FDesignerCanvas + DynamicView ]; const install = (app: App): void => { @@ -161,6 +156,7 @@ export { PullRefresh, List, ListView, + Lookup, SwipeCell, ActionSheet, Tabs, @@ -176,9 +172,7 @@ export { FloatContainer, Utils, - Modal, DynamicView, - FDesignerCanvas }; export default { diff --git a/packages/mobile-ui-vue/components/input-group/index.ts b/packages/mobile-ui-vue/components/input-group/index.ts index e7494d76fdb338d3f11647902a7b2dd00893dc67..bead9f222b0d909a6f65a097ed87b67580e56135 100644 --- a/packages/mobile-ui-vue/components/input-group/index.ts +++ b/packages/mobile-ui-vue/components/input-group/index.ts @@ -12,5 +12,6 @@ withRegisterDesigner(InputGroup, { name: INPUT_GROUP_REGISTERED_NAME, propsResol export * from './src/input-group.props'; export * from './src/types'; + export { InputGroup }; export default InputGroup; diff --git a/packages/mobile-ui-vue/components/input-group/src/composition/use-number.ts b/packages/mobile-ui-vue/components/input-group/src/composition/use-number.ts index 98ff4314120d3f4415f1328e7abb4a335d56eacc..e6020bade91711af09a269c3f0eabe99540bbb3a 100644 --- a/packages/mobile-ui-vue/components/input-group/src/composition/use-number.ts +++ b/packages/mobile-ui-vue/components/input-group/src/composition/use-number.ts @@ -16,13 +16,13 @@ import { InputProps } from '../input-group.props'; import { formatToNumber, isDef, parseFloat } from '@farris/mobile-ui-vue/common'; import { Instance } from './types'; -import { InputTypeMap, InputUpdateOn, InputUpdateOnMap } from '../types'; +import { InputType, InputUpdateOn, InputUpdateOnMap } from '../types'; export function useNumber(props: InputProps): Instance { - const allowDot = props.type === InputTypeMap.number; + const allowDot = props.type === InputType.number; const updateOn: InputUpdateOn = InputUpdateOnMap.blur; const placeholder = '请输入数字'; - const inputType = allowDot ? InputTypeMap.text : InputTypeMap.number; + const inputType = allowDot ? InputType.text : InputType.number; const inputMode = allowDot ? 'decimal' : 'numeric'; const formatValue = (value: string | number) => { diff --git a/packages/mobile-ui-vue/components/input-group/src/composition/use-textarea.ts b/packages/mobile-ui-vue/components/input-group/src/composition/use-textarea.ts index 62f5441e55d20bd1ac2d062df55ad3953713fd95..b26850af5fbcf3487ff3dad4a6309c9dfb1e9d10 100644 --- a/packages/mobile-ui-vue/components/input-group/src/composition/use-textarea.ts +++ b/packages/mobile-ui-vue/components/input-group/src/composition/use-textarea.ts @@ -1,33 +1,18 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ import { Ref, onMounted, unref } from 'vue'; import { addUnit } from '@farris/mobile-ui-vue/common'; import { InputProps } from '../input-group.props'; import { Instance } from './types'; import { useCommon } from './use-common'; -import { InputTypeMap } from '../types'; +import { InputType } from '../types'; export function useTextarea(props: InputProps, inputRef: Ref): Instance { const { placeholder, updateOn, inputMode, formatValue, getModelValue } = useCommon(props); - const inputType = InputTypeMap.textarea; + const inputType = InputType.textarea; const adjustSize = () => { const input = unref(inputRef); - if (!(props.type === InputTypeMap.textarea && props.autoHeight) || !input) { + if (!(props.type === InputType.textarea && props.autoHeight) || !input) { return; } diff --git a/packages/mobile-ui-vue/components/input-group/src/designer/input-group.design.component.tsx b/packages/mobile-ui-vue/components/input-group/src/designer/input-group.design.component.tsx index 77a178a4621ec85a787be5daff4cdbb0916b625d..052a1a13397d38b73b691940c090e6e21e07b933 100644 --- a/packages/mobile-ui-vue/components/input-group/src/designer/input-group.design.component.tsx +++ b/packages/mobile-ui-vue/components/input-group/src/designer/input-group.design.component.tsx @@ -1,4 +1,3 @@ - /** * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. * @@ -14,39 +13,57 @@ * See the License for the specific language governing permissions and * limitations under the License. */ -import { computed, defineComponent, inject, onMounted, readonly, ref, SetupContext } from 'vue'; -import { InputGroup, InputProps, inputProps } from '../..'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import { computed, defineComponent, inject, onMounted, ref, SetupContext } from 'vue'; +import { + DesignerHostService, + DesignerItemContext, + extractProperties, + useDesignerComponent +} from '@farris/mobile-ui-vue/common'; import { useInputGroupDesignerRules } from './use-designer-rules'; +import { inputProps } from '../input-group.props'; +import InputGroup from '../input-group.component'; export default defineComponent({ - name: 'FmInputGroupDesign', - props: inputProps, - emits: [] as (string[] & ThisType) | undefined, - setup(props: InputProps, context: SetupContext) { - const elementRef = ref(); - const designerHostService = inject('designer-host-service'); - const designItemContext = inject('design-item-context') as DesignerItemContext; - const designerRulesComposition = useInputGroupDesignerRules(designItemContext, designerHostService); - const componentInstance = useDesignerComponent(elementRef, designItemContext, designerRulesComposition); + name: 'FmInputGroupDesign', + inheritAttrs: false, + props: extractProperties(inputProps, ['placeholder']), + setup(props, context) { + const elementRef = ref(); + const designerHostService = inject('designer-host-service'); + const designItemContext = inject( + 'design-item-context' + ) as DesignerItemContext; + const designerRulesComposition = useInputGroupDesignerRules( + designItemContext, + designerHostService + ); + const componentInstance = useDesignerComponent( + elementRef, + designItemContext, + designerRulesComposition + ); - onMounted(() => { - elementRef.value.componentInstance = componentInstance; - }); + onMounted(() => { + elementRef.value.componentInstance = componentInstance; + }); - const inputGroupProps = { - editable: false, - }; + context.expose(componentInstance.value); + + const inputProps = computed(()=>{ + return { + ...props, + editable: false + }; + }); - context.expose(componentInstance.value); - - return () => { - return ( - - ); - }; - } + return () => { + return ( + + ); + }; + } }); diff --git a/packages/mobile-ui-vue/components/input-group/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/input-group/src/designer/use-designer-rules.ts index 2d3dd89c385b980e964b103bd92b7a70c69c2347..9de599c140bd3205e8759f271a8c7c40a93be7c4 100644 --- a/packages/mobile-ui-vue/components/input-group/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/input-group/src/designer/use-designer-rules.ts @@ -1,4 +1,4 @@ -import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; +import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; import { InputGroupProperty } from "../property-config/input-group.property-config"; export function useInputGroupDesignerRules(designItemContext: DesignerItemContext, designerHostService): UseDesignerRules { diff --git a/packages/mobile-ui-vue/components/input-group/src/input-group.component.tsx b/packages/mobile-ui-vue/components/input-group/src/input-group.component.tsx index 06291c23313e4b6db06d78fb67f9c0a4ac089d8e..5b4cd229ec435b93a0a49a9095f0bd542cfcd3a4 100644 --- a/packages/mobile-ui-vue/components/input-group/src/input-group.component.tsx +++ b/packages/mobile-ui-vue/components/input-group/src/input-group.component.tsx @@ -19,7 +19,7 @@ import { preventDefault, stopPropagation, useBem } from '@farris/mobile-ui-vue/c import { Icon } from '@farris/mobile-ui-vue/icon'; import { INPUT_NAME, InputProps, inputProps } from './input-group.props'; import { useInputState, useInputEvent, useInputExpose } from './composition'; -import { InputTypeMap } from './types'; +import { InputType } from './types'; export default defineComponent({ name: INPUT_NAME, @@ -60,7 +60,7 @@ export default defineComponent({ }; }); - const isTextArea = computed(() => props.type === InputTypeMap.textarea); + const isTextArea = computed(() => props.type === InputType.textarea); const renderControl = () => { return isTextArea.value ? ( @@ -108,10 +108,10 @@ export default defineComponent({ }; const renderWordLimit = () => - props.showWordLimit && - props.maxLength && ( + props.showWordLimit && (
- {String(innerValue.value).length}/{props.maxLength} + {String(innerValue.value).length} + { props.maxLength && /{props.maxLength} }
); diff --git a/packages/mobile-ui-vue/components/input-group/src/input-group.props.ts b/packages/mobile-ui-vue/components/input-group/src/input-group.props.ts index 13a26c3e1d64570454e37a03af9389da8104db64..6db6873bb24969641bd4dfb24d6e67886a6d1a89 100644 --- a/packages/mobile-ui-vue/components/input-group/src/input-group.props.ts +++ b/packages/mobile-ui-vue/components/input-group/src/input-group.props.ts @@ -1,5 +1,5 @@ import { ExtractPropTypes, PropType } from 'vue'; -import { InputTextAlign, InputTextAlignMap, InputType, InputTypeMap, InputUpdateOn } from "./types"; +import { InputTextAlign, InputTextAlignMap, InputType, InputUpdateOn } from "./types"; import { getPropsResolverGenerator } from '../../dynamic-resolver'; import inputGroupSchema from './schema/input-group.schema.json'; import { schemaMapper } from './schema/schema-mapper'; @@ -12,7 +12,7 @@ export const inputCommonProps = { name: { type: String, default: '' }, - type: { type: String as PropType, default: InputTypeMap.text }, + type: { type: String as PropType, default: InputType.text }, placeholder: { type: String, default: '' }, diff --git a/packages/mobile-ui-vue/components/input-group/src/property-config/converter/input.converter.ts b/packages/mobile-ui-vue/components/input-group/src/property-config/converter/input.converter.ts index 2e66e4b8e92cf480cece47f77b36bf69fffd274c..183b249eac93868f063993402382e2ed7c7de4b0 100644 --- a/packages/mobile-ui-vue/components/input-group/src/property-config/converter/input.converter.ts +++ b/packages/mobile-ui-vue/components/input-group/src/property-config/converter/input.converter.ts @@ -1,4 +1,4 @@ -import { ComponentSchema } from "../../../../designer-canvas/src/types"; +import { ComponentSchema } from "@farris/mobile-ui-vue/common"; import { PropertyConverter, SchemaService } from "../../../../dynamic-resolver/src/types"; const inputFormatValidationTypes = [ diff --git a/packages/mobile-ui-vue/components/input-group/src/property-config/input-group.property-config.ts b/packages/mobile-ui-vue/components/input-group/src/property-config/input-group.property-config.ts index 33eb86d5708e3edc80b04287f9cf18846c810ad9..27d9818b323ed66272e04daf5618c76f91cbd69c 100644 --- a/packages/mobile-ui-vue/components/input-group/src/property-config/input-group.property-config.ts +++ b/packages/mobile-ui-vue/components/input-group/src/property-config/input-group.property-config.ts @@ -1,5 +1,4 @@ -import { InputBaseProperty } from '@farris/mobile-ui-vue/common/src/entity/input-base-property'; -import { DesignerComponentInstance } from '@farris/mobile-ui-vue/designer-canvas'; +import { DesignerComponentInstance, InputBaseProperty } from '@farris/mobile-ui-vue/common'; import { typeConverter, commonConverter, @@ -26,12 +25,11 @@ export class InputGroupProperty extends InputBaseProperty { { maxLength: { description: '文本字数最大长度', - title: '最大长度', + title: '最大字数', type: 'number', editor: { nullable: true, - min: 0, - useThousands: false + min: 0 } } }, diff --git a/packages/mobile-ui-vue/components/input-group/src/schema/input-group.schema.json b/packages/mobile-ui-vue/components/input-group/src/schema/input-group.schema.json index 658e623f09444cf1cc730960f9338c5b28061872..e9cd461e15f03eeecc43482f74e97d7d16230ddd 100644 --- a/packages/mobile-ui-vue/components/input-group/src/schema/input-group.schema.json +++ b/packages/mobile-ui-vue/components/input-group/src/schema/input-group.schema.json @@ -1,77 +1,68 @@ { - "$schema": "https://json-schema.org/draft/2020-12/schema", - "$id": "https://farris-design.gitee.io/input-group.schema.json", - "title": "input-group", - "description": "", - "type": "object", - "properties": { - "id": { - "description": "标识", - "type": "string" - }, - "type": { - "description": "控件类型", - "type": "string", - "default": "input-group" - }, - "appearance": { - "description": "外观", - "type": "object", - "properties": { - "class": { - "type": "string" - }, - "style": { - "type": "string" - } - }, - "default": {} - }, - "binding": { - "description": "绑定", - "type": "object", - "default": {} - }, - "required": { - "description": "必填", - "type": "boolean", - "default": false - }, - "readonly": { - "description": "只读", - "type": "boolean", - "default": false - }, - "disabled": { - "description": "禁用", - "type": "boolean", - "default": false - }, - "placeholder": { - "description": "提示文本", - "type": "string" - }, - "formatValidation": { - "description": "验证类型", - "type": "object", - "default": {} + "$schema": "https://json-schema.org/draft/2020-12/schema", + "$id": "https://farris-design.gitee.io/input-group.schema.json", + "title": "input-group", + "description": "", + "type": "object", + "properties": { + "id": { + "description": "标识", + "type": "string" + }, + "type": { + "description": "控件类型", + "type": "string", + "default": "input-group" + }, + "appearance": { + "description": "外观", + "type": "object", + "properties": { + "class": { + "type": "string" }, - "onUpdate:modelValue": { - "description": "值更新事件", - "type": "string", - "default": "" + "style": { + "type": "string" } + }, + "default": {} + }, + "binding": { + "description": "绑定", + "type": "object", + "default": {} + }, + "required": { + "description": "必填", + "type": "boolean", + "default": false + }, + "readonly": { + "description": "只读", + "type": "boolean", + "default": false + }, + "disabled": { + "description": "禁用", + "type": "boolean", + "default": false + }, + "placeholder": { + "description": "提示文本", + "type": "string" + }, + "formatValidation": { + "description": "验证类型", + "type": "object", + "default": {} }, - "events": [ - "onUpdate:modelValue" - ], - "required": [ - "type" - ], - "ignore": [ - "id", - "appearance", - "binding", - "visible" - ] -} \ No newline at end of file + "onUpdate:modelValue": { + "description": "值更新事件", + "type": "string", + "default": "" + } + }, + "events": ["onUpdate:modelValue"], + "required": ["type"], + "ignore": ["id", "appearance", "binding", "visible"] +} diff --git a/packages/mobile-ui-vue/components/input-group/src/types/index.ts b/packages/mobile-ui-vue/components/input-group/src/types/index.ts index 0a89559108a4a15db0fa42aebb7a344639281fe1..b6f652a33896d1da073a941422ecabdc2588db10 100644 --- a/packages/mobile-ui-vue/components/input-group/src/types/index.ts +++ b/packages/mobile-ui-vue/components/input-group/src/types/index.ts @@ -9,7 +9,7 @@ export enum InputUpdateOnMap { blur = 'blur' } -export enum InputTypeMap { +export enum InputType { text = 'text', textarea = 'textarea', number = 'number', @@ -25,4 +25,3 @@ export type InputTextAlign = `${InputTextAlignMap}`; export type InputUpdateOn = `${InputUpdateOnMap}`; -export type InputType = `${InputTypeMap}`; diff --git a/packages/mobile-ui-vue/components/list-view/src/designer/list-view.design.component.tsx b/packages/mobile-ui-vue/components/list-view/src/designer/list-view.design.component.tsx index f6134fdff945c2b9c4f5f2fac4700ad65387e3a8..a55e3ca50bac4b4bf2249d6dc48c2ca981846bf5 100644 --- a/packages/mobile-ui-vue/components/list-view/src/designer/list-view.design.component.tsx +++ b/packages/mobile-ui-vue/components/list-view/src/designer/list-view.design.component.tsx @@ -3,7 +3,7 @@ import { LIST_VIEW_NAME, ListViewProps, listViewProps } from '../list-view.props import { useDesignerRules } from './use-designer-rules'; import List from '@farris/mobile-ui-vue/list'; import { useBem } from '@farris/mobile-ui-vue/common'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas'; +import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/common'; export default defineComponent({ name: 'FmListViewDesign', diff --git a/packages/mobile-ui-vue/components/list-view/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/list-view/src/designer/use-designer-rules.ts index 40aeb4c0600ce4b443b1640108525796ad5b08c2..d2b71120a11de6ff7df62b4ab2f8fbfbac9d1aa5 100644 --- a/packages/mobile-ui-vue/components/list-view/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/list-view/src/designer/use-designer-rules.ts @@ -1,7 +1,7 @@ import { ref } from "vue"; -import { DesignerHostService, DraggingResolveContext, UseDesignerRules } from "../../../designer-canvas/src/composition/types"; +import { DesignerHostService, DraggingResolveContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; import { ComponentProperty } from "../property-config/component.property-config"; -import { DesignerItemContext } from "@farris/mobile-ui-vue/designer-canvas"; +import { DesignerItemContext } from "@farris/mobile-ui-vue/common"; export function useDesignerRules(designItemContext: DesignerItemContext,designerHostService?: DesignerHostService): UseDesignerRules { diff --git a/packages/mobile-ui-vue/components/list-view/src/list-view.props.ts b/packages/mobile-ui-vue/components/list-view/src/list-view.props.ts index 2bdf5bff01b589b322b86289bfefd11ac31cfed5..26512af3ede635336bbad5f7112f933661b0d602 100644 --- a/packages/mobile-ui-vue/components/list-view/src/list-view.props.ts +++ b/packages/mobile-ui-vue/components/list-view/src/list-view.props.ts @@ -21,7 +21,6 @@ import { CheckboxProps } from '@farris/mobile-ui-vue/checkbox/src/checkbox.props import { getPropsResolverGenerator } from '../../dynamic-resolver'; import { schemaMapper } from './schema/schema-mapper'; import listViewSchema from './schema/list-view.schema.json'; -import listViewPropertyConfig from './property-config/list-view.property-config.json'; import { schemaResolver } from './schema/schema-resolver'; export const LIST_VIEW_NAME = 'fm-list-view'; @@ -111,6 +110,5 @@ export const propsResolverGenerator = getPropsResolverGenerator( listViewProps, listViewSchema, schemaMapper, - schemaResolver, - listViewPropertyConfig, + schemaResolver ); diff --git a/packages/mobile-ui-vue/components/list-view/src/property-config/component.property-config.ts b/packages/mobile-ui-vue/components/list-view/src/property-config/component.property-config.ts index 073ac3a8fe542f8f6b6c1858fe7c810bea841469..1304cda2a52d2b7f4d5a3b7ebc1cb59e5f2c21ac 100644 --- a/packages/mobile-ui-vue/components/list-view/src/property-config/component.property-config.ts +++ b/packages/mobile-ui-vue/components/list-view/src/property-config/component.property-config.ts @@ -1,4 +1,4 @@ -import { BaseControlProperty } from "@farris/mobile-ui-vue/property-panel"; +import { BaseControlProperty } from "@farris/mobile-ui-vue/common"; export class ComponentProperty extends BaseControlProperty { diff --git a/packages/mobile-ui-vue/components/list-view/src/property-config/list-view.property-config.json b/packages/mobile-ui-vue/components/list-view/src/property-config/list-view.property-config.json deleted file mode 100644 index 75c9494bb38f45b67ab5dd580d47377788251bc8..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/list-view/src/property-config/list-view.property-config.json +++ /dev/null @@ -1,143 +0,0 @@ -{ - "title": "list-view", - "description": "A Farris Component", - "type": "object", - "categories": { - "basic": { - "description": "Basic Infomation", - "title": "基本信息", - "properties": { - "id": { - "description": "组件标识", - "title": "标识", - "type": "string", - "readonly": true - }, - "type": { - "description": "组件类型", - "title": "控件类型", - "type": "string" - } - } - }, - "behavior": { - "description": "", - "title": "行为", - "properties": { - "visible": { - "description": "运行时组件是否可见", - "type": "boolean", - "title": "是否可见", - "editor": { - "type": "combo-list", - "data": [ - { - "value": true, - "name": "是" - }, - { - "value": false, - "name": "否" - } - ] - } - }, - "enablePullRefresh": { - "description": "是否启用下拉刷新列表数据", - "type": "boolean", - "title": "是否启用下拉刷新", - "editor": { - "type": "combo-list", - "data": [ - { - "value": true, - "name": "是" - }, - { - "value": false, - "name": "否" - } - ] - } - }, - "enableMultiSelect": { - "description": "是否启用多选功能,启用后长按列表条目进入多选状态", - "type": "boolean", - "title": "是否启用多选功能", - "editor": { - "type": "combo-list", - "data": [ - { - "value": true, - "name": "是" - }, - { - "value": false, - "name": "否" - } - ] - } - }, - "multiSelect": { - "description": "是否默认处于多选状态", - "type": "boolean", - "title": "是否默认处于多选状态", - "editor": { - "type": "combo-list", - "data": [ - { - "value": true, - "name": "是" - }, - { - "value": false, - "name": "否" - } - ] - } - }, - "fill": { - "description": "是否填充页面下方剩余区域", - "type": "boolean", - "title": "是否填充", - "editor": { - "type": "combo-list", - "data": [ - { - "value": true, - "name": "是" - }, - { - "value": false, - "name": "否" - } - ] - } - }, - "split": { - "description": "是否在列表条目之间显示分隔线", - "type": "boolean", - "title": "是否显示分隔线", - "editor": { - "type": "combo-list", - "data": [ - { - "value": true, - "name": "是" - }, - { - "value": false, - "name": "否" - } - ] - } - }, - "emptyMessage": { - "description": "列表数据为空时显示的占位文本", - "title": "空数据提示文本", - "type": "string" - } - } - } - } -} \ No newline at end of file diff --git a/packages/mobile-ui-vue/components/lookup/index.ts b/packages/mobile-ui-vue/components/lookup/index.ts index f51566db69f31b3d86ab9b0093c3172a4b89e107..885ec8fbd5e56a7be7ba09b423c756c77b331290 100644 --- a/packages/mobile-ui-vue/components/lookup/index.ts +++ b/packages/mobile-ui-vue/components/lookup/index.ts @@ -1,9 +1,20 @@ -import { withInstall } from '@farris/mobile-ui-vue/common'; +import { withInstall, withRegister, withRegisterDesigner } from '@farris/mobile-ui-vue/common'; import LookupInstallless from './src/lookup.component'; import { LOOKUP_HTTP_SERVICE_TOKEN } from './src/lookup.props'; import { LookupDisplayType } from './src/composition'; +import { propsResolverGenerator } from './src/lookup.props'; +import LookupDesign from './src/designer/lookup.design.component'; + +export { LookupSchemaRepositoryToken, FieldSelectorRepositoryToken } from './src/property-config/lookup.property-config'; const Lookup = withInstall(LookupInstallless); +// 注册运行时及设计时 + +const LOOKUP_REGISTERED_NAME = 'lookup'; +withRegister(Lookup, { name: LOOKUP_REGISTERED_NAME, propsResolverGenerator }); +withRegisterDesigner(Lookup, { name: LOOKUP_REGISTERED_NAME, propsResolverGenerator, designerComponent: LookupDesign }); + + export { Lookup, LOOKUP_HTTP_SERVICE_TOKEN, LookupDisplayType }; export default Lookup; diff --git a/packages/mobile-ui-vue/components/lookup/src/components/footer.component.tsx b/packages/mobile-ui-vue/components/lookup/src/components/footer.component.tsx index b5da66bcc9e22cb860dbb3fe0731a52025d4aa89..6840cf90720e78f6f334a80fe659e2795e538611 100644 --- a/packages/mobile-ui-vue/components/lookup/src/components/footer.component.tsx +++ b/packages/mobile-ui-vue/components/lookup/src/components/footer.component.tsx @@ -1,6 +1,6 @@ import { computed, defineComponent } from 'vue'; import { useBem } from '@farris/mobile-ui-vue/common'; -import { Checker, CheckerShapeMap } from '@farris/mobile-ui-vue/checker'; +import { Checker, CheckerShape } from '@farris/mobile-ui-vue/checker'; import Button from '@farris/mobile-ui-vue/button'; import { useLookupPanelState } from '../composition'; import { LOOKUP_PANEL_NAME } from '../lookup-panel.props'; @@ -28,7 +28,7 @@ export default defineComponent({ class={bem('footer-checker')} label={isSelectedAllValue.value ? '取消全选' : '全选'} modelValue={isSelectedAllValue.value} - shape={CheckerShapeMap.Round} + shape={CheckerShape.Round} onChange={handleSelecteAll} >} diff --git a/packages/mobile-ui-vue/components/lookup/src/composition/use-render-component.tsx b/packages/mobile-ui-vue/components/lookup/src/composition/use-render-component.tsx index 3dbd6e6523fd49c9f9cd54a171f793778fbbed00..6616b4583a160d35932d3081c7a4dcaf7d43e118 100644 --- a/packages/mobile-ui-vue/components/lookup/src/composition/use-render-component.tsx +++ b/packages/mobile-ui-vue/components/lookup/src/composition/use-render-component.tsx @@ -1,6 +1,6 @@ import { computed } from "vue"; import { getValue, stopPropagation, useBem } from "@farris/mobile-ui-vue/common"; -import { Checker, CheckerShapeMap } from "@farris/mobile-ui-vue/checker"; +import { Checker, CheckerShape } from "@farris/mobile-ui-vue/checker"; import Icon from "@farris/mobile-ui-vue/icon"; import Cell from "@farris/mobile-ui-vue/cell"; import { ListDataItem, LookupDisplayType, UseRenderComponent } from "./types"; @@ -34,7 +34,7 @@ export const useRenderComponent: UseRenderComponent = (events) => { handleChange(item)} > ); diff --git a/packages/mobile-ui-vue/components/lookup/src/designer/lookup.design.component.tsx b/packages/mobile-ui-vue/components/lookup/src/designer/lookup.design.component.tsx new file mode 100644 index 0000000000000000000000000000000000000000..17407092fa7230fd9ebcba18d7293b1dcf7a41d4 --- /dev/null +++ b/packages/mobile-ui-vue/components/lookup/src/designer/lookup.design.component.tsx @@ -0,0 +1,42 @@ +import { computed, defineComponent, inject, onMounted, ref } from 'vue'; +import { + DesignerHostService, + DesignerItemContext, + extractProperties, + useDesignerComponent +} from '@farris/mobile-ui-vue/common'; +import { lookupProps } from '../lookup.props'; +import { usePickerDesignerRules } from './use-designer-rules'; +import InputGroup from '@farris/mobile-ui-vue/input-group'; + +export default defineComponent({ + name: 'FmPickerDesign', + inheritAttrs: false, + props: extractProperties(lookupProps, ['placeholder']), + setup(props, context) { + const elementRef = ref(); + const designerHostService = inject('designer-host-service'); + const designItemContext = inject( + 'design-item-context' + ) as DesignerItemContext; + const designerRulesComposition = usePickerDesignerRules(designItemContext, designerHostService); + const componentInstance = useDesignerComponent( + elementRef, + designItemContext, + designerRulesComposition + ); + + onMounted(() => { + elementRef.value.componentInstance = componentInstance; + }); + + context.expose(componentInstance.value); + + const inputProps = computed(() => ({ + ...props, + editable: false + })); + + return () => ; + } +}); diff --git a/packages/mobile-ui-vue/components/lookup/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/lookup/src/designer/use-designer-rules.ts new file mode 100644 index 0000000000000000000000000000000000000000..9db02ba77e2a1ff8e3414919ec655b91654fb1c7 --- /dev/null +++ b/packages/mobile-ui-vue/components/lookup/src/designer/use-designer-rules.ts @@ -0,0 +1,15 @@ +import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; +import { LookupProperty } from "../property-config/lookup.property-config"; +export function usePickerDesignerRules(designItemContext: DesignerItemContext, designerHostService): UseDesignerRules { + + const schema = designItemContext.schema as ComponentSchema; + + // 构造属性配置方法 + function getPropsConfig(componentId: string, componentInstance: DesignerComponentInstance) { + const lookupProps = new LookupProperty(componentId, designerHostService); + return lookupProps.getPropertyConfig(schema, componentInstance); + } + + return { getPropsConfig } as UseDesignerRules; + +} diff --git a/packages/mobile-ui-vue/components/lookup/src/lookup.props.ts b/packages/mobile-ui-vue/components/lookup/src/lookup.props.ts index 20fa4fbc3ed0db13e0f015ca42930753bddb22a9..aca051ceb15115485d53c2a576ffc126a3eddae0 100644 --- a/packages/mobile-ui-vue/components/lookup/src/lookup.props.ts +++ b/packages/mobile-ui-vue/components/lookup/src/lookup.props.ts @@ -1,6 +1,10 @@ import { ExtractPropTypes } from 'vue'; import { buttonEditProps } from '@farris/mobile-ui-vue/button-edit'; import { lookupPanelProps } from './lookup-panel.props'; +import { getPropsResolverGenerator } from '@farris/mobile-ui-vue/dynamic-resolver'; +import lookupSchema from './schema/lookup.schema.json'; +import { schemaMapper } from './schema/schema-mapper'; +import { schemaResolver } from './schema/schema-resolver'; export * from './lookup-panel.props'; @@ -12,3 +16,5 @@ export const lookupProps = { }; export type LookupProps = ExtractPropTypes; + +export const propsResolverGenerator = getPropsResolverGenerator(lookupProps, lookupSchema, schemaMapper, schemaResolver); diff --git a/packages/mobile-ui-vue/components/lookup/src/property-config/converters/lookup-property.converter.ts b/packages/mobile-ui-vue/components/lookup/src/property-config/converters/lookup-property.converter.ts new file mode 100644 index 0000000000000000000000000000000000000000..4980fd32460205ae92c589b28cfa995914f3b3c8 --- /dev/null +++ b/packages/mobile-ui-vue/components/lookup/src/property-config/converters/lookup-property.converter.ts @@ -0,0 +1,119 @@ +function generateSourceUri(ctrlId: string) { + let code = 'form_group_' + Date.now(); + if (ctrlId) { + code = ctrlId.replaceAll('-', '_').replaceAll('.', '_'); + } + return 'lookup.' + code; +} + + +export const lookupDataSourceConverter = { + convertFrom: (schema: Record, propertyKey: string) => { + return schema.editor[propertyKey]?.displayName; + }, + convertTo: (schema: Record, propertyKey: string, propertyValue: any[]) => { + if (propertyValue && propertyValue.length > 0) { + const datasource = propertyValue[0]; + const { name, id, metadataContent, code } = datasource; + + if (!schema.editor.dataSource) { + schema.editor.dataSource = {}; + } + + schema.editor.dataSource.displayName = `${name}(${code})`; + schema.editor['helpId'] = id; + + const { displayType, idField, textField } = metadataContent; + schema.editor.displayType = displayType; + schema.editor.dataSource.idField = idField; + schema.editor.textField = textField; + schema.editor.dataSource.type = "ViewObject"; + + + const { pageInfo, treeInfo } = metadataContent.dataSource; + // setPageInfo(schema.editor, pageInfo); + + if (treeInfo) { + const { onlySelectLeaf, loadDataType } = treeInfo; + schema.editor.loadTreeDataType = loadDataType || 'default'; + schema.editor.onlySelectLeaf = onlySelectLeaf == null ? false: onlySelectLeaf; + } + + if (!schema.editor.dataSource.uri) { + schema.editor.dataSource.uri = generateSourceUri(schema.id); + } + } + } +}; + +export const lookupIdFieldConverter = { + convertFrom: (schema: Record, propertyKey: string) => { + return schema.editor.dataSource?.idField; + }, + convertTo: (schema: Record, propertyKey: string, propertyValue: any) => { + if (propertyValue && propertyValue.length > 0) { + const fieldInfo = propertyValue[0]; + schema.editor.dataSource.idField = fieldInfo?.bindingPath; + } + } +}; + +export const lookupTextFieldConverter = { + convertFrom: (schema: Record, propertyKey: string) => { + return schema.editor?.textField; + }, + convertTo: (schema: Record, propertyKey: string, propertyValue: any) => { + if (propertyValue && propertyValue.length > 0) { + const fieldInfo = propertyValue[0]; + schema.editor.textField = fieldInfo?.bindingPath; + } + } +}; + +export const lookupDisplayTypeConverter = { + convertFrom: (schema: Record, propertyKey: string) => { + return schema.editor.displayType ? schema.editor.displayType.toUpperCase() : 'LIST'; + }, + convertTo: (schema: Record, propertyKey: string, propertyValue: any) => { + schema.editor.displayType = propertyValue; + } +}; + +export const lookupDialogOptionsConverter = { + convertFrom: (schema: Record, propertyKey: string) => { + const options = schema.editor.dialog || {}; + if (propertyKey === 'title') { + return options[propertyKey] || ''; + } + + if (propertyKey === 'width') { + if (schema.editor.displayType?.toUpperCase().startsWith('NAV')) { + return options[propertyKey] || 960; + } + return options[propertyKey] || 590; + } + + if (propertyKey === 'height') { + return options[propertyKey] || 620; + } + + if (propertyKey === 'rememberSize') { + return options[propertyKey] === undefined ? !!schema.editor.enableUserData : options[propertyKey]; + } + + if (propertyKey === 'navigatorWidth') { + return options[propertyKey] || 300; + } + + const keys = ['showMaxButton', 'showCloseButton', 'resizeable', 'draggable', 'enableEsc']; + if (keys.includes(propertyKey)) { + return options[propertyKey] == null ? true : options[propertyKey]; + } + + }, + convertTo: (schema: Record, propertyKey: string, propertyValue: any) => { + schema.editor.dialog = schema.editor.dialog || {}; + schema.editor.dialog[propertyKey] = propertyValue; + } +}; + diff --git a/packages/mobile-ui-vue/components/lookup/src/property-config/lookup.property-config.ts b/packages/mobile-ui-vue/components/lookup/src/property-config/lookup.property-config.ts new file mode 100644 index 0000000000000000000000000000000000000000..5600972331da7ee86a4bc0b094a71c215740b80f --- /dev/null +++ b/packages/mobile-ui-vue/components/lookup/src/property-config/lookup.property-config.ts @@ -0,0 +1,219 @@ +import { InputBaseProperty } from '@farris/mobile-ui-vue/common'; +import { lookupDataSourceConverter, lookupTextFieldConverter } from './converters/lookup-property.converter'; + +export const LookupSchemaRepositoryToken = Symbol('schema_repository_token'); + +export const FieldSelectorRepositoryToken = Symbol('Field_Selector Component Repository Service Token'); + +export class LookupProperty extends InputBaseProperty { + constructor(componentId: string, designerHostService: any) { + super(componentId, designerHostService); + } + + getEditorProperties(propertyData: any) { + const self = this; + + const editorOptions = propertyData.editor; + + const editorProperties = self.getComponentConfig( + propertyData, + { type: 'lookup' }, + { + dataSource: { + description: "数据源", + title: "数据源", + type: "string", + refreshPanelAfterChanged: true, + editor: { + type: "schema-selector", + title: "选择数据源", + editorParams: { + propertyData: editorOptions, + formBasicInfo: this.formSchemaUtils.getFormMetadataBasicInfo() + }, + displayFormatter: (items) => { + if (items && items.length) { + return items.map((item) => `${item['name']}(${item['code']})`).join(','); + } + return ''; + }, + viewOptions: [ + { + id: 'recommend', title: '推荐', type: 'List', + dataSource: 'Recommand', + enableGroup: true, + groupField: 'category', + groupFormatter: (value, data) => { + return `${value === 'local' ? '本地元数据' : '最近使用'}`; + } + }, + { id: 'total', title: '全部', type: 'List', dataSource: 'Total' } + ], + repositoryToken: LookupSchemaRepositoryToken, + onSubmitModal: (dataSourceSchema: any) => { + if (dataSourceSchema) { + delete editorOptions.mappingFields; + const formInfo = this.formSchemaUtils.getFormMetadataBasicInfo(); + // 获取数据源详细配置信息 + return this.metadataService.getPickMetadata(formInfo.relativePath, dataSourceSchema[0].data) + .then((res: any) => { + const metadata = JSON.parse(res?.metadata.content); + return metadata; + }); + } + } + }, + $converter: lookupDataSourceConverter + }, + displayType: { + description: "类型: 树列表、列表、双列表、左树右列表", + title: "展示类型", + type: "string", + editor: { + type: "combo-list", + disabled: true, + data: [ + { text: '列表', value: 'List' }, + { text: '树列表', value: 'TreeList' }, + { text: '左树右列表', value: 'NavTreeList' } + ], + textField: 'text', + valueField: 'value' + } + }, + idField: { + description: "数据源标识字段", + title: "标识字段", + type: "string", + visible: false + }, + textField: { + description: "显示文本字段", + title: "文本字段", + type: "string", + $converter: lookupTextFieldConverter, + editor: { + type: "field-selector", + textField: 'bindingPath', + idField: 'bindingPath', + editorParams: { + propertyData: editorOptions, + formBasicInfo: this.formSchemaUtils.getFormMetadataBasicInfo() + }, + columns: [ + { field: 'name', title: '名称' }, + { field: 'code', title: '编号' }, + { field: 'bindingPath', title: '绑定字段' }, + ], + repositoryToken: FieldSelectorRepositoryToken + } + }, + mappingFields: { + description: "字段映射", + title: "字段映射", + type: "string", + editor: { + type: "mapping-editor", + modalWidth: 800, + modalHeight: 600, + editable: false, + editorParams: { + propertyData: editorOptions, + formBasicInfo: this.formSchemaUtils.getFormMetadataBasicInfo() + }, + fromData: { + editable: false, + formatter: (cell, data) => { + return `${data.raw['name']} [${data.raw['bindingPath']}]`; + }, + idField: 'id', + textField: 'bindingPath', + valueField: 'bindingPath', + repositoryToken: FieldSelectorRepositoryToken + }, + toData: { + idField: 'id', + textField: 'bindingPath', + valueField: 'bindingPath', + dataSource: this.designViewModelUtils.getAllFields2TreeByVMId(this.viewModelId), + formatter: (cell, data) => { + return `${data.raw['name']} [${data.raw['bindingPath']}]`; + } + } + } + }, + multiSelect: { + description: "启用多选", + title: "启用多选", + type: "boolean", + editor: { + type: 'combo-list', + enableClear: false, + editable: false + }, + refreshPanelAfterChanged: true, + visible: this.isSimpleStringField() + }, + loadTreeDataType: { + description: "树形数据加载方式", + title: "数据加载方式", + type: "string", + editor: { + type: 'combo-list', + editable: false, + data: [ + { value: 'all', text: '全部加载' }, + { value: 'async', text: '分层加载' }, + { value: 'default', text: '默认' } + ], + textField: 'text', + valueField: 'value' + }, + visible: this.showLoadType(editorOptions) + }, + onlySelectLeaf: { + description: "仅选择叶子节点", + title: "仅选择叶子节点", + type: "boolean", + visible: this.showOnlySelectLeaf(editorOptions), + } + }, + (changeObject) => { + if (!changeObject) { + return; + } + switch (changeObject.propertyID) { + case 'data': { + break; + } + } + } + ); + return editorProperties; + } + + private isSimpleStringField() { + const fullPath = this.designViewModelField?.path || ''; + if (fullPath) { + const field = fullPath.indexOf('.') > -1 ? fullPath.split('.')[0] : fullPath; + const fields = this.designViewModelUtils.getAllFields2TreeByVMId(this.viewModelId); + if (fields && fields.length) { + const fieldInfo = fields.map(node => node.data).find(data => data.code === field); + return fieldInfo?.type?.$type === "StringType" && fieldInfo?.$type === 'SimpleField'; + } + return false; + } + return true; + } + + private getDisplayType(editorOptions: any) { + return editorOptions.displayType ? editorOptions.displayType.toUpperCase() : ''; + } + private showLoadType(editorOptions: any) { + const displayType = this.getDisplayType(editorOptions); + return (displayType === 'TREELIST' || displayType === 'NAVTREELIST'); + } + private showOnlySelectLeaf(editorOptions: any) { + return this.getDisplayType(editorOptions) === 'TREELIST'; + } +} diff --git a/packages/mobile-ui-vue/components/lookup/src/schema/lookup.schema.json b/packages/mobile-ui-vue/components/lookup/src/schema/lookup.schema.json new file mode 100644 index 0000000000000000000000000000000000000000..853b9375ff147fb55512fe22e45422998551e3d1 --- /dev/null +++ b/packages/mobile-ui-vue/components/lookup/src/schema/lookup.schema.json @@ -0,0 +1,120 @@ +{ + "$schema": "https://json-schema.org/draft/2020-12/schema", + "$id": "https://farris-design.gitee.io/lookup.schema.json", + "title": "lookup", + "description": "A Farris Lookup Component", + "type": "object", + "properties": { + "id": { + "description": "标识", + "type": "string" + }, + "type": { + "description": "控件类型", + "type": "string", + "default": "lookup" + }, + "appearance": { + "description": "外观", + "type": "object", + "properties": { + "class": { + "type": "string" + }, + "style": { + "type": "string" + } + }, + "default": {} + }, + "binding": { + "description": "绑定", + "type": "object", + "default": {} + }, + "required": { + "description": "必填", + "type": "boolean", + "default": false + }, + "readonly": { + "description": "只读", + "type": "boolean", + "default": false + }, + "disabled": { + "description": "禁用", + "type": "boolean", + "default": false + }, + "enableClear": { + "description": "", + "type": "boolean", + "default": false + }, + "placeholder": { + "description": "提示文本", + "type": "string" + }, + "displayType": { + "description": "", + "type": "string" + }, + "title": { + "description": "标题", + "type": "string", + "default": "" + }, + "idField": { + "description": "值字段", + "type": "string", + "default": "value" + }, + "textField": { + "description": "显示字段", + "type": "string", + "default": "name" + }, + "mappingFields": { + "description": "帮助字段映射", + "type": "object", + "default": {} + }, + "uri": { + "type": "string", + "default": "" + }, + "dataSource": { + "type": "object", + "default": null + }, + "multiSelect": { + "type": "boolean", + "default": false + }, + "loadTreeDataType": { + "type": "string", + "default": "default" + }, + "onlySelectLeaf": { + "type": "boolean", + "default": false + }, + "onUpdate:modelValue": { + "description": "值更新事件", + "type": "string" + } + }, + "events": [ + "onUpdate:modelValue" + ], + "required": [ + "type" + ], + "ignore": [ + "id", + "appearance", + "binding", + "visible" + ] +} \ No newline at end of file diff --git a/packages/mobile-ui-vue/components/lookup/src/schema/schema-mapper.ts b/packages/mobile-ui-vue/components/lookup/src/schema/schema-mapper.ts new file mode 100644 index 0000000000000000000000000000000000000000..cbdfe5f71e069cffc320648d9a96ca06bddffda2 --- /dev/null +++ b/packages/mobile-ui-vue/components/lookup/src/schema/schema-mapper.ts @@ -0,0 +1,35 @@ +import { MapperFunction, resolveAppearance } from '@farris/mobile-ui-vue/dynamic-resolver'; + +function converMappingFieldsToObject(mappingFields: any) { + if (typeof mappingFields == 'string' && mappingFields.startsWith('{') && mappingFields.endsWith('}')) { + mappingFields = mappingFields.replace(/'/g, '"'); + return {mappingFields: JSON.parse(mappingFields)}; + } + + return {mappingFields}; +} + +export const schemaMapper = new Map([ + ['appearance', resolveAppearance], + ['binding', 'modelValue'], + ['mappingFields', (key: string, value: any, resolvedSchema) => { + if (value) { + return converMappingFieldsToObject(value); + } + + const {mappingFields} = resolvedSchema; + return converMappingFieldsToObject(mappingFields); + }], + ['uri', (key: string, value: any, resolvedSchema) => { + if (value) { + return {uri: value}; + } + return {uri: resolvedSchema?.dataSource?.uri}; + }], + ['idField', (key: string, value: any, resolvedSchema) => { + if (value) { + return {idField: value}; + } + return {idField: resolvedSchema?.dataSource?.idField}; + }] +]); diff --git a/packages/mobile-ui-vue/components/lookup/src/schema/schema-resolver.ts b/packages/mobile-ui-vue/components/lookup/src/schema/schema-resolver.ts new file mode 100644 index 0000000000000000000000000000000000000000..7c8af7fc63d68147438fc329e74ebce565df4ef7 --- /dev/null +++ b/packages/mobile-ui-vue/components/lookup/src/schema/schema-resolver.ts @@ -0,0 +1,5 @@ +import { DynamicResolver } from "@farris/mobile-ui-vue/dynamic-resolver"; + +export function schemaResolver(resolver: DynamicResolver, schema: Record, context: Record): Record { + return schema; +} diff --git a/packages/mobile-ui-vue/components/modal/index.ts b/packages/mobile-ui-vue/components/modal/index.ts deleted file mode 100644 index ad48a036b87ac274deddb96ce85ae9ffe6236e95..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/index.ts +++ /dev/null @@ -1,32 +0,0 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -import type { App, Plugin } from 'vue'; -import FModal from './src/modal.component'; -import FModalService from './src/composition/modal.service'; - -export * from './src/modal.props'; - -export const FM_MODAL_SERVICE_TOKEN = Symbol('FModalService'); - -FModal.install = (app: App) => { - app.component(FModal.name as string, FModal); - const modalInstance = new FModalService(app); - app.provide(FM_MODAL_SERVICE_TOKEN, modalInstance); - app.provide('FModalService', modalInstance); -}; - -export { FModal, FModalService }; -export default FModal as typeof FModal & Plugin; diff --git a/packages/mobile-ui-vue/components/modal/src/components/modal-context-holder.component.tsx b/packages/mobile-ui-vue/components/modal/src/components/modal-context-holder.component.tsx deleted file mode 100644 index 4f24d447152ff44f9dd2a7accbb98fc81fa279d4..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/src/components/modal-context-holder.component.tsx +++ /dev/null @@ -1,23 +0,0 @@ -import { defineComponent, SetupContext, shallowRef, VNode } from "vue"; - -export interface ContextHolder { - addModal: (modal: () => VNode) => () => void; -} -export default defineComponent({ - name: 'FModalContextHolder', - setup(props: any, context: SetupContext) { - const modals = shallowRef<(() => VNode)[]>([]); - const addModal = (modal: () => VNode) => { - modals.value.push(modal); - modals.value = modals.value.slice(); - return () => { - // 删除当前模态框 - modals.value = modals.value.filter(currentModal => currentModal !== modal); - }; - }; - context.expose({ addModal }); - return () => { - return modals.value.map(modal => modal()); - }; - } -}); diff --git a/packages/mobile-ui-vue/components/modal/src/composition/destroy.ts b/packages/mobile-ui-vue/components/modal/src/composition/destroy.ts deleted file mode 100644 index e68523fb9e051802488672d432b5cf8554e952c0..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/src/composition/destroy.ts +++ /dev/null @@ -1 +0,0 @@ -export const destroyFunctionList: any[] = []; diff --git a/packages/mobile-ui-vue/components/modal/src/composition/modal.service.tsx b/packages/mobile-ui-vue/components/modal/src/composition/modal.service.tsx deleted file mode 100644 index ff8a7dc10cf9a99b557d3814e769b5b467ac6435..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/src/composition/modal.service.tsx +++ /dev/null @@ -1,263 +0,0 @@ -import { ref, h, render, VNode, cloneVNode, shallowRef, nextTick, App, AppContext, createApp, onUnmounted, onMounted, computed } from "vue"; -import { ModalFunctions, ModalOptions } from "./type"; -import FModal from '../modal.component'; -// import FarrisPlugin from '../../../plugin'; - -function getContentRender(props: ModalOptions) { - if (props.content && props.content.render) { - return props.content.render; - } - if (props.render && typeof props.render === 'function') { - return props.render; - } -} - -function createModalInstance(options: ModalOptions) { - const container = document.createElement('div'); - container.style.display = 'contents'; - - const app: App = createApp({ - setup(props, context) { - - onUnmounted(() => { - document.body.removeChild(container); - }); - - const modalRef = ref(); - - const customClass = ref(options.class || ''); - const showButtons = ref(!!options.showButtons); - const showHeader = ref(!!options.showHeader); - const showCloseButton = ref(options.showCloseButton == null ? true : options.showCloseButton); - const showModal = ref(true); - const modalTitle = ref(options.title || ''); - const acceptCallback = options.acceptCallback || (() => { }); - const rejectCallback = options.rejectCallback || (() => { }); - - const modalClosedCallback = options.closedCallback || (($event: Event) => { }); - const modalResizedCallback = options.resizeHandle || (($event: Event) => { }); - - const contentRender = getContentRender(options); - - const onClosed = ($event: Event) => { - showModal.value = false; - app.unmount(); - modalClosedCallback($event); - }; - - onMounted(() => { - // console.log(modalRef); - }); - - context.expose({ - modalRef - }); - - return () => ( - - {contentRender && contentRender(app)} - - ); - } - }); - document.body.appendChild(container); - // if (FarrisPlugin && !!FarrisPlugin.install) { - // app.use(FarrisPlugin); - // } - - app.mount(container); - - return app; -} - -export default class ModalService { - private appContext: AppContext | null = null; - - private modalRef = ref(); - - private activeModalIndex = ref(0); - - private modalRefs: Record = {}; - - private isUseEscCloseModal = ref(false); - - private activeModalInstance = computed(() => { - return this.modalRefs[this.activeModalIndex.value]; - }); - - private app: App; - - constructor(currentApp: App) { - this.app = currentApp; - this.appContext = currentApp ? currentApp._context : null; - } - - getCurrentModal() { - return this.activeModalInstance.value; - } - - private adaptToWindow(width: number, height: number) { - // 可视区域尺寸 - const { width: winWidth, height: winHeight } = { - width: window.innerWidth, - height: window.innerHeight - }; - - if (winWidth < width) { - width = winWidth; - } - - if (winHeight < height) { - height = winHeight; - } - - return { - width, - height - }; - } - - static show(options: ModalOptions) { - const modalOptions = Object.assign({ - title: '', - showButtons: true, - showHeader: true - }, options); - const app: App = createModalInstance(modalOptions); - return app; - } - - open(options: ModalOptions): ModalFunctions { - // 创建一个空白文档作为模态框容器,空白文档不属于DOM树,比创建一般节点性能较好,且仅渲染子元素 - const container = document.createDocumentFragment(); - - if (options.showMaxButton && options.fitContent) { - options.showMaxButton = false; - } - - const modalOptions = shallowRef(Object.assign({ - title: '', - showButtons: true, - showHeader: true, - }, options)); - - const showModal = ref(true); - const acceptCallback = modalOptions.value.acceptCallback || (() => { }); - const rejectCallback = modalOptions.value.rejectCallback || (() => { }); - - const modalClosedCallback = modalOptions.value.closedCallback || (($event?: Event, from?: string) => { }); - const modalResizedCallback = modalOptions.value.resizeHandle || (($event: Event) => { }); - let modalInstance: VNode | null; - - const contentRender = getContentRender(modalOptions.value); - - const onClosed = ($event?: Event) => { - showModal.value = false; - - const isCloseIconClick = ($event?.target as any)?.classList.contains('modal_close'); - - modalClosedCallback($event, this.isUseEscCloseModal.value ? 'esc' : isCloseIconClick ? 'icon' : 'button'); - - }; - - const destroy = ($event?: Event) => { - onClosed($event); - if (modalInstance) { - nextTick(() => { - if (this.modalRefs[this.activeModalIndex.value]) { - delete this.modalRefs[this.activeModalIndex.value]; - } - render(null, container as any); - modalInstance = null; - this.modalRef.value = null; - - if (this.modalRefs) { - const modals = Object.keys(this.modalRefs).map((key: string) => Number(key)); - if (modals.length > 0) { - this.activeModalIndex.value = Math.max(...modals); - } else { - this.activeModalIndex.value = 0; - } - } - - this.isUseEscCloseModal.value = false; - }); - } - - }; - - const onEsc = (payload: any) => { - this.isUseEscCloseModal.value = true; - this.activeModalInstance && this.activeModalInstance.value?.close(payload?.event); - }; - - const { width: modalWidth, height: modalHeight } = modalOptions.value; - const adaptedSize = this.adaptToWindow(modalWidth || 500, modalHeight || 320); - Object.assign(modalOptions.value, adaptedSize); - - const ModalWrapper = () => ( - - {contentRender && contentRender(this.app)} - - ); - - const renderModal = (props: Partial): VNode => { - const vnode = h(ModalWrapper, props); - vnode.appContext = this.appContext; - // if (FarrisPlugin && !!FarrisPlugin.install) { - // vnode.appContext?.app.use(FarrisPlugin); - // } - render(vnode, container as any); - return vnode; - }; - modalInstance = renderModal( - { - ...modalOptions.value, - // 'onUpdate:modelValue': onUpdateModelValue, - } - ); - - this.activeModalIndex.value++; - this.modalRefs[this.activeModalIndex.value] = this.modalRef.value; - - const update = (updateConfig: ModalOptions) => { - modalOptions.value = { - ...modalOptions.value, - ...updateConfig - }; - if (modalInstance) { - render(cloneVNode(modalInstance, { ...modalOptions }), container as any); - } - }; - - return { - update, - destroy, - modalRef: this.activeModalInstance - }; - } -} diff --git a/packages/mobile-ui-vue/components/modal/src/composition/resizeable/position.ts b/packages/mobile-ui-vue/components/modal/src/composition/resizeable/position.ts deleted file mode 100644 index 8aa65d4a5cd4b6cef9b9e09f51fa9b5cd6bfc658..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/src/composition/resizeable/position.ts +++ /dev/null @@ -1,104 +0,0 @@ -export interface IPosition { - x: number; - y: number; -} - -export class Position implements IPosition { - constructor(public x: number, public y: number) { } - - static getTransformInfo(target: Element) { - const styleInfo = window.getComputedStyle(target); - const transforms = styleInfo.getPropertyValue('transform').replace(/[^-\d,]/g, '').split(','); - if (transforms.length >= 6) { - const translateX = parseInt(transforms[4], 10); - const translateY = parseInt(transforms[5], 10); - return {x: translateX, y: translateY }; - } - - return {x: 0, y: 0 }; - } - - static fromEvent(e: MouseEvent | TouchEvent, el: any = null) { - - if (this.isMouseEvent(e)) { - return new Position(e.clientX, e.clientY); - } - - if (el === null || e.changedTouches.length === 1) { - return new Position(e.changedTouches[0].clientX, e.changedTouches[0].clientY); - } - - for (let i = 0; i < e.changedTouches.length; i++) { - if (e.changedTouches[i].target === el) { - return new Position(e.changedTouches[i].clientX, e.changedTouches[i].clientY); - } - } - } - - static isMouseEvent(e: MouseEvent | TouchEvent): e is MouseEvent { - return Object.prototype.toString.apply(e).indexOf('MouseEvent') === 8; - } - - static isIPosition(obj): obj is IPosition { - return !!obj && ('x' in obj) && ('y' in obj); - } - - static getCurrent(el: Element) { - const pos = new Position(0, 0); - - if (window) { - const computed = window.getComputedStyle(el); - if (computed) { - const x = parseInt(computed.getPropertyValue('left'), 10); - const y = parseInt(computed.getPropertyValue('top'), 10); - pos.x = isNaN(x) ? 0 : x; - pos.y = isNaN(y) ? 0 : y; - } - return pos; - } - - return null; - } - - static copy(p: IPosition) { - return new Position(0, 0).set(p); - } - - get value(): IPosition { - return { x: this.x, y: this.y }; - } - - add(p: IPosition) { - this.x += p.x; - this.y += p.y; - return this; - } - - subtract(p: IPosition) { - this.x -= p.x; - this.y -= p.y; - return this; - } - - multiply(n: number) { - this.x *= n; - this.y *= n; - } - - divide(n: number) { - this.x /= n; - this.y /= n; - } - - reset() { - this.x = 0; - this.y = 0; - return this; - } - - set(p: IPosition) { - this.x = p.x; - this.y = p.y; - return this; - } -} diff --git a/packages/mobile-ui-vue/components/modal/src/composition/resizeable/resize-event.ts b/packages/mobile-ui-vue/components/modal/src/composition/resizeable/resize-event.ts deleted file mode 100644 index 6f3828a241b8f14aabb28ea63a2828b280dc9959..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/src/composition/resizeable/resize-event.ts +++ /dev/null @@ -1,11 +0,0 @@ -export interface IResizeEvent { - size: { - width?: number; - height?: number; - }; - position: { - x?: number; - y?: number; - }; - transform?: string; -} diff --git a/packages/mobile-ui-vue/components/modal/src/composition/resizeable/size.ts b/packages/mobile-ui-vue/components/modal/src/composition/resizeable/size.ts deleted file mode 100644 index 10f028b9fabd2aa8b9264dece948c0c8679e54ca..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/src/composition/resizeable/size.ts +++ /dev/null @@ -1,33 +0,0 @@ -export interface ISize { - width: number; - height: number; -} - -export class Size implements ISize { - constructor(public width: number, public height: number) {} - - static getCurrent(el: Element) { - const size = new Size(0, 0); - - if (window) { - const computed = window.getComputedStyle(el); - if (computed) { - size.width = parseInt(computed.getPropertyValue('width'), 10); - size.height = parseInt(computed.getPropertyValue('height'), 10); - } - return size; - } - - return null; - } - - static copy(s: Size) { - return new Size(0, 0).set(s); - } - - set(s: ISize) { - this.width = s.width; - this.height = s.height; - return this; - } -} diff --git a/packages/mobile-ui-vue/components/modal/src/composition/type.ts b/packages/mobile-ui-vue/components/modal/src/composition/type.ts deleted file mode 100644 index e39156ec691e10ca43277acca8e54bb1c7d91f8d..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/src/composition/type.ts +++ /dev/null @@ -1,49 +0,0 @@ -import { App, VNode } from "vue"; -import { JSX } from "vue/jsx-runtime"; -import { IResizeEvent } from "./resizeable/resize-event"; - -/** 自定义按钮结构 */ -export interface ModalButton { - name?: string; - class: string; - focusedByDefault?: boolean; - disable?: boolean; - iconClass?: string; - handle: ($event: MouseEvent, context: any) => any; - text: string; -} - -export interface ModalOptions { - class?: string; - title?: string; - width?: number; - height?: number; - minWidth?: number; - minHeight?: number; - showButtons?: boolean; - showHeader?: boolean; - showFloatingClose?: boolean; - content?: { render(): JSX.Element }; - render?: (app: App) => JSX.Element; - fitContent?: boolean; - buttons?: ModalButton[]; - draggable?: boolean; - showMaxButton?: boolean; - showCloseButton?: boolean; - acceptCallback?: () => void; - rejectCallback?: () => void; - closedCallback?: ($event?: Event, from?: 'esc' | 'icon' | 'button') => void; - resizeHandle?: (event: IResizeEvent) => void; - enableEsc?: boolean; -} - -export interface ModalFunctions { - update: (options: ModalOptions) => void; - destroy: () => void; - modalRef: any; -} - -export interface UseModal { - FModalContextHolder: () => VNode; - -} diff --git a/packages/mobile-ui-vue/components/modal/src/composition/use-draggable.ts b/packages/mobile-ui-vue/components/modal/src/composition/use-draggable.ts deleted file mode 100644 index 2a239d952c9d283574f033124f7768571db7710b..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/src/composition/use-draggable.ts +++ /dev/null @@ -1,222 +0,0 @@ -import { Ref, ref, watch } from "vue"; -import { Position } from "./resizeable/position"; - -export function useDraggable(props: any, context: any, canMove: Ref) { - - const dragTarget = ref(); - const allowDrag = ref(props.draggable); - const lockAxis = ref(props.lockAxis); - - const dragHandle = ref(); - const boundingElement = ref(); - const moving = ref(false); - - const origPos = ref(new Position(0, 0)); - const oldTranslate = ref(new Position(0, 0)); - const movingPos= ref(new Position(0, 0)); - const currentPos= ref(new Position(0, 0)); - - watch(() => canMove.value, (move) => { - dragHandle.value.style.cursor = move ? 'move' : 'default'; - }); - - function checkHandleTarget(target: EventTarget, element: Element) { - // Checks if the target is the element clicked, then checks each child element of element as well - // Ignores button clicks - - // Ignore elements of type button - if (element.tagName === 'BUTTON') { - return false; - } - - // If the target was found, return true (handle was found) - if (element === target) { - return true; - } - - // Recursively iterate this elements children - - for (const child in element.children) { - if (Object.prototype.hasOwnProperty.call(element.children, child)) { - if (checkHandleTarget(target, element.children[child])) { - return true; - } - } - } - - // Handle was not found in this lineage - // Note: return false is ignore unless it is the parent element - return false; - } - - function transform() { - let translateX = movingPos.value.x + oldTranslate.value.x; - let translateY = movingPos.value.y + oldTranslate.value.y; - - if (lockAxis.value === 'x') { - translateX = origPos.value?.x || 0; - movingPos.value.x = 0; - } else if (lockAxis.value === 'y') { - translateY = origPos.value?.y || 0; - movingPos.value.y = 0; - } - - const value = `translate3d(${Math.round(translateX)}px, ${Math.round(translateY)}px, 0px)`; - if (dragTarget.value) { - dragTarget.value.style.transform = value; - } - - // save current position - currentPos.value.x = translateX; - currentPos.value.y = translateY; - } - - function checkBounds(){ - if(!boundingElement.value || !dragTarget.value){ return null; } - const boundary = boundingElement.value.getBoundingClientRect(); - const targetRect = dragTarget.value.getBoundingClientRect(); - const result = { - 'top': boundary.top < targetRect.top, - 'right': boundary.right > targetRect.right, - 'bottom': boundary.bottom > targetRect.bottom, - 'left': boundary.left < targetRect.left - }; - - if (!result.top) { - movingPos.value.y -= targetRect.top - boundary.top; - } - - if (!result.bottom) { - movingPos.value.y -= targetRect.bottom - boundary.bottom; - } - - if (!result.right) { - movingPos.value.x -= targetRect.right - boundary.right; - } - - if (!result.left) { - movingPos.value.x -= targetRect.left - boundary.left; - } - - transform(); - return result; - } - - function moveTo(p?: Position) { - if (p) { - if (origPos.value) { - p.subtract(origPos.value); - } - - movingPos.value.set(p); - transform(); - checkBounds(); - } - } - - function onMouseMove(event: MouseEvent) { - if (moving.value && allowDrag.value) { - event.stopPropagation(); - event.preventDefault(); - - // Add a transparent helper div: - // helperBlock.add(); - moveTo(Position.fromEvent(event, dragHandle.value)); - } - } - - function stopMove() { - if (moving.value) { - - moving.value = false; - - oldTranslate.value.add(movingPos.value); - movingPos.value.reset(); - - dragTarget.value?.classList.remove('ng-dragging'); - - document.removeEventListener('mousemove', onMouseMove); - document.removeEventListener('mouseup', stopMove); - } - } - - function startMove() { - if (!moving.value && dragHandle.value) { - moving.value = true; - dragHandle.value.classList.add('ng-dragging'); - - document.addEventListener('mousemove', onMouseMove); - document.addEventListener('mouseup', stopMove); - } - } - - function resetTranslate() { - if (dragTarget.value) { - const pos = Position.getTransformInfo(dragTarget.value); - oldTranslate.value.set(pos); - return; - } - - oldTranslate.value.reset(); - } - - function onMouseDown(event: MouseEvent) { - if (!canMove.value) { - return; - } - // 1. skip right click; - if (event instanceof MouseEvent && event.button === 2) { - return; - } - // 2. if handle is set, the element can only be moved by handle - const target = event.target || event.srcElement; - if (dragHandle.value !== undefined && target && !checkHandleTarget(target, dragHandle.value)) { - return; - } - - // 3. if allow drag is set to false, ignore the mousedown - if (allowDrag.value === false) { - return; - } - - // 隐藏其他浮动层 - document.body.click(); - - event.stopPropagation(); - event.preventDefault(); - - origPos.value = Position.fromEvent(event, dragTarget.value); - resetTranslate(); - startMove(); - } - - function registerDraggle(handle: HTMLElement, hostElement: HTMLElement, boundingHost: HTMLElement | null) { - if (allowDrag.value && hostElement) { - if (handle) { - dragHandle.value = handle; - } else if (props.dragHandle) { - if (props.dragHandle instanceof HTMLElement) { - dragHandle.value = props.dragHandle; - } else if (typeof props.dragHandle === 'string') { - const element = hostElement.querySelector(props.dragHandle); - if(element) { - dragHandle.value = element as HTMLElement; - } - } - } - - dragTarget.value = hostElement; - boundingElement.value = boundingHost; - if (dragHandle.value) { - dragHandle.value.classList.add('ng-draggable'); - dragHandle.value.addEventListener('mousedown', onMouseDown); - } else { - allowDrag.value = false; - } - } - } - - return { - registerDraggle, resetTranslate - }; -} diff --git a/packages/mobile-ui-vue/components/modal/src/composition/use-resizeable.tsx b/packages/mobile-ui-vue/components/modal/src/composition/use-resizeable.tsx deleted file mode 100644 index e23782f59266e655aa21db2e46ffb8e28938173c..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/src/composition/use-resizeable.tsx +++ /dev/null @@ -1,390 +0,0 @@ -import { ref } from "vue"; -import { Position } from "./resizeable/position"; -import { Size } from "./resizeable/size"; -import { IResizeEvent } from "./resizeable/resize-event"; - -export function useResizeable(props: any, context: any) { - - const resizedTarget = ref(); - const boundingElement = ref(); - - const origMousePos = ref(); - const origSize = ref(); - const origPos = ref(); - const currSize = ref(); - const currPos = ref(); - const direction = ref<{ 'n': boolean; 's': boolean; 'w': boolean; 'e': boolean } | null>(); - const resizeHandlerElement = ref(); - const modalBounding = ref(); - const resizedEventParam = ref(); - - const lastSize = ref(); - - const allowDrag = ref(props.draggable); - - const isMaximized = ref(false); - - function initBounding() { - const el = boundingElement.value || document.body; - const computed = window.getComputedStyle(el); - if(!computed){ - return; - } - - if (!resizedTarget.value) { - return; - } - - const transforms = Position.getTransformInfo(resizedTarget.value); - - - const bounding: any = {}; - - if (currPos.value) { - bounding.deltaL = resizedTarget.value.offsetLeft - currPos.value.x; - bounding.deltaT = resizedTarget.value.offsetTop - currPos.value.y; - } - - const p = computed.getPropertyValue('position'); - bounding.width = el.clientWidth; - bounding.height = el.clientHeight; - bounding.pr = parseInt(computed.getPropertyValue('padding-right'), 10); - bounding.pb = parseInt(computed.getPropertyValue('padding-bottom'), 10); - bounding.position = computed.getPropertyValue('position'); - - if (p === 'static') { - el.style.position = 'relative'; - } - - bounding.translateX = transforms.x; - bounding.translateY = transforms.y; - - modalBounding.value = bounding; - } - - function startResize(event: MouseEvent) { - - if (resizedTarget.value) { - origSize.value = Size.getCurrent(resizedTarget.value); - origPos.value = Position.getCurrent(resizedTarget.value); - currSize.value = origSize.value ? Size.copy(origSize.value) : null; - currPos.value = origPos.value ? Position.copy(origPos.value) : null; - - initBounding(); - - const directionType = (event.target as HTMLElement).getAttribute('type') || ''; - direction.value = { - n: !!directionType.match(/n/), - s: !!directionType.match(/s/), - w: !!directionType.match(/w/), - e: !!directionType.match(/e/) - }; - - } - } - - function doResize() { - if (resizedTarget.value) { - const container = resizedTarget.value as HTMLElement; - if (direction.value) { - if ((direction.value.n || direction.value.s) && currSize.value?.height) { - container.style.height = currSize.value.height + 'px'; - } - if ((direction.value.w || direction.value.e) && currSize.value?.width) { - container.style.width = currSize.value.width + 'px'; - } - - if (currPos.value) { - if (currPos.value?.x) { - container.style.left = currPos.value.x + 'px'; - } - if (currPos.value?.y) { - container.style.top = currPos.value.y + 'px'; - } - } - } - } - } - - function checkSize() { - - const minHeight = !props.minHeight ? 1 : props.minHeight; - const minWidth = !props.minWidth ? 1 : props.minWidth; - - if (currSize.value && currPos.value && direction.value && origSize.value) { - if (currSize.value.height < minHeight) { - currSize.value.height = minHeight; - - if (direction.value.n && origPos.value) { - currPos.value.y = origPos.value.y + (origSize.value.height - minHeight); - } - } - - if (currSize.value.width < minWidth) { - currSize.value.width = minWidth; - - if (direction.value.w && origPos.value) { - currPos.value.x = origPos.value.x + (origSize.value.width - minWidth); - } - } - - if (props.maxHeight && currSize.value.height > props.maxHeight) { - currSize.value.height = props.maxHeight; - - if (origPos.value && direction.value.n) { - currPos.value.y = origPos.value.y + (origSize.value.height - props.maxHeight); - } - } - - if (props.maxWidth && currSize.value.width > props.maxWidth) { - currSize.value.width = props.maxWidth; - - if (direction.value.w && origPos.value) { - currPos.value.x = origPos.value.x + (origSize.value.width - props.maxWidth); - } - } - } - - } - - function checkBounds(){ - if (boundingElement.value) { - const bounding = modalBounding.value; - - if (currPos.value && currSize.value && direction.value && origSize.value) { - const maxWidth = bounding.width - bounding.pr - bounding.deltaL - bounding.translateX - currPos.value.x; - const maxHeight = bounding.height - bounding.pb - bounding.deltaT - bounding.translateY - currPos.value.y; - - if (direction.value.n && (currPos.value.y + bounding.translateY < 0) && origPos.value) { - currPos.value.y = -bounding.translateY; - currSize.value.height = origSize.value.height + origPos.value.y + bounding.translateY; - } - - if (direction.value.w && (currPos.value.x + bounding.translateX) < 0 && origPos.value) { - currPos.value.x = -bounding.translateX; - currSize.value.width = origSize.value.width + origPos.value.x + bounding.translateX; - } - - if (currSize.value.width > maxWidth) { - currSize.value.width = maxWidth; - } - - if (currSize.value.height > maxHeight) { - currSize.value.height = maxHeight; - } - } - } - } - - function resizeTo(p: Position) { - - if (!origMousePos.value || !origSize.value || !origPos.value || !direction.value) { - return; - } - - p.subtract(origMousePos.value); - - const tmpX = p.x; - const tmpY = p.y; - - if (direction.value.n) { - // n, ne, nw - currPos.value!.y = origPos.value.y + tmpY; - currSize.value!.height = origSize.value.height - tmpY; - } else if (direction.value.s) { - // s, se, sw - currSize.value!.height = origSize.value.height + tmpY; - } - - if (direction.value.e) { - // e, ne, se - currSize.value!.width = origSize.value.width + tmpX; - } else if (direction.value.w) { - // w, nw, sw - currSize.value!.width = origSize.value.width - tmpX; - currPos.value!.x = origPos.value.x + tmpX; - } - - checkBounds(); - checkSize(); - doResize(); - } - - function onMouseMove(event: MouseEvent) { - if (!resizeHandlerElement.value) { - return; - } - - const pos = Position.fromEvent(event); - if (pos) { - resizeTo(pos); - } - } - - function getResizedEventParam(): IResizeEvent | null { - if (resizedTarget.value) { - const { width, height, x, y } = resizedTarget.value.getBoundingClientRect(); - const transforms = Position.getTransformInfo(resizedTarget.value); - - return { - size: { width, height }, - position: {x: x - transforms.x, y: y - transforms.y } - }; - } - return null; - } - - function onMouseLeave(event: MouseEvent) { - if (resizedTarget.value) { - const resizedParam = getResizedEventParam(); - resizedEventParam.value = resizedParam; - } - - origMousePos.value = undefined; - origSize.value = null; - origPos.value = null; - currSize.value = null; - currPos.value = null; - direction.value = null; - resizeHandlerElement.value = null; - - document.removeEventListener('mousemove', onMouseMove); - document.removeEventListener('mouseup', onMouseLeave); - } - - function registerMouseEvent() { - document.addEventListener('mousemove', onMouseMove); - document.addEventListener('mouseup', onMouseLeave); - } - - function onMouseDown(event: MouseEvent) { - // skip right click; - if (event instanceof MouseEvent && event.button === 2) { - return; - } - - if (!allowDrag.value) { - return; - } - // 隐藏其他浮动层 - document.body.click(); - // prevent default events - event.stopPropagation(); - event.preventDefault(); - - origMousePos.value = Position.fromEvent(event); - resizeHandlerElement.value = event.target; - startResize(event); - registerMouseEvent(); - } - - function renderResizeBar(hostElement: any) { - resizedTarget.value = hostElement; - return <> -
onMouseDown(e)}>
-
onMouseDown(e)}>
-
onMouseDown(e)}>
-
onMouseDown(e)}>
-
onMouseDown(e)}>
-
onMouseDown(e)}>
-
onMouseDown(e)}>
-
onMouseDown(e)}>
- ; - } - - function maximize(updateLastSize = true) { - // 隐藏其他浮动层 - document.body.click(); - - const container = boundingElement.value || document.body; - const maxSize = Size.getCurrent(container); - const target = resizedTarget.value as HTMLElement; - - if (updateLastSize && target) { - lastSize.value = getResizedEventParam(); - lastSize.value!.transform = target.style.transform; - } - - if (maxSize && target) { - currSize.value = maxSize; - - target.style.height = (currSize.value.height - 14) + 'px'; - target.style.width = (currSize.value.width - 14) + 'px'; - target.style.left = '7px'; - target.style.top = '7px'; - target.style.transform = ''; - - resizedEventParam.value = { - size: currSize.value, - position: {x: 0, y: 0} - }; - - allowDrag.value = false; - isMaximized.value = true; - } - } - - function restore() { - // 隐藏其他浮动层 - document.body.click(); - - if (lastSize.value) { - const size = { width: lastSize.value.size.width || 0, height: lastSize.value.size.height || 0 }; - const position = { x: (window.innerWidth - size.width) / 2, y: (window.innerHeight - size.height) / 2}; - - currSize.value?.set(size); - currPos.value?.set(position); - - const target = resizedTarget.value as HTMLElement; - target.style.height = size.height + 'px'; - target.style.width = size.width + 'px'; - target.style.left = `${position.x}px`; - target.style.top = `${position.y}px`; - target.style.transform = ''; - resizedEventParam.value = { - size, - position - }; - - allowDrag.value = props.draggable; - - isMaximized.value = false; - } - } - - function moveToCenter() { - if (resizedTarget.value) { - const modalSize = Size.getCurrent(resizedTarget.value); - if (modalSize) { - const { width, height } = modalSize; - resizedTarget.value.style.left = `${(window.innerWidth - width) / 2}px`; - resizedTarget.value.style.top = `${(window.innerHeight - height) / 2}px`; - resizedTarget.value.style.transform = ''; - - } - } - } - - function onWindowResize() { - const windowResizeHandle = () => { - if (isMaximized.value) { - maximize(false); - } else { - moveToCenter(); - } - // 隐藏其他浮动层 - document.body.click(); - }; - - window.addEventListener('resize', windowResizeHandle); - return () => { - window.removeEventListener('resize', windowResizeHandle); - }; - } - - const unWindowResizeHandle = onWindowResize(); - - return { - renderResizeBar, boundingElement, resizedEventParam, maximize, restore, allowDrag, isMaximized, unWindowResizeHandle - }; -} diff --git a/packages/mobile-ui-vue/components/modal/src/composition/use-shortcut.ts b/packages/mobile-ui-vue/components/modal/src/composition/use-shortcut.ts deleted file mode 100644 index 52e510aec03aad23d435c7ffad16c9fe82f99608..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/src/composition/use-shortcut.ts +++ /dev/null @@ -1,56 +0,0 @@ -import { ref } from "vue"; - - -function registrationShortcutKeyEvent(keyCode: string, callBack: (...args) => void) { - if (keyCode) { - const registerKeyDown =(event: KeyboardEvent) =>{ - if (event.key.toLowerCase() === keyCode.toLowerCase()) { - callBack({ event, key: keyCode }); - } - }; - - document.addEventListener('keydown', registerKeyDown); - - return () => { - document.removeEventListener('keydown', registerKeyDown); - }; - } - -} - -export function useEsc(props: any, context: any) { - const enableEsc = ref(props.enableEsc); - - let removeEventListener: any = null; - - if (enableEsc.value) { - removeEventListener = registrationShortcutKeyEvent('Escape', ($event: any) => { - context.emit('esc', { event: $event.event, type: 'esc' }); - }); - - return { - remove: removeEventListener - }; - } - - return null; -} - -export function useEnter(props: any, context: any) { - const enableEnter = ref(props.enableEnter); - - let removeEventListener: any = null; - - if (enableEnter.value) { - removeEventListener = registrationShortcutKeyEvent('Enter', ($event: any) => { - context.emit('enter', { event: $event.event, type: 'enter' }); - }); - - return { - remove: removeEventListener - }; - } - - return null; - -} diff --git a/packages/mobile-ui-vue/components/modal/src/modal.component.tsx b/packages/mobile-ui-vue/components/modal/src/modal.component.tsx deleted file mode 100644 index 31b1e0a72ae5afd0fcc6ed7d8ff1fe69e6150996..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/src/modal.component.tsx +++ /dev/null @@ -1,375 +0,0 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -import { computed, defineComponent, ref, SetupContext, Teleport, watch, Transition, onMounted, onUnmounted, provide, nextTick } from 'vue'; -import { ModalButton, ModalOptions } from './composition/type'; -import { ModalProps, modalProps } from './modal.props'; -import { useResizeable } from './composition/use-resizeable'; -import { useDraggable } from './composition/use-draggable'; -import './modal.css'; -import { useEnter, useEsc } from './composition/use-shortcut'; - -export default defineComponent({ - name: 'FModal', - props: modalProps, - emits: ['update:modelValue', 'accept', 'cancel', 'closed', 'resize', 'esc', 'enter'] as (string[] & ThisType) | undefined, - setup(props: ModalProps, context: SetupContext) { - const width = ref(props.width || 300); - const height = ref(props.height || 200); - const modelValue = ref(props.modelValue); - const modalId = ref(''); - const customClass = ref(props.class); - const fitContent = ref(props.fitContent); - const showHeader = ref(props.showHeader); - const headerIconClass = ref(''); - const enableClose = ref(props.showCloseButton); - const enableMaximize = ref(props.showMaxButton); - const enableMinimize = ref(false); - const dialogType = ref(''); - const iframeSrc = ref(''); - const buttonAlignment = ref(''); - const showButtons = ref(props.showButtons); - const title = ref(props.title); - const resizeable = ref(props.reiszeable); - const containment = ref(props.containment || null); - const modalContainerRef = ref(); - - - function close($event: MouseEvent, accept?: boolean) { - modelValue.value = false; - context.emit('update:modelValue', false); - if (accept != null) { - context.emit(accept ? 'accept' : 'cancel'); - } - - context.emit('closed', $event); - } - const defaultButtons: ModalButton[] = [ - { - name: 'cancel', - text: '取消', - class: 'btn btn-secondary', - handle: ($event: MouseEvent) => { - close($event, false); - } - }, - { - name: 'accept', - text: '确定', - class: 'btn btn-primary', - handle: ($event: MouseEvent) => { - close($event, true); - } - } - ]; - const buttons = ref(props.buttons && props.buttons.length ? props.buttons : defaultButtons); - - const showHeaderIcon = computed(() => !!headerIconClass.value); - const showFooter = computed(() => !!showButtons.value && !!buttons.value); - - const modalHeaderRef = ref(); - const modalElementRef = ref(); - const maximized = ref(false); - - const { renderResizeBar, maximize, restore, boundingElement, - resizedEventParam, allowDrag, unWindowResizeHandle } = useResizeable(props, context); - const { registerDraggle } = useDraggable(props, context, allowDrag); - - // 监听modal 标题变化 - watch(() => props.title, (newValue, oldValue) => { - if (newValue !== oldValue) { - title.value = newValue; - } - }); - - // 监听打开关闭状态变化 - watch(() => props.modelValue, (newValue, oldValue) => { - if (newValue !== oldValue) { - modelValue.value = newValue; - } - }); - // 监听是否展示标题变化 - watch(() => props.showHeader, (newValue, oldValue) => { - if (newValue !== oldValue) { - showHeader.value = newValue; - } - }); - // 监听是否展示按钮变化 - // todo: 可以抽出公共方法 - watch(() => props.showButtons, (newValue, oldValue) => { - if (newValue !== oldValue) { - showButtons.value = newValue; - } - }); - - watch(() => resizedEventParam.value, (newSize, oldSize) => { - const newSizeValue = newSize || {}; - const oldSizeValue = oldSize || {}; - - if (JSON.stringify(newSizeValue) !== JSON.stringify(oldSizeValue)) { - context.emit('resize', { newSize, oldSize }); - } - }); - - function removeModalOpenStyle() { - const modalTotal = document.querySelectorAll('.farris-modal').length; - if (!modalTotal || modalTotal - 1 <= 0) { - document.body.classList.remove('modal-open'); - } - - if (modalContainerRef.value) { - modalContainerRef.value.classList.remove('show'); - } - } - - const showModal = computed(() => { - if (modelValue.value) { - document.body.classList.add('modal-open'); - } else { - removeModalOpenStyle(); - } - - return modelValue.value; - }); - - const modalContainerClass = computed(() => { - const classObject = { - modal: true, - 'farris-modal': true, - 'fade': true, - } as Record; - classObject['f-modal-fitContent'] = !!fitContent.value; - classObject.show = !!showModal.value; - return classObject; - }); - - const modalDialogClass = computed(() => { - const classObject = { 'modal-dialog': true }; - const customClassArray = customClass.value?.split(' '); - customClassArray?.reduce((target: any, className: string) => { - target[className] = true; - return target; - }, classObject); - return classObject; - }); - - const modalDialogStyle = computed(() => { - const styleObject = { - position: 'absolute', - top: `${(window.innerHeight - height.value) / 2}px`, - left: `${(window.innerWidth - width.value) / 2}px`, - width: `${width.value}px`, - height: fitContent.value ? 'auto' : `${height.value}px` - }; - return styleObject; - }); - - const modalContentClass = computed(() => { - const classObject = { - 'modal-content': true, - 'modal-content-has-header': showHeader.value - }; - return classObject; - }); - - const modalHeaderStyle = computed(() => { - const styleObject = { display: showHeader.value ? '' : 'none' }; - styleObject['pointer-events'] = allowDrag.value ? 'auto': 'none'; - return styleObject; - }); - - const headerMaxButtonClass = computed(() => { - const classObject = { 'f-icon': true, modal_maximize: true, modalrevert: maximized.value }; - return classObject; - }); - - const modalBodyClass = computed(() => { - const classObject = { 'modal-body': true, 'f-utils-flex-column': dialogType.value === 'iframe' }; - return classObject; - }); - - function buildFooterStyles(): Record { - return {}; - } - - const modalFooterStyle = computed(() => { - const styleObject = { textAlgin: buttonAlignment.value }; - const footerSytles = buildFooterStyles(); - return Object.assign(styleObject, footerSytles); - }); - - function maxDialog($event: MouseEvent) { - $event.stopPropagation(); - if (maximized.value) { - maximized.value = false; - restore(); - return; - } - maximize(); - maximized.value = true; - } - - async function customButtonClick(button: ModalButton, $event: MouseEvent) { - if (button.handle) { - const result = await button.handle($event, button); - if (result) { - context.emit('closed', $event); - } - } - } - - function updateModalOptions(options: ModalOptions) { - if (options.width) { - width.value = options.width; - } - if (options.height) { - height.value = options.height; - } - if (options.buttons) { - buttons.value = options.buttons; - } - if (options.title) { - title.value = options.title; - } - } - - let escEventHandler: any = null; - let enterEventHandler: any = null; - - onMounted(() => { - if (modalElementRef.value && !containment.value) { - containment.value = (modalElementRef.value as HTMLElement).parentElement; - boundingElement.value = containment.value; - registerDraggle(modalHeaderRef.value, modalElementRef.value, boundingElement.value); - } - if (showModal.value) { - document.body.classList.add('modal-open'); - } - - escEventHandler = useEsc(props, context); - enterEventHandler = useEnter(props, context); - - }); - - onUnmounted(() => { - removeModalOpenStyle(); - if (unWindowResizeHandle) { - unWindowResizeHandle(); - } - - if (escEventHandler) { - escEventHandler.remove(); - } - - if (enterEventHandler) { - enterEventHandler.remove(); - } - }); - - context.expose({ - modalElementRef, - updateModalOptions, - close, - maxDialog - }); - - function renderFloatingCloseButton() { - return
    - {enableMinimize.value && ( -
  • - -
  • - )} - {enableMaximize.value && ( -
  • - -
  • - )} - {enableClose.value && ( -
  • close(payload, false)} style="pointer-events: auto;"> - -
  • - )} -
; - } - - function renderFooterButtons() { - return ; - } - - function renderModalHeader() { - return ; - } - - function onClickModalBackdrop($event) { - $event.stopPropagation(); - } - - return () => { - return ( - - {showModal.value && - -
-
-
- { showHeader.value && renderModalHeader() } - -
- {context.slots.default?.()} - {dialogType.value === 'iframe' && ( - - )} -
- {showFooter.value && renderFooterButtons()} -
- {!fitContent.value && resizeable.value && modalElementRef.value && !maximized.value && renderResizeBar(modalElementRef.value)} -
-
-
} -
- ); - }; - } -}); diff --git a/packages/mobile-ui-vue/components/modal/src/modal.css b/packages/mobile-ui-vue/components/modal/src/modal.css deleted file mode 100644 index 080d52aa71e8e0b9e1fe7b77fdd02b361982cdf3..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/src/modal.css +++ /dev/null @@ -1,84 +0,0 @@ -.fade-enter-active, -.fade-leave-active { - transition: opacity 0.5s ease; -} - -.fade-enter-from, -.fade-leave-to { - opacity: 0; -} - -.fv-resizable-handle { - position: absolute; - font-size: 0.1px; - display: block; - touch-action: none; - - &:hover { - background: rgba(42, 135, 255, .07); - } - - &.fv-resizable-n { - cursor: n-resize; - height: 0.4375rem; - width: 100%; - top: -0.3125rem; - left: 0; - } - - &.fv-resizable-e { - cursor: e-resize; - width: 0.4375rem; - right: -0.3125rem; - height: 100%; - top: 0; - } - - &.fv-resizable-s { - cursor: s-resize; - height: 0.4375rem; - width: 100%; - bottom: -0.3125rem; - left: 0; - } - - &.fv-resizable-w { - cursor: w-resize; - height: 100%; - width: 0.4375rem; - left: -0.3125rem; - top: 0; - } - - &.fv-resizable-ne { - cursor: ne-resize; - width: .75rem; - height: .75rem; - right: 1px; - top: 1px; - } - - &.fv-resizable-se { - cursor: se-resize; - width: .75rem; - height: .75rem; - right: 1px; - bottom: 1px; - } - - &.fv-resizable-nw { - cursor: nw-resize; - width: .75rem; - height: .75rem; - left: 1px; - top: 1px; - } - - &.fv-resizable-sw { - cursor: sw-resize; - width: .75rem; - height: .75rem; - left: 1px; - bottom: 1px; - } -} diff --git a/packages/mobile-ui-vue/components/modal/src/modal.props.ts b/packages/mobile-ui-vue/components/modal/src/modal.props.ts deleted file mode 100644 index 19fa251526cbd84092470e1af2353ab39b979e8e..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/src/modal.props.ts +++ /dev/null @@ -1,83 +0,0 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -import { ExtractPropTypes, PropType } from 'vue'; -import { ModalButton } from './composition/type'; - -export type DragHandleType = HTMLElement | string; - -export const modalProps = { - /** - * 自定义类 - */ - class: { type: String, default: '' }, - /** - * 模态框标题 - */ - title: { type: String, default: '' }, - /** - * 模态框宽度 - */ - width: { type: Number, default: 500 }, - /** - * 模态框高度 - */ - height: { type: Number, default: 320 }, - /** - * 自定义按钮列表 - */ - buttons: { - type: Array, - default: [] - }, - /** - * 是否展示模态框 - */ - modelValue: { type: Boolean, default: false }, - /** - * 是否展示头部 - */ - showHeader: { type: Boolean, default: true }, - /** - * 是否展示默认按钮 - */ - showButtons: { type: Boolean, default: true }, - /** - * 是否启用自适应样式 - */ - fitContent: { type: Boolean, default: true }, - /** - * 是否展示右上角按钮 - */ - showCloseButton: { type: Boolean, default: true }, - showMaxButton: { type: Boolean, default: false }, - minHeight: {type: Number}, - maxHeight: {type: Number}, - minWidth: {type: Number}, - maxWidth: {type: Number}, - containment: {type: Object as PropType, default: null}, - reiszeable: { type: Boolean, default: false }, - draggable: { type: Boolean, default: false}, - dragHandle: { type: Object as PropType, default: null}, - closedCallback: { type: Function, default: null}, - resizeHandle: { type: Function, default: null}, - render: { type: Function, default: null}, - acceptCallback: { type: Function, default: null}, - rejectCallback: { type: Function, default: null}, - enableEsc: { type: Boolean, default: true }, - enableEnter: { type: Boolean, default: false } -}; - -export type ModalProps = Partial>; diff --git a/packages/mobile-ui-vue/components/modal/style.ts b/packages/mobile-ui-vue/components/modal/style.ts deleted file mode 100644 index 9fef5f8ed020e3bee1f22913ce5428e931e3a730..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/modal/style.ts +++ /dev/null @@ -1,3 +0,0 @@ -import "@farris/mobile-ui-vue/dependent-base/style"; -import "@farris/mobile-ui-vue/button/style"; -import "@theme-default/components/modal.css"; diff --git a/packages/mobile-ui-vue/components/navbar/src/designer/nav.design.component.tsx b/packages/mobile-ui-vue/components/navbar/src/designer/nav.design.component.tsx index 6c3581ea4755c769c0b96697244e8cb3d57b1624..359bf636be9eda617501ccd6fb754bd3f3d39404 100644 --- a/packages/mobile-ui-vue/components/navbar/src/designer/nav.design.component.tsx +++ b/packages/mobile-ui-vue/components/navbar/src/designer/nav.design.component.tsx @@ -19,7 +19,7 @@ import { computed, defineComponent, inject, onMounted, ref, SetupContext } from import Navbar from '../..'; import { navbarProps, NavbarProps } from '../navbar.props'; import { useDesignerRules } from './use-designer-rules'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/common'; export default defineComponent({ name: 'FNavDesign', diff --git a/packages/mobile-ui-vue/components/navbar/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/navbar/src/designer/use-designer-rules.ts index afb90976dd732edf852ef0a7f589e31bdc46d029..2c0f77c92728dee5a853300b12db1888bda9ca1b 100644 --- a/packages/mobile-ui-vue/components/navbar/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/navbar/src/designer/use-designer-rules.ts @@ -1,5 +1,4 @@ -import { DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; -import { DraggingResolveContext } from "@farris/mobile-ui-vue/designer-canvas/src/composition/types"; +import { DesignerItemContext, UseDesignerRules, DraggingResolveContext } from "@farris/mobile-ui-vue/common"; import { nextTick, ref } from "vue"; import { NavBarProperty } from "../property-config/navbar.property-config"; diff --git a/packages/mobile-ui-vue/components/navbar/src/property-config/navbar.property-config.ts b/packages/mobile-ui-vue/components/navbar/src/property-config/navbar.property-config.ts index 4ad90c37cf959ab5cf100725ace670ac5f0105ac..0cabd550539cebb2f231599fee47f98b94e8bed2 100644 --- a/packages/mobile-ui-vue/components/navbar/src/property-config/navbar.property-config.ts +++ b/packages/mobile-ui-vue/components/navbar/src/property-config/navbar.property-config.ts @@ -1,4 +1,4 @@ -import { BaseControlProperty } from "@farris/mobile-ui-vue/property-panel"; +import { BaseControlProperty } from "@farris/mobile-ui-vue/common"; export class NavBarProperty extends BaseControlProperty { constructor(componentId: string, designerHostService: any) { @@ -10,12 +10,12 @@ export class NavBarProperty extends BaseControlProperty { // 外观 this.propertyConfig.categories['appearance'] = this.getAppearanceConfig(propertyData); // 行为 - this.propertyConfig.categories['behavior'] = this.getBehaviorConfig(propertyData); + this.propertyConfig.categories['behavior'] = this.getNavBarBehaviorConfig(propertyData); return this.propertyConfig; } - private getBehaviorConfig(propertyData) { + private getNavBarBehaviorConfig(propertyData) { return { description: "基本信息", title: "行为", diff --git a/packages/mobile-ui-vue/components/navbar/src/schema/navbar.schema.json b/packages/mobile-ui-vue/components/navbar/src/schema/navbar.schema.json index 1d7fac2629ed806801e18d001478c176d3ada77c..f61ca3117df7af33295c1b0baa210821c6759099 100644 --- a/packages/mobile-ui-vue/components/navbar/src/schema/navbar.schema.json +++ b/packages/mobile-ui-vue/components/navbar/src/schema/navbar.schema.json @@ -54,8 +54,6 @@ "type" ], "ignore": [ - "id", - "type", "appearance" ] } \ No newline at end of file diff --git a/packages/mobile-ui-vue/components/number-input/src/designer/number-input.design.component.tsx b/packages/mobile-ui-vue/components/number-input/src/designer/number-input.design.component.tsx index e030ff535714a3aac9aae64afd22fb66095d1ec1..ec373e0d663c1d746f38e7a642c04fe600cc3dd0 100644 --- a/packages/mobile-ui-vue/components/number-input/src/designer/number-input.design.component.tsx +++ b/packages/mobile-ui-vue/components/number-input/src/designer/number-input.design.component.tsx @@ -1,30 +1,45 @@ -import { defineComponent, inject, onMounted, ref, SetupContext } from 'vue'; - -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import { computed, defineComponent, inject, onMounted, ref } from 'vue'; +import { + DesignerHostService, + DesignerItemContext, + extractProperties, + useDesignerComponent +} from '@farris/mobile-ui-vue/common'; import { useDesignerRules } from './use-designer-rules'; +import NumberInput from '../number-input.component'; import { numberInputProps } from '../number-input.props'; -import InputGroup from '../..'; export default defineComponent({ - name: 'FmNunberInputDesign', - props: numberInputProps, - emits: [], - setup(props, context: SetupContext) { - const elementRef = ref(); - const designItemContext = inject('design-item-context') as DesignerItemContext; - const designerHostService = inject('designer-host-service'); - const designerRulesComposition = useDesignerRules(designItemContext, designerHostService); - const componentInstance = useDesignerComponent(elementRef, designItemContext, designerRulesComposition); + name: 'FmNunberInputDesign', + inheritAttrs: false, + props: extractProperties(numberInputProps, ['placeholder', 'enableNull']), + setup(props, context) { + const elementRef = ref(); + const designItemContext = inject( + 'design-item-context' + ) as DesignerItemContext; + const designerHostService = inject('designer-host-service'); + const designerRulesComposition = useDesignerRules(designItemContext, designerHostService); + const componentInstance = useDesignerComponent( + elementRef, + designItemContext, + designerRulesComposition + ); - onMounted(() => { - elementRef.value.componentInstance = componentInstance; - }); + onMounted(() => { + elementRef.value.componentInstance = componentInstance; + }); - context.expose(componentInstance.value); + context.expose(componentInstance.value); + const inputProps = computed(()=>{ + return { + ...props, + editable: false, + enableNull: true + }; + }); - return () => ( - - ); - } + return () => ; + } }); diff --git a/packages/mobile-ui-vue/components/number-input/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/number-input/src/designer/use-designer-rules.ts index 12ebbbcebe3d663c9e3d5b5ab4fdacbea7f34108..4e6377b410c9572c22d3fde92c966e67701d2cf9 100644 --- a/packages/mobile-ui-vue/components/number-input/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/number-input/src/designer/use-designer-rules.ts @@ -1,4 +1,4 @@ -import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; +import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; import { NumberInputProperty } from "../property-config/number-input.property-config"; export function useDesignerRules(designItemContext: DesignerItemContext, designerHostService): UseDesignerRules { diff --git a/packages/mobile-ui-vue/components/number-input/src/number-input.component.tsx b/packages/mobile-ui-vue/components/number-input/src/number-input.component.tsx index c17b190c06e536e4b8109eed3d452f3f45e4e4e0..94c12ba6f744f33acf999607f225bd54bbab3d8c 100644 --- a/packages/mobile-ui-vue/components/number-input/src/number-input.component.tsx +++ b/packages/mobile-ui-vue/components/number-input/src/number-input.component.tsx @@ -1,38 +1,16 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -import { defineComponent, SetupContext } from 'vue'; +import { defineComponent } from 'vue'; import { useBem } from '@farris/mobile-ui-vue/common'; import InputGroup from "@farris/mobile-ui-vue/input-group"; -import { NUMBER_INPUT_NAME, numberInputProps, NumberInputProps } from './number-input.props'; +import { NUMBER_INPUT_NAME, numberInputProps } from './number-input.props'; export default defineComponent({ name: NUMBER_INPUT_NAME, props: numberInputProps, - emits: ['update:modelValue'], - setup(props: NumberInputProps, context: SetupContext) { + setup(props) { const { bem } = useBem(NUMBER_INPUT_NAME); - const { emit } = context; - - const handleValueChange = (value: string | number) => { - emit('update:modelValue', value); - }; return () => ( - + ); } }); diff --git a/packages/mobile-ui-vue/components/number-input/src/number-input.props.ts b/packages/mobile-ui-vue/components/number-input/src/number-input.props.ts index fb1e2812957c89b687d23f527d03946465e89d54..a82429e61fd5a818812824c914b1fe7c5e9d0825 100644 --- a/packages/mobile-ui-vue/components/number-input/src/number-input.props.ts +++ b/packages/mobile-ui-vue/components/number-input/src/number-input.props.ts @@ -1,5 +1,5 @@ import { ExtractPropTypes } from 'vue'; -import { inputCommonProps } from '@farris/mobile-ui-vue/input-group'; +import { inputProps } from '@farris/mobile-ui-vue/input-group'; import { getPropsResolverGenerator } from '@farris/mobile-ui-vue/dynamic-resolver'; import numberInputSchema from './schema/number-input.schema.json'; import { schemaMapper } from './schema/schema-mapper'; @@ -8,11 +8,9 @@ import { schemaResolver } from './schema/schema-resolver'; export const NUMBER_INPUT_NAME = 'FmNumberInput'; export const numberInputProps = { - ...inputCommonProps, - enableNull: { type: Boolean, default: undefined }, - precision: { type: Number, default: 2 } -} as Record; + ...inputProps +}; export type NumberInputProps = ExtractPropTypes; -export const propsResolverGenerator = getPropsResolverGenerator(numberInputProps, numberInputSchema, schemaMapper, schemaResolver); +export const propsResolverGenerator = getPropsResolverGenerator(numberInputProps, numberInputSchema, schemaMapper, schemaResolver); diff --git a/packages/mobile-ui-vue/components/number-input/src/property-config/number-input.property-config.ts b/packages/mobile-ui-vue/components/number-input/src/property-config/number-input.property-config.ts index 63918fbc45a758a726c2a9143a77a7a1b788d1b1..fd36c058e1a9b20c43bd563c3a5408c02ff12265 100644 --- a/packages/mobile-ui-vue/components/number-input/src/property-config/number-input.property-config.ts +++ b/packages/mobile-ui-vue/components/number-input/src/property-config/number-input.property-config.ts @@ -1,30 +1,33 @@ -import { InputBaseProperty } from "@farris/mobile-ui-vue/common/src/entity/input-base-property"; +import { InputBaseProperty } from '@farris/mobile-ui-vue/common'; export class NumberInputProperty extends InputBaseProperty { + constructor(componentId: string, designerHostService: any) { + super(componentId, designerHostService); + } - constructor(componentId: string, designerHostService: any) { - super(componentId, designerHostService); - } - - - getEditorProperties(propertyData: any) { - return this.getComponentConfig(propertyData, {}, { - precision: { - description: "", - title: "精度", - type: "number" - }, - max: { - description: "", - title: "最大值", - type: "number" - }, - min: { - description: "", - title: "最小值", - type: "number" - }, - }); - } - + getEditorProperties(propertyData: any) { + return this.getComponentConfig( + propertyData, + {}, + { + precision: { + description: '', + title: '精度', + type: 'number' + }, + max: { + description: '', + title: '最大值', + type: 'number', + visible: false + }, + min: { + description: '', + title: '最小值', + type: 'number', + visible: false + } + } + ); + } } diff --git a/packages/mobile-ui-vue/components/page-body-container/src/designer/page-body-container.design.component.tsx b/packages/mobile-ui-vue/components/page-body-container/src/designer/page-body-container.design.component.tsx index c86873fb74227ad7889de006491233095edd8c27..6a35ae959782306737902bf343caa37898f39846 100644 --- a/packages/mobile-ui-vue/components/page-body-container/src/designer/page-body-container.design.component.tsx +++ b/packages/mobile-ui-vue/components/page-body-container/src/designer/page-body-container.design.component.tsx @@ -1,7 +1,7 @@ import { SetupContext, defineComponent, inject, onMounted, ref } from 'vue'; import { PageBodyContainerProps, pageBodyContainerProps } from '../page-body-container.props'; import { useDesignerRules } from './use-designer-rules'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/common';; export default defineComponent({ name: 'FmPageBodyContainerDesign', diff --git a/packages/mobile-ui-vue/components/page-body-container/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/page-body-container/src/designer/use-designer-rules.ts index 6d3cde536e0f2516b3ad2893f797988825d4d86b..509cfa3d619f9e406e546efc709945e91bb6e393 100644 --- a/packages/mobile-ui-vue/components/page-body-container/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/page-body-container/src/designer/use-designer-rules.ts @@ -1,7 +1,7 @@ import { nextTick, ref } from "vue"; import { PAGE_BODY_CONTAINER_NAME } from '../page-body-container.props'; -import { DesignerHostService, DraggingResolveContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas/src/composition/types"; -import { DesignerItemContext } from "@farris/mobile-ui-vue/designer-canvas"; +import { DesignerHostService, DraggingResolveContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; +import { DesignerItemContext } from "@farris/mobile-ui-vue/common"; import { PageBodyContainerProperty } from "../property-config/page-body-container.property-config"; export function useDesignerRules(designItemContext: DesignerItemContext, designerHostService?: DesignerHostService): UseDesignerRules { diff --git a/packages/mobile-ui-vue/components/page-body-container/src/property-config/page-body-container.property-config.ts b/packages/mobile-ui-vue/components/page-body-container/src/property-config/page-body-container.property-config.ts index c439fbc134ce52c51582b74f8eb699d9502c3fdc..3ffa3e43166ea42f20aa7384de312a8c98e4d069 100644 --- a/packages/mobile-ui-vue/components/page-body-container/src/property-config/page-body-container.property-config.ts +++ b/packages/mobile-ui-vue/components/page-body-container/src/property-config/page-body-container.property-config.ts @@ -1,4 +1,4 @@ -import { BaseControlProperty } from "@farris/mobile-ui-vue/property-panel"; +import { BaseControlProperty } from "@farris/mobile-ui-vue/common"; export class PageBodyContainerProperty extends BaseControlProperty { constructor(componentId: string, designerHostService: any) { diff --git a/packages/mobile-ui-vue/components/page-container/src/designer/page-container.design.component.tsx b/packages/mobile-ui-vue/components/page-container/src/designer/page-container.design.component.tsx index 59f267cd386bdf3dff20f87b87f002483b81407c..c3114429478b7e420040c1ba5b1a42d8bb465534 100644 --- a/packages/mobile-ui-vue/components/page-container/src/designer/page-container.design.component.tsx +++ b/packages/mobile-ui-vue/components/page-container/src/designer/page-container.design.component.tsx @@ -1,7 +1,7 @@ import { SetupContext, defineComponent, inject, onMounted, ref } from 'vue'; import { PageContainerProps, pageContainerProps } from '../page-container.props'; import { useDesignerRules } from './use-designer-rules'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/common';; export default defineComponent({ name: 'FmPageContainerDesign', diff --git a/packages/mobile-ui-vue/components/page-container/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/page-container/src/designer/use-designer-rules.ts index f5a8fc603e87dc9a1db0de633a8bae409d629eb6..a7220a9cb34b3e9e7228cb44ff8a482d407422ca 100644 --- a/packages/mobile-ui-vue/components/page-container/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/page-container/src/designer/use-designer-rules.ts @@ -1,7 +1,7 @@ import { ref } from "vue"; import { PAGE_CONTAINER_NAME } from '../page-container.props'; -import { DesignerHostService, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; -import { DraggingResolveContext } from "@farris/mobile-ui-vue/designer-canvas/src/composition/types"; +import { DesignerHostService, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; +import { DraggingResolveContext } from "@farris/mobile-ui-vue/common"; import { PageContainerProperty } from "../property-config/page-container.property-config"; export function useDesignerRules(designItemContext: DesignerItemContext, designerHostService?: DesignerHostService): UseDesignerRules { diff --git a/packages/mobile-ui-vue/components/page-container/src/property-config/page-container.property-config.ts b/packages/mobile-ui-vue/components/page-container/src/property-config/page-container.property-config.ts index c5d5ade562f76f9b84ed4fdf726e1f81dcf4ac9c..d36a043afa00929822464ef7d45fd535744d42ea 100644 --- a/packages/mobile-ui-vue/components/page-container/src/property-config/page-container.property-config.ts +++ b/packages/mobile-ui-vue/components/page-container/src/property-config/page-container.property-config.ts @@ -1,4 +1,4 @@ -import { BaseControlProperty } from "@farris/mobile-ui-vue/property-panel"; +import { BaseControlProperty } from "@farris/mobile-ui-vue/common"; export class PageContainerProperty extends BaseControlProperty { constructor(componentId: string, designerHostService: any) { diff --git a/packages/mobile-ui-vue/components/page-footer-container/src/designer/page-footer-container.design.component.tsx b/packages/mobile-ui-vue/components/page-footer-container/src/designer/page-footer-container.design.component.tsx index 77cfa6838282f5899aa146a2e65ec715c3ae095d..22c581508dc7b5239827e274180caa3c596cf360 100644 --- a/packages/mobile-ui-vue/components/page-footer-container/src/designer/page-footer-container.design.component.tsx +++ b/packages/mobile-ui-vue/components/page-footer-container/src/designer/page-footer-container.design.component.tsx @@ -1,7 +1,7 @@ import { SetupContext, defineComponent, inject, onMounted, ref } from 'vue'; import { PageFooterContainerProps, pageFooterContainerProps } from '../page-footer-container.props'; import { useDesignerRules } from './use-designer-rules'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/common';; export default defineComponent({ name: 'FmPageFooterContainerDesign', diff --git a/packages/mobile-ui-vue/components/page-footer-container/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/page-footer-container/src/designer/use-designer-rules.ts index c8a6911959079321bb5c56a59de6a33fd38e9c42..00e12a993f22f36bc38113d40812c283c7d94bf9 100644 --- a/packages/mobile-ui-vue/components/page-footer-container/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/page-footer-container/src/designer/use-designer-rules.ts @@ -1,7 +1,7 @@ import { ref } from "vue"; import { PAGE_FOOTER_CONTAINER_NAME } from '../page-footer-container.props'; -import { DesignerHostService, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; -import { DraggingResolveContext } from "@farris/mobile-ui-vue/designer-canvas/src/composition/types"; +import { DesignerHostService, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; +import { DraggingResolveContext } from "@farris/mobile-ui-vue/common"; import { PageFooterContainerProperty } from "../property-config/page-footer-container.property-config"; export function useDesignerRules(designItemContext: DesignerItemContext, designerHostService?: DesignerHostService): UseDesignerRules { diff --git a/packages/mobile-ui-vue/components/page-footer-container/src/property-config/page-footer-container.property-config.ts b/packages/mobile-ui-vue/components/page-footer-container/src/property-config/page-footer-container.property-config.ts index f37d1c71d3bedb2ffd74163f6b27af03203a9589..47fe8ee5999109109724912e08eecb3165ce5386 100644 --- a/packages/mobile-ui-vue/components/page-footer-container/src/property-config/page-footer-container.property-config.ts +++ b/packages/mobile-ui-vue/components/page-footer-container/src/property-config/page-footer-container.property-config.ts @@ -1,4 +1,4 @@ -import { BaseControlProperty } from "@farris/mobile-ui-vue/property-panel"; +import { BaseControlProperty } from "@farris/mobile-ui-vue/common"; export class PageFooterContainerProperty extends BaseControlProperty { constructor(componentId: string, designerHostService: any) { diff --git a/packages/mobile-ui-vue/components/page-header-container/src/designer/page-header-container.design.component.tsx b/packages/mobile-ui-vue/components/page-header-container/src/designer/page-header-container.design.component.tsx index 9401c7123a1c4494d8407a6ac391a432cd6d2e7b..0f354e8dd11850bf48437b2db722ebaf12ef295e 100644 --- a/packages/mobile-ui-vue/components/page-header-container/src/designer/page-header-container.design.component.tsx +++ b/packages/mobile-ui-vue/components/page-header-container/src/designer/page-header-container.design.component.tsx @@ -1,7 +1,7 @@ import { SetupContext, defineComponent, inject, onMounted, ref } from 'vue'; import { PageHeaderContainerProps, pageHeaderContainerProps } from '../page-header-container.props'; import { useDesignerRules } from './use-designer-rules'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/common';; export default defineComponent({ name: 'FmPageHeaderContainerDesign', diff --git a/packages/mobile-ui-vue/components/page-header-container/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/page-header-container/src/designer/use-designer-rules.ts index 77abd9ddfc17314f7b842a1d19713e82e99e6c42..a2279ec5615bf3c3208279f031da893fe54490fe 100644 --- a/packages/mobile-ui-vue/components/page-header-container/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/page-header-container/src/designer/use-designer-rules.ts @@ -1,7 +1,7 @@ import { ref } from "vue"; import { PAGE_HEADER_CONTAINER_NAME } from '../page-header-container.props'; -import { ComponentSchema, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; -import { DraggingResolveContext } from "@farris/mobile-ui-vue/designer-canvas/src/composition/types"; +import { ComponentSchema, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; +import { DraggingResolveContext } from "@farris/mobile-ui-vue/common"; import { PageHeaderContainerProperty } from "../property-config/page-header-container.property-config"; export function useDesignerRules(designItemContext: DesignerItemContext, designerHostService): UseDesignerRules { diff --git a/packages/mobile-ui-vue/components/page-header-container/src/property-config/page-header-container.property-config.ts b/packages/mobile-ui-vue/components/page-header-container/src/property-config/page-header-container.property-config.ts index 4303729e44aba2f3fa44a1b47abfc3acf75201b6..a292e7834f42044bc6e875bd23c7d8aae7d8740f 100644 --- a/packages/mobile-ui-vue/components/page-header-container/src/property-config/page-header-container.property-config.ts +++ b/packages/mobile-ui-vue/components/page-header-container/src/property-config/page-header-container.property-config.ts @@ -1,4 +1,4 @@ -import { BaseControlProperty } from "@farris/mobile-ui-vue/property-panel"; +import { BaseControlProperty } from "@farris/mobile-ui-vue/common"; export class PageHeaderContainerProperty extends BaseControlProperty { constructor(componentId: string, designerHostService: any) { diff --git a/packages/mobile-ui-vue/components/picker/index.ts b/packages/mobile-ui-vue/components/picker/index.ts index ee28dbf6b83d6da87d20474a248be6a58798c9d0..1ae96803550ace5532cf7b3eece4515cf3f09b53 100644 --- a/packages/mobile-ui-vue/components/picker/index.ts +++ b/packages/mobile-ui-vue/components/picker/index.ts @@ -2,7 +2,7 @@ import { withInstall, withRegister, withRegisterDesigner } from '@farris/mobile- import PickerPanelInstallless from "./src/picker-panel.component"; import PickerInstallless from "./src/picker.component"; import { propsResolverGenerator } from './src/picker.props'; -import EnumFieldInputDesign from './src/designer/enum-field-input.design.component'; +import PickerDesign from './src/designer/picker.design.component'; export * from './src/picker-panel.props'; export * from './src/types'; @@ -14,13 +14,13 @@ const PickerPanel = withInstall(PickerPanelInstallless); export * from './src/picker.props'; export * from './src/composition/use-picker-state'; -const PICKER_REGISTERED_NAME = 'picker'; const Picker = withInstall(PickerInstallless); // 注册运行时及设计时 +const PICKER_REGISTERED_NAME = 'picker'; withRegister(Picker, { name: PICKER_REGISTERED_NAME, propsResolverGenerator }); -withRegisterDesigner(Picker, { name: PICKER_REGISTERED_NAME, propsResolverGenerator, designerComponent: EnumFieldInputDesign }); +withRegisterDesigner(Picker, { name: PICKER_REGISTERED_NAME, propsResolverGenerator, designerComponent: PickerDesign }); export { Picker, PickerPanel }; export default Picker; diff --git a/packages/mobile-ui-vue/components/picker/src/designer/picker.design.component.tsx b/packages/mobile-ui-vue/components/picker/src/designer/picker.design.component.tsx new file mode 100644 index 0000000000000000000000000000000000000000..8f16c721e373e8f193977523ca2864f95ba1bc74 --- /dev/null +++ b/packages/mobile-ui-vue/components/picker/src/designer/picker.design.component.tsx @@ -0,0 +1,62 @@ +import { computed, defineComponent, inject, onMounted, ref } from 'vue'; +import { + DesignerHostService, + DesignerItemContext, + extractProperties, + useDesignerComponent +} from '@farris/mobile-ui-vue/common'; +import { pickerProps } from '../picker.props'; +import { usePickerDesignerRules } from './use-designer-rules'; +import InputGroup from '@farris/mobile-ui-vue/input-group'; + +export default defineComponent({ + name: 'FmPickerDesign', + inheritAttrs: false, + props: extractProperties(pickerProps, ['placeholder', 'columns', 'valueField', 'textField']), + setup(props, context) { + const elementRef = ref(); + const designerHostService = inject('designer-host-service'); + const designItemContext = inject( + 'design-item-context' + ) as DesignerItemContext; + const designerRulesComposition = usePickerDesignerRules(designItemContext, designerHostService); + const componentInstance = useDesignerComponent( + elementRef, + designItemContext, + designerRulesComposition + ); + + onMounted(() => { + elementRef.value.componentInstance = componentInstance; + }); + + /** + * 解决在设计时,数据为空数组,界面不显示内容的问题 + */ + const realEnumData = computed(() => { + if (!props.columns || props.columns.length === 0) { + const result = [] as any; + [ + { value: 'example1', name: '示例一' }, + { value: 'example2', name: '示例二' } + ].map((item) => { + const tempData = {}; + tempData[props.valueField] = item['value']; + tempData[props.textField] = item['name']; + result.push(tempData); + }); + return result; + } + return props.columns; + }); + + context.expose(componentInstance.value); + + const inputProps = computed(() => ({ + ...props, + editable: false + })); + + return () => ; + } +}); diff --git a/packages/mobile-ui-vue/components/picker/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/picker/src/designer/use-designer-rules.ts index c497b5bd7fd8984d66d74f49b28f5665837205df..d889f74f73e232ac66a585b0549c42cf93deb59f 100644 --- a/packages/mobile-ui-vue/components/picker/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/picker/src/designer/use-designer-rules.ts @@ -1,13 +1,13 @@ -import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; -import { EnumFieldInputProperty } from "../property-config/enum-field-input.property-config"; -export function useEnumFieldDesignerRules(designItemContext: DesignerItemContext, designerHostService): UseDesignerRules { +import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; +import { PickerInputProperty } from "../property-config/picker.property-config"; +export function usePickerDesignerRules(designItemContext: DesignerItemContext, designerHostService): UseDesignerRules { const schema = designItemContext.schema as ComponentSchema; // 构造属性配置方法 function getPropsConfig(componentId: string, componentInstance: DesignerComponentInstance) { - const radioGroupProps = new EnumFieldInputProperty(componentId, designerHostService); - return radioGroupProps.getPropertyConfig(schema, componentInstance); + const radioGroupProps = new PickerInputProperty(componentId, designerHostService); + return radioGroupProps.getPropertyConfig(schema, componentInstance); } return { getPropsConfig } as UseDesignerRules; diff --git a/packages/mobile-ui-vue/components/picker/src/property-config/picker.property-config.ts b/packages/mobile-ui-vue/components/picker/src/property-config/picker.property-config.ts new file mode 100644 index 0000000000000000000000000000000000000000..5ab366074a6e90f156d3036d010a59e2aaa62cb1 --- /dev/null +++ b/packages/mobile-ui-vue/components/picker/src/property-config/picker.property-config.ts @@ -0,0 +1,51 @@ +import { InputBaseProperty } from '@farris/mobile-ui-vue/common'; + +export class PickerInputProperty extends InputBaseProperty { + constructor(componentId: string, designerHostService: any) { + super(componentId, designerHostService); + } + + getEditorProperties(propertyData: any) { + const self = this; + const editorProperties = self.getComponentConfig( + propertyData, + { type: 'radio-group' }, + { + editable: { + description: '', + title: '允许编辑', + type: 'boolean' + }, + enableClear: { + description: '', + title: '启用清空', + type: 'boolean' + }, + data: { + description: '', + title: '数据', + type: 'array', + $converter: '/converter/enum-data.converter', + ...self.getItemCollectionEditor( + propertyData, + propertyData.editor.valueField, + propertyData.editor.textField + ), + // 这个属性,标记当属性变更得时候触发重新更新属性 + refreshPanelAfterChanged: true + } + } + ); + editorProperties['setPropertyRelates'] = function (changeObject) { + if (!changeObject) { + return; + } + switch (changeObject.propertyID) { + case 'data': { + break; + } + } + }; + return editorProperties; + } +} diff --git a/packages/mobile-ui-vue/components/picker/src/schema/picker.schema.json b/packages/mobile-ui-vue/components/picker/src/schema/picker.schema.json index 19a83d6350b111846061733e7c5984442b7755bb..55f8e95fdac369cd89e33f88c2facd3181e05b7e 100644 --- a/packages/mobile-ui-vue/components/picker/src/schema/picker.schema.json +++ b/packages/mobile-ui-vue/components/picker/src/schema/picker.schema.json @@ -1,91 +1,92 @@ { - "$schema": "https://json-schema.org/draft/2020-12/schema", - "$id": "https://farris-design.gitee.io/enum-field.schema.json", - "title": "picker", - "description": "A Farris Picker Component", - "type": "object", - "properties": { - "id": { - "description": "标志", - "type": "string" - }, - "type": { - "description": "控件类型", - "type": "string", - "default": "picker" - }, - "appearance": { - "description": "外观", - "type": "object", - "properties": { - "class": { - "type": "string" - }, - "style": { - "type": "string" - } - }, - "default": {} - }, - "binding": { - "description": "绑定", - "type": "object", - "default": {} - }, - "required": { - "description": "必填", - "type": "boolean", - "default": false - }, - "readonly": { - "description": "只读", - "type": "boolean", - "default": false - }, - "disabled": { - "description": "禁用", - "type": "boolean", - "default": false - }, - "placeholder": { - "description": "提示文本", - "type": "string" - }, - "title": { - "description": "标题", - "type": "string", - "default": "" - }, - "valueField": { - "description": "值字段", - "type": "string", - "default": "id" - }, - "textField": { - "description": "显示字段", - "type": "string", - "default": "name" - }, - "data": { - "description": "数据", - "type": "array", - "default": [] + "$schema": "https://json-schema.org/draft/2020-12/schema", + "$id": "https://farris-design.gitee.io/enum-field.schema.json", + "title": "picker", + "description": "A Farris Picker Component", + "type": "object", + "properties": { + "id": { + "description": "标志", + "type": "string" + }, + "type": { + "description": "控件类型", + "type": "string", + "default": "picker" + }, + "appearance": { + "description": "外观", + "type": "object", + "properties": { + "class": { + "type": "string" }, - "onUpdate:modelValue": { - "description": "值更新事件", - "type": "string" + "style": { + "type": "string" } + }, + "default": {} + }, + "binding": { + "description": "绑定", + "type": "object", + "default": {} + }, + "required": { + "description": "必填", + "type": "boolean", + "default": false + }, + "readonly": { + "description": "只读", + "type": "boolean", + "default": false + }, + "disabled": { + "description": "禁用", + "type": "boolean", + "default": false + }, + "editable": { + "description": "", + "type": "boolean", + "default": false + }, + "enableClear": { + "description": "", + "type": "boolean", + "default": false + }, + "placeholder": { + "description": "提示文本", + "type": "string" + }, + "title": { + "description": "标题", + "type": "string", + "default": "" + }, + "valueField": { + "description": "值字段", + "type": "string", + "default": "value" + }, + "textField": { + "description": "显示字段", + "type": "string", + "default": "name" + }, + "data": { + "description": "数据", + "type": "array", + "default": [] }, - "events": [ - "onUpdate:modelValue" - ], - "required": [ - "type" - ], - "ignore": [ - "id", - "type", - "appearance", - "binding" - ] -} \ No newline at end of file + "onUpdate:modelValue": { + "description": "值更新事件", + "type": "string" + } + }, + "events": ["onUpdate:modelValue"], + "required": ["type"], + "ignore": ["id", "appearance", "binding", "visible"] +} diff --git a/packages/mobile-ui-vue/components/property-panel/index.ts b/packages/mobile-ui-vue/components/property-panel/index.ts deleted file mode 100644 index 7963be09873589e9a106f4da19789b3c3683afe5..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/property-panel/index.ts +++ /dev/null @@ -1,24 +0,0 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -import { BaseControlProperty } from './src/composition/entity/base-property'; -import { SchemaDOMMapping } from './src/composition/entity/schema-dom-mapping'; - -export * from './src/composition/props/property-panel-item.props'; -export * from './src/composition/props/property-panel.props'; - -export * from './src/composition/type'; - -export { BaseControlProperty, SchemaDOMMapping }; diff --git a/packages/mobile-ui-vue/components/property-panel/src/composition/class/property-panel-item-list.css b/packages/mobile-ui-vue/components/property-panel/src/composition/class/property-panel-item-list.css deleted file mode 100644 index 1df3d4efa1d8893c31e9f33890874b4a6359e920..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/property-panel/src/composition/class/property-panel-item-list.css +++ /dev/null @@ -1,80 +0,0 @@ -.propertyCascadeItem { - background-color: transparent !important; - border: none !important; -} - -.propertyCascadeItem .card-header { - background-color: transparent !important; - padding: 4px 0px !important; - color: inherit !important; -} - -.propertyCascadeItem .card-header .panel-item-title { - width: 100%; - position: relative; - font-size: inherit !important; -} - -.propertyCascadeItem .card-header .panel-item-title .farris-input-wrap { - margin-left: -5px; - margin-right: -5px; -} - -.propertyCascadeItem .form-group .col-form-label .f-icon { - color: #a3a3a3 !important; -} - -.propertyCascadeItem .f-accordion-collapse, -.propertyCascadeItem .f-accordion-expand { - right: 0; - left: auto !important; - top: 6px; - color: #6b94ec !important; - position: absolute; -} - -.propertyCascadeItem .card-body { - padding: 3px 12px !important; - background: rgba(255, 255, 255, 0.8); - border-radius: 8px; - margin: 4px 0px; -} - -.propertyCascadeItem .card-body.hidden { - display: none; -} - -.landscape { - display: none; - flex-shrink: 0; - align-items: center; - justify-content: flex-end; -} - -.wide-panel .vertical { - display: none; -} - -.wide-panel .landscape { - display: block; - padding: 0px; - overflow: hidden; -} - -.wide-panel .line-item { - display: flex; -} - -.wide-panel .line-item .f-header { - margin-bottom: 0; -} - -.wide-panel .line-item .f-section-formgroup-legend { - width: 89px; - text-align: right; - padding-right: 13px; -} - -.wide-panel .line-item .farris-input-wrap { - flex: 1 1 0; -} diff --git a/packages/mobile-ui-vue/components/property-panel/src/composition/class/property-panel-item.css b/packages/mobile-ui-vue/components/property-panel/src/composition/class/property-panel-item.css deleted file mode 100644 index 50a976a6eab7e26aba701fc87e331785298ebf0b..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/property-panel/src/composition/class/property-panel-item.css +++ /dev/null @@ -1,30 +0,0 @@ -.property-item .form-group { - margin-bottom: 2px; -} - -.property-item .col-form-label { - line-height: 26px; -} - -.property-item .row-item { - align-items: center; -} - -.wide-panel .row-item { - display: flex; -} - -.wide-panel .row-item .component { - flex: 1 1 0; -} - -.wide-panel .row-item label { - width: 89px; - text-align: right; - padding-right: 10px; -} - -.wrap { - overflow: hidden; - text-overflow: ellipsis; -} \ No newline at end of file diff --git a/packages/mobile-ui-vue/components/property-panel/src/composition/class/property-panel.css b/packages/mobile-ui-vue/components/property-panel/src/composition/class/property-panel.css deleted file mode 100644 index a83de6b5095d92267e8de909e48e6206f00fcb83..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/property-panel/src/composition/class/property-panel.css +++ /dev/null @@ -1,222 +0,0 @@ -:host { - width: inherit; - height: inherit; -} - -.property-panel { - position: relative; -} - -.property-panel .switcher { - position: absolute; - top: 9px; - right: 0; - width: 40px; - text-align: center; -} - - -.property-panel .switcher i { - color: #4190FF; - font-size: 12px; - cursor: pointer; -} - -.property-panel .side-panel { - width: 41px; - background-color: #fff; - padding-top: 45px; - text-align: center; -} - -.property-panel .side-panel .icon { - display: block; - text-align: center; - color: #4190FF; - margin-bottom: 10px; -} - -.property-panel .side-panel span { - writing-mode: vertical-rl; - font-size: 14px; -} - -.propertyPanel { - width: 300px; - height: 100%; - color: rgba(0, 0, 0, 0.75); - background: #f3f8ff !important; - border-color: #d8dbe2 !important; - display: flex; -} - -.propertyPanel .title { - position: relative; - background: #d0d8e9 !important; - - flex-wrap: wrap; - border: 0; -} - -.propertyPanel .title.p-right { - padding-right: 40px; -} - -.propertyPanel .title>.title-label { - line-height: 34px; - white-space: nowrap; - overflow: hidden; - text-overflow: ellipsis; - padding-left: 12px; - padding-right: 12px; - color: #333333; - font-size: 13px; - font-weight: 600; - cursor: pointer; -} - -.propertyPanel .title>.title-label.active { - background: #8fb1df !important -} - -.propertyPanel .title .title-actions { - position: absolute; - right: 10px; - top: 0px; - padding-left: 35px; - height: 35px; - -ms-flex: 1; - flex: 1; - box-sizing: border-box; -} - -.propertyPanel .title .title-actions { - position: absolute; - right: 10px; - top: 0px; -} - -.propertyPanel .property-grid .group-label { - line-height: 30px; - display: block; - padding-left: 13px; - cursor: pointer; - background: rgb(226, 233, 246) !important; - ; - color: #435069 !important; - font-weight: 600 !important; - border-radius: 6px; -} - -.propertyPanel .search .textbox { - padding-left: 10px; -} - -.propertyPanel .search .input-group { - border-radius: 0; -} - -.propertyPanel .panel-body { - overflow: auto; - height: 100%; -} - -.propertyPanel .property-grid { - list-style: none; - margin: 0 10px; - padding: 0; -} - -.propertyPanel .property-grid li { - padding: 2px 0; -} - -.propertyPanel .panel-body .property-grid .group-label+div { - padding-bottom: 14px !important; - padding-top: .25rem !important; -} - -.propertyPanel .action-item { - cursor: pointer; - display: inline-block; - transition: transform 50ms ease; - position: relative; - padding: 0px; -} - -.propertyPanel .action-item>.f-icon { - color: rgba(66, 66, 66, .75); - line-height: 35px; - font-weight: 600; -} - -.propertyPanel .search .input-group-clear { - border-radius: 0 !important; -} - -/***************************白色主题******************************/ - -.white-theme .propertyPanel { - background: #fff !important; - border: 1px solid #D8DCE6 !important; -} - -.white-theme .propertyPanel .title { - overflow: visible; - background: #fff !important; - justify-content: space-around; -} - -.white-theme .propertyPanel { - background: #fff !important; -} - -.white-theme .propertyPanel .title { - overflow: visible; - background: #fff !important; - flex-wrap: wrap; - text-align: center; -} - -.white-theme .propertyPanel .title>.title-label { - border-bottom: 0; - font-weight: 400 !important; - /* margin-left: 20px; - margin-right: 20px; */ - border-bottom: 0; - background: #fff !important; - flex: 1; - color: #83849B; -} - -.white-theme .propertyPanel .title>.title-label>span { - padding: 0 14px 7px 14px; -} - -.white-theme .propertyPanel .title>.title-label.active>span { - border-bottom: 2px solid #5b89fe; - color: #5B89FE; - border-radius: 1.5px; -} - -.white-theme .propertyPanel .title.only { - text-align: left; -} - -.white-theme .propertyPanel .property-grid .group-label { - background: #fff !important; - line-height: 30px; - font-weight: 400 !important; - font-size: 13px; - color: #3F4764 !important; - border-radius: 6px; - background: #EEF4FF !important; - color: #435069 !important; -} - -.white-theme .propertyPanel .property-grid .group-label .f-icon { - color: #5D89FE; - font-size: 13px; -} - -/***************************白色主题 end ******************************/ \ No newline at end of file diff --git a/packages/mobile-ui-vue/components/property-panel/src/composition/props/property-panel-item-list.props.ts b/packages/mobile-ui-vue/components/property-panel/src/composition/props/property-panel-item-list.props.ts deleted file mode 100644 index 40bf0ca77a9f7902125345aec1afa7d3ff8f3cb1..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/property-panel/src/composition/props/property-panel-item-list.props.ts +++ /dev/null @@ -1,32 +0,0 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -import { ExtractPropTypes, PropType } from 'vue'; -import { ElementPropertyConfig } from '../entity/property-entity'; - -export const propertyPanelItemListProps = { - /** 某一分类下的属性配置 */ - // as PropType - category: { type: Object, default: {} }, - - categoryKey: { type: String }, - /** 属性值 */ - propertyData: { type: Object, default: {} }, - - valueChanged: { type: Function }, - - triggerRefreshPanel: { type: Function } -}; -export type PropertyPanelItemListProps = ExtractPropTypes; diff --git a/packages/mobile-ui-vue/components/property-panel/src/composition/props/property-panel-item.props.ts b/packages/mobile-ui-vue/components/property-panel/src/composition/props/property-panel-item.props.ts deleted file mode 100644 index c87c39e87b06433bd66629f11c7d54e665f93ee6..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/property-panel/src/composition/props/property-panel-item.props.ts +++ /dev/null @@ -1,22 +0,0 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -import { ExtractPropTypes, PropType } from 'vue'; - -export const propertyPanelItemProps = { - elementConfig: { type: Object, default: {} }, - category: { type: Object, default: {} } -}; -export type PropertyPanelItemProps = ExtractPropTypes; diff --git a/packages/mobile-ui-vue/components/property-panel/src/composition/props/property-panel.props.ts b/packages/mobile-ui-vue/components/property-panel/src/composition/props/property-panel.props.ts deleted file mode 100644 index 456a906bfad82d94fe2dd3451190addcb9a578d3..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/property-panel/src/composition/props/property-panel.props.ts +++ /dev/null @@ -1,64 +0,0 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -import { ExtractPropTypes, PropType } from 'vue'; - -type ShowMode = 'panel' | 'sidebar'; - -export const propertyPanelProps = { - - width: { type: String, default: '300px' }, - - height: { type: Number, default: 10 }, - - isWidePanel: { type: Boolean, default: false }, - - /** 是否启用搜索 */ - enableSearch: { type: Boolean, default: true }, - - /** 使用模式 */ - mode: { type: String as PropType, default: 'panel' }, - - /** 是否持有面板的隐藏显示状态 */ - isPersitOpenState: { type: Boolean, default: false }, - - /** isPersitOpenState=true时,控制面板是否隐藏显示 */ - isShowPanel: { type: Boolean, default: false }, - - /** 属性名 */ - propertyName: { type: String, default: '' }, - - /** 属性类型 */ - propertyConfig: { type: Array }, - - /** 属性值 */ - propertyData: { type: Object, default: {} }, - - /** 是否展示关闭按钮 */ - showCloseBtn: { type: Boolean, default: false }, - - /** 当前选中的标签页id */ - selectedTabId: { type: String, default: '' }, - - /** 是否是白色主题 */ - isWhiteTheme: { type: Boolean, default: true }, - - /** dom结构 */ - schema: { type: Object, default: {} }, - - /** 属性变更后事件 */ - propertyChanged: { type: Function } -}; -export type PropertyPanelProps = ExtractPropTypes; diff --git a/packages/mobile-ui-vue/components/property-panel/src/composition/type.ts b/packages/mobile-ui-vue/components/property-panel/src/composition/type.ts deleted file mode 100644 index f6727192b3f282af52eb8b82f4e307908a33fa7f..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/property-panel/src/composition/type.ts +++ /dev/null @@ -1,84 +0,0 @@ -/** - * 属性类型 - */ -export enum PropertyType { - /** 字符串 */ - string = 'string', - - /** 布尔,下拉选择 */ - boolean = 'boolean', - - /** 数字 */ - number = 'number', - - /** 下拉选择:单选 */ - select = 'select', - - /** 已废弃,请使用editableSelect */ - boolOrExp = 'boolOrExp', - - /** 可编辑的下拉选择:单选,并且可编辑 */ - editableSelect = 'editableSelect', - - /** 下拉多选 */ - multiSelect = 'multiSelect', - - /** 日期 */ - date = 'date', - - /** 日期时间 */ - datetime = 'datetime', - - /** 模态窗,自定义组件 */ - modal = 'modal', - - /** 级联 */ - cascade = 'cascade', - - /** 自定义组件 */ - custom = 'custom', - - /** 多功能属性编辑器,支持常量、变量、自定义、表达式等场景 */ - unity = 'unity', - - /** 事件编辑器集成,支持导入命令、参数编辑等场景 */ - events = 'events', - - /** 开关类编辑器,适用于布尔值属性 */ - switch = 'switch', - - /** 多语言输入框 */ - multiLanguage = 'multiLanguage' -} - -/** 属性值转换器,返回模态框类属性文本框内的显示内容 */ -export interface TypeConverter { - // 由模态框转为属性框中展示的值 - convertTo(data: any, params?: any): string; -} - -export interface KeyMap { - key: any; - value: any; -} - -/** - * binding 类型 - */ -export enum FormBindingType { - Form = "Form", - Variable = "Variable" -} - -export interface FormUnifiedColumnLayout { - uniqueColClassInSM: number; - uniqueColClassInMD: number; - uniqueColClassInLG: number; - uniqueColClassInEL: number; -} - -export interface IPropertyConfig { - getPropertyConfig(propertyData: any, eventsEditorUtils: any); -} - -export * from './entity/property-entity'; diff --git a/packages/mobile-ui-vue/components/property-panel/src/mock.ts b/packages/mobile-ui-vue/components/property-panel/src/mock.ts deleted file mode 100644 index 8266d0cfe1d4cdc4bc725cc7fb687e28393b7f6a..0000000000000000000000000000000000000000 --- a/packages/mobile-ui-vue/components/property-panel/src/mock.ts +++ /dev/null @@ -1,174 +0,0 @@ -export const propertyConfigTemp = [ - { - categoryId: 'basic', - categoryName: '基本信息', - properties: [ - { - propertyID: 'id', - propertyName: '标识', - propertyType: 'string', - description: '组件的id', - readonly: true - }, - { - propertyID: 'type', - propertyName: '控件类型', - propertyType: 'select', - description: '组件的类型', - } - ] - }, - { - categoryId: 'appearance', - categoryName: '样式', - properties: [ - { - propertyID: 'fill', - propertyName: '填充', - propertyType: 'datetime', - description: 'flex布局下,填充满剩余部分', - modelValue: '2023-4-9', - editor: { - id: 'd152e48d-13d1-4553-94fa-525fa67d4f2b', - type: 'date-picker', - require: false, - format: 'yyyy-MM-dd', - weekSelect: false, - startFieldCode: 'BillDate', - endFieldCode: 'BillDate' - }, - }, - { - propertyID: 'expanded', - propertyName: '展开', - propertyType: 'boolean', - description: '是否展开', - modelValue: 'false', - editor: { - type: 'combo-list', - require: false, - valueType: '1', - multiSelect: false, - data: [ - { - value: 'true', - name: 'true' - }, - { - value: 'false', - name: 'false' - } - ] - } - }, - { - propertyID: 'showHeader', - propertyName: '显示头部区域', - propertyType: 'boolean', - description: '是否显示头部区域', - modelValue: 'true', - editor: { - type: 'combo-list', - require: false, - valueType: '1', - multiSelect: false, - data: [ - { - value: 'true', - name: 'true' - }, - { - value: 'false', - name: 'false' - } - ] - } - }, - { - propertyID: 'mainTitle', - propertyName: '主标题', - propertyType: 'string', - description: '主标题名称', - group: 'header' - }, - { - propertyID: 'subTitle', - propertyName: '副标题', - propertyType: 'string', - description: '副标题名称', - group: 'header' - }, - { - propertyID: 'enableMaximize', - propertyName: '显示最大化', - propertyType: 'boolean', - description: '是否显示最大化', - group: 'header' - }, - { - propertyID: 'enableAccordion', - propertyName: '启用收折功能', - propertyType: 'boolean', - description: '是否启用收折功能', - group: 'header' - }, - { - propertyID: 'accordionMode', - propertyName: '收折模式', - propertyType: 'select', - description: '收折模式选择', - iterator: [{ key: 'default', value: '默认收折' }, { key: 'custom', value: '自定义收折' }], - group: 'header' - } - ] - }, - { - categoryId: 'toolbar', - categoryName: '工具栏', - properties: [ - { - propertyID: 'toolbarCls', - propertyName: '工具栏样式', - propertyType: 'string' - }, - { - propertyID: 'toolbarBtnSize', - propertyName: '按钮尺寸', - propertyType: 'select', - iterator: [ - { key: 'default', value: '标准' }, - { key: 'lg', value: '大号' } - ] - }, - { - propertyID: 'toolbarPopDirection', - propertyName: '弹出方向', - propertyType: 'select', - iterator: [ - { key: 'default', value: '自动' }, - { key: 'top', value: '向上' }, - { key: 'bottom', value: '向下' } - ] - } - ] - } -]; - -export const propertyDataTemp = { - id: 'dataGrid', - testCategoryCascade: { - showSize2: false - }, - language1: { - 'zh-CHS': 'check1', - 'en': 'hhhh' - }, - language2: { - 'en': 'hhhh2', - 'zh-CHS': 'check2', - }, - language3: { - 'en': 'hhhh3', - 'zh-CHS': 'check3', - } -}; diff --git a/packages/mobile-ui-vue/components/radio-group/src/designer/radio-group.design.component.tsx b/packages/mobile-ui-vue/components/radio-group/src/designer/radio-group.design.component.tsx index fa99c50f85b18f332ebd88fb41c17f25547e1c06..ea8a890658ca6e79e5de4f29df2ac41a3320945a 100644 --- a/packages/mobile-ui-vue/components/radio-group/src/designer/radio-group.design.component.tsx +++ b/packages/mobile-ui-vue/components/radio-group/src/designer/radio-group.design.component.tsx @@ -1,74 +1,74 @@ - -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -import { computed, defineComponent, inject, onMounted, readonly, ref, SetupContext } from 'vue'; -import { RadioGroup, RadioGroupProps, radioGroupProps } from '../..'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas'; +import { computed, defineComponent, inject, onMounted, ref } from 'vue'; +import { + DesignerHostService, + DesignerItemContext, + extractProperties, + useDesignerComponent +} from '@farris/mobile-ui-vue/common'; import { useRadioGroupDesignerRules } from './use-designer-rules'; +import { radioGroupProps } from '../radio-group.props'; +import RadioGroup from '../radio-group.component'; export default defineComponent({ - name: 'FmRadioGroupDesign', - props: radioGroupProps, - emits: [] as (string[] & ThisType) | undefined, - setup(props: RadioGroupProps, context: SetupContext) { - const elementRef = ref(); - const designerHostService = inject('designer-host-service'); - const designItemContext = inject('design-item-context') as DesignerItemContext; - const designerRulesComposition = useRadioGroupDesignerRules(designItemContext, designerHostService); - const componentInstance = useDesignerComponent(elementRef, designItemContext, designerRulesComposition); + name: 'FmRadioGroupDesign', + props: extractProperties(radioGroupProps, [ + 'options', + 'textField', + 'valueField', + 'direction', + 'type' + ]), + setup(props, context) { + const elementRef = ref(); + const designerHostService = inject('designer-host-service'); + const designItemContext = inject( + 'design-item-context' + ) as DesignerItemContext; + const designerRulesComposition = useRadioGroupDesignerRules( + designItemContext, + designerHostService + ); + const componentInstance = useDesignerComponent( + elementRef, + designItemContext, + designerRulesComposition + ); - onMounted(() => { - elementRef.value.componentInstance = componentInstance; - }); + onMounted(() => { + elementRef.value.componentInstance = componentInstance; + }); - /** - * 解决在设计时,数据为空数组,界面不显示内容的问题 - */ - const realEnumData = computed(() => { - if (!props.options || props.options.length === 0) { - const result = [] as any; - [ - { value: 'example1', name: '示例一' }, - { value: 'example2', name: '示例二' } - ].map(item => { - const tempData = {}; - tempData[props.valueField] = item['value']; - tempData[props.textField] = item['name']; - result.push(tempData); - }); - return result; - } - return props.options; + /** + * 解决在设计时,数据为空数组,界面不显示内容的问题 + */ + const realEnumData = computed(() => { + if (!props.options || props.options.length === 0) { + const result = [] as any; + [ + { value: 'example1', name: '示例一' }, + { value: 'example2', name: '示例二' } + ].map((item) => { + const tempData = {}; + tempData[props.valueField] = item['value']; + tempData[props.textField] = item['name']; + result.push(tempData); }); + return result; + } + return props.options; + }); - const inputGroupProps = computed(() => ({ - ...props, - editable: false, - readonly: true, - modelValue:null, - options:realEnumData.value, - type:"default" - })); + const radioGroupProps = computed(() => ({ + ...props, + editable: false, + readonly: true, + options: realEnumData.value + })); - context.expose(componentInstance.value); + context.expose(componentInstance.value); - return () => { - return ( - - ); - }; - } + return () => { + return ; + }; + } }); diff --git a/packages/mobile-ui-vue/components/radio-group/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/radio-group/src/designer/use-designer-rules.ts index 3e53eb89631306279106f2f54b65250615bc8fe8..1a9e02c9d13bc1d11339be5bd35e84b06cf34abf 100644 --- a/packages/mobile-ui-vue/components/radio-group/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/radio-group/src/designer/use-designer-rules.ts @@ -1,4 +1,4 @@ -import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; +import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; import { RadioGroupProperty } from "../property-config/radio-group.property-config"; export function useRadioGroupDesignerRules(designItemContext: DesignerItemContext, designerHostService): UseDesignerRules { @@ -6,8 +6,8 @@ export function useRadioGroupDesignerRules(designItemContext: DesignerItemContex // 构造属性配置方法 function getPropsConfig(componentId: string, componentInstance: DesignerComponentInstance) { - const radioGroupProps = new RadioGroupProperty(componentId, designerHostService); - return radioGroupProps.getPropertyConfig(schema, componentInstance); + const radioGroupProps = new RadioGroupProperty(componentId, designerHostService); + return radioGroupProps.getPropertyConfig(schema, componentInstance); } return { getPropsConfig } as UseDesignerRules; diff --git a/packages/mobile-ui-vue/components/radio-group/src/property-config/radio-group.property-config.ts b/packages/mobile-ui-vue/components/radio-group/src/property-config/radio-group.property-config.ts index 9b69160f2355e5d68637a37f5e527cec3c95bf26..705b099375e496b1cd9509868a0a487f9aa588ae 100644 --- a/packages/mobile-ui-vue/components/radio-group/src/property-config/radio-group.property-config.ts +++ b/packages/mobile-ui-vue/components/radio-group/src/property-config/radio-group.property-config.ts @@ -1,4 +1,4 @@ -import { InputBaseProperty } from '@farris/mobile-ui-vue/common/src/entity/input-base-property'; +import { InputBaseProperty } from '@farris/mobile-ui-vue/common'; export class RadioGroupProperty extends InputBaseProperty { constructor(componentId: string, designerHostService: any) { @@ -21,7 +21,6 @@ export class RadioGroupProperty extends InputBaseProperty { description: '', title: '数据', type: 'array', - $converter: '/converter/enum-data.converter', ...self.getItemCollectionEditor( propertyData, propertyData.editor.valueField, diff --git a/packages/mobile-ui-vue/components/radio-group/src/radio-group.component.tsx b/packages/mobile-ui-vue/components/radio-group/src/radio-group.component.tsx index cd552d70c4fb5d61cb1ed4519839e1c9fe74942c..706fc0443ef418700dc9ae5ba3bf4c297a4a3d7e 100644 --- a/packages/mobile-ui-vue/components/radio-group/src/radio-group.component.tsx +++ b/packages/mobile-ui-vue/components/radio-group/src/radio-group.component.tsx @@ -1,19 +1,3 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - import { SetupContext, computed, defineComponent, ref, watch } from 'vue'; import { useBem, useLink } from '@farris/mobile-ui-vue/common'; import { useGroupItems } from '@farris/mobile-ui-vue/checkbox-group'; @@ -21,14 +5,13 @@ import Radio from '@farris/mobile-ui-vue/radio'; import { RADIO_GROUP_NAME, RadioGroupContext, - RadioGroupProps, radioGroupProps } from './radio-group.props'; export default defineComponent({ name: RADIO_GROUP_NAME, props: radioGroupProps, - setup(props: RadioGroupProps, context: SetupContext) { + setup(props, context: SetupContext) { const { emit, slots } = context; const innerValue = ref(props.modelValue); diff --git a/packages/mobile-ui-vue/components/radio-group/src/radio-group.props.ts b/packages/mobile-ui-vue/components/radio-group/src/radio-group.props.ts index 2148d888b1354c058b1fa1208e284d5151e5e077..23a3b0f22e018d7a5418b1065b1479a0173b90b0 100644 --- a/packages/mobile-ui-vue/components/radio-group/src/radio-group.props.ts +++ b/packages/mobile-ui-vue/components/radio-group/src/radio-group.props.ts @@ -1,5 +1,5 @@ import { ExtractPropTypes, PropType } from 'vue'; -import {CheckerShape, CheckerShapeMap } from '@farris/mobile-ui-vue/checker'; +import {CheckerShape } from '@farris/mobile-ui-vue/checker'; import { CheckboxGroupContext, checkboxGroupProps } from '@farris/mobile-ui-vue/checkbox-group'; import { getPropsResolverGenerator } from '@farris/mobile-ui-vue/dynamic-resolver'; import inputSchema from './schema/radio-group.schema.json'; @@ -11,10 +11,10 @@ export const RADIO_GROUP_NAME = 'fm-radio-group'; export const radioGroupProps = { ...checkboxGroupProps, - shape: { type: String as PropType, default: CheckerShapeMap.Round }, + shape: { type: String as PropType, default: CheckerShape.Round }, modelValue: { type: [String, Number] , default: '' } -} as Record; +}; export type RadioGroupProps = ExtractPropTypes; @@ -24,4 +24,4 @@ type Merge = { export type RadioGroupContext = Merge void }>; -export const propsResolverGenerator = getPropsResolverGenerator(radioGroupProps, inputSchema, schemaMapper, schemaResolver); +export const propsResolverGenerator = getPropsResolverGenerator(radioGroupProps, inputSchema, schemaMapper, schemaResolver); diff --git a/packages/mobile-ui-vue/components/radio-group/src/schema/radio-group.schema.json b/packages/mobile-ui-vue/components/radio-group/src/schema/radio-group.schema.json index 7fad6675bf4385ad99edf0f0c63a07ac83c3e1d5..d993339cf0d92da9b2d916ee21e66a24c99486a4 100644 --- a/packages/mobile-ui-vue/components/radio-group/src/schema/radio-group.schema.json +++ b/packages/mobile-ui-vue/components/radio-group/src/schema/radio-group.schema.json @@ -32,23 +32,14 @@ "type": "object", "default": {} }, - "readonly": { - "type": "string", + "required": { + "description": "必填", + "type": "boolean", "default": false }, - "title": { - "description": "", - "type": "string", - "default": "" - }, - "label": { - "description": "", + "readonly": { "type": "string", - "default": "" - }, - "lableWidth": { - "description": "", - "type": "number" + "default": false }, "visible": { "description": "", @@ -63,7 +54,7 @@ "direction": { "description": "", "type": "string", - "default": "horizontal" + "default": "vertical" }, "textField": { "description": "", @@ -74,6 +65,11 @@ "description": "", "type": "string", "default": "value" + }, + "checkerType": { + "description": "", + "type": "string", + "default": "default" } }, "required": ["type"], diff --git a/packages/mobile-ui-vue/components/radio-group/src/schema/schema-mapper.ts b/packages/mobile-ui-vue/components/radio-group/src/schema/schema-mapper.ts index bf5fa0c7c604d94ab7ec1f164e2600ff20912a90..98eb00913b3deb56f695a38e0c7467d64318441b 100644 --- a/packages/mobile-ui-vue/components/radio-group/src/schema/schema-mapper.ts +++ b/packages/mobile-ui-vue/components/radio-group/src/schema/schema-mapper.ts @@ -1,6 +1,11 @@ -import { MapperFunction, resolveAppearance, resolveData } from '@farris/mobile-ui-vue/dynamic-resolver'; +import { + MapperFunction, + resolveAppearance, + resolveData +} from '@farris/mobile-ui-vue/dynamic-resolver'; export const schemaMapper = new Map([ - ['appearance', resolveAppearance], - ['data', resolveData], + ['appearance', resolveAppearance], + ['data', 'options'], + ['checkerType', 'type'] ]); diff --git a/packages/mobile-ui-vue/components/radio-group/src/schema/schema-resolver.ts b/packages/mobile-ui-vue/components/radio-group/src/schema/schema-resolver.ts index 7c8af7fc63d68147438fc329e74ebce565df4ef7..1e756819460221c500d1b646dbd318d77d7cfaf0 100644 --- a/packages/mobile-ui-vue/components/radio-group/src/schema/schema-resolver.ts +++ b/packages/mobile-ui-vue/components/radio-group/src/schema/schema-resolver.ts @@ -1,5 +1,9 @@ -import { DynamicResolver } from "@farris/mobile-ui-vue/dynamic-resolver"; +import { DynamicResolver } from '@farris/mobile-ui-vue/dynamic-resolver'; -export function schemaResolver(resolver: DynamicResolver, schema: Record, context: Record): Record { - return schema; +export function schemaResolver( + resolver: DynamicResolver, + schema: Record, + context: Record +): Record { + return schema; } diff --git a/packages/mobile-ui-vue/components/radio/src/radio.component.tsx b/packages/mobile-ui-vue/components/radio/src/radio.component.tsx index fb7a6bf9ff8197f618396499f7aba94aa2264c6a..1d6c235b1ea2c25527449de459cae83cf7def99e 100644 --- a/packages/mobile-ui-vue/components/radio/src/radio.component.tsx +++ b/packages/mobile-ui-vue/components/radio/src/radio.component.tsx @@ -15,7 +15,7 @@ */ import { defineComponent } from 'vue'; -import { Checker, CheckerRoleMap, CheckerShapeMap } from '@farris/mobile-ui-vue/checker'; +import { Checker, CheckerRole, CheckerShape } from '@farris/mobile-ui-vue/checker'; import { useBem, useLink } from '@farris/mobile-ui-vue/common'; import { RADIO_GROUP_NAME, RadioGroupContext } from '@farris/mobile-ui-vue/radio-group'; import { RADIO_NAME, RadioProps, radioProps } from './radio.props'; @@ -45,10 +45,10 @@ export default defineComponent({ : props.modelValue; return ( , default: CheckerRole.Radio }, + + shape: { type: String as PropType, default: CheckerShape.Round }, }; export type RadioProps = ExtractPropTypes; diff --git a/packages/mobile-ui-vue/components/register-designer.ts b/packages/mobile-ui-vue/components/register-designer.ts index dbb9c1503acbbfcb7e63ff6feed442c982e070f9..69cb383b4579ca3c6af46463cb34ad8f24118d6a 100644 --- a/packages/mobile-ui-vue/components/register-designer.ts +++ b/packages/mobile-ui-vue/components/register-designer.ts @@ -2,9 +2,9 @@ import { RegisterContext } from "./common"; import { propertyConfigSchemaMapForDesigner, schemaMapForDesigner, schemaResolverMapForDesigner } from "./dynamic-resolver"; import { propertyEffectMapForDesigner } from "./dynamic-resolver/src/resolver/property-config/property-config-resolver-design"; -const componentMap: Record = {}; -const componentPropsConverter: Record = {}; -const componentPropertyConfigConverter: Record = {}; +const componentMapForDisngner: Record = {}; +const componentPropsConverterForDesigner: Record = {}; +const componentPropertyConfigConverterForDesigner: Record = {}; let componentsRegistered = false; /** @@ -24,8 +24,8 @@ function registerDesignerComponents(components: any[]) { }; components.forEach(component => { - component.registerDesigner(componentMap, componentPropsConverter, componentPropertyConfigConverter, registerContext); + component.registerDesigner && component.registerDesigner(componentMapForDisngner, componentPropsConverterForDesigner, componentPropertyConfigConverterForDesigner, registerContext); }); } -export { registerDesignerComponents, componentMap, componentPropsConverter }; +export { registerDesignerComponents, componentMapForDisngner, componentPropsConverterForDesigner }; diff --git a/packages/mobile-ui-vue/components/register.ts b/packages/mobile-ui-vue/components/register.ts index 02f0fe969571bf9a6428251f84f3c07564bf31c1..fee88e812a7396677009b2c058a53cb647855cac 100644 --- a/packages/mobile-ui-vue/components/register.ts +++ b/packages/mobile-ui-vue/components/register.ts @@ -20,6 +20,9 @@ import Switch from './switch'; import DatePicker from './date-picker'; import DateTimePicker from './date-time-picker'; import Picker from './picker'; +import Lookup from './lookup'; +import RadioGroup from './radio-group'; +import CheckboxGroup from './checkbox-group'; const componentMap: Record = {}; const propsConverterMap: Record = {}; @@ -32,20 +35,50 @@ let componentsRegistered = false; * 注册组件 */ function registerComponents() { - if (componentsRegistered) { - return; - } - componentsRegistered = true; + if (componentsRegistered) { + return; + } + componentsRegistered = true; - const componentsToRegister = [ - Component, PageContainer, PageHeaderContainer, PageBodyContainer, PageFooterContainer, - ContentContainer, FloatContainer, - Navbar, Button, ButtonGroup, Listview, - Form, FormItem, InputGroup, Textarea, NumberInput, Switch, DatePicker, DateTimePicker, Picker - ]; - componentsToRegister.forEach((componentToRegister) => { - componentToRegister.register(componentMap, propsConverterMap, propConfigsConverterMap, resolverMap); - }); + const componentsToRegister = [ + Component, + PageContainer, + PageHeaderContainer, + PageBodyContainer, + PageFooterContainer, + ContentContainer, + FloatContainer, + Navbar, + Button, + ButtonGroup, + Listview, + Form, + FormItem, + InputGroup, + Textarea, + NumberInput, + Switch, + DatePicker, + DateTimePicker, + Picker, + Lookup, + RadioGroup, + CheckboxGroup + ]; + componentsToRegister.forEach((componentToRegister) => { + componentToRegister.register( + componentMap, + propsConverterMap, + propConfigsConverterMap, + resolverMap + ); + }); } -export { componentMap, propsConverterMap, propConfigsConverterMap, resolverMap, registerComponents }; +export { + componentMap, + propsConverterMap, + propConfigsConverterMap, + resolverMap, + registerComponents +}; diff --git a/packages/mobile-ui-vue/components/switch/src/designer/switch.design.component.tsx b/packages/mobile-ui-vue/components/switch/src/designer/switch.design.component.tsx index c8e5c5da540f646a2df08739c3a5f46ceebce514..a56bdc8759e9c2b0e07bbd89424a3faa49b5962d 100644 --- a/packages/mobile-ui-vue/components/switch/src/designer/switch.design.component.tsx +++ b/packages/mobile-ui-vue/components/switch/src/designer/switch.design.component.tsx @@ -1,51 +1,47 @@ - -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -import { computed, defineComponent, inject, onMounted, readonly, ref, SetupContext } from 'vue'; -import { Switch, SwitchProps, switchProps } from '../..'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';; +import { computed, defineComponent, inject, onMounted, ref } from 'vue'; +import { Switch, switchProps } from '../..'; +import { + DesignerHostService, + DesignerItemContext, + extractProperties, + useDesignerComponent +} from '@farris/mobile-ui-vue/common'; import { useInputGroupDesignerRules } from './use-designer-rules'; export default defineComponent({ - name: 'FmSwitchDesign', - props: switchProps, - emits: [] as (string[] & ThisType) | undefined, - setup(props: SwitchProps, context: SetupContext) { - const elementRef = ref(); - const designerHostService = inject('designer-host-service'); - const designItemContext = inject('design-item-context') as DesignerItemContext; - const designerRulesComposition = useInputGroupDesignerRules(designItemContext, designerHostService); - const componentInstance = useDesignerComponent(elementRef, designItemContext, designerRulesComposition); + name: 'FmSwitchDesign', + inheritAttrs: false, + props: extractProperties(switchProps, ['activeColor', 'inactiveColor']), + setup(props, context) { + const elementRef = ref(); + const designerHostService = inject('designer-host-service'); + const designItemContext = inject( + 'design-item-context' + ) as DesignerItemContext; + const designerRulesComposition = useInputGroupDesignerRules( + designItemContext, + designerHostService + ); + const componentInstance = useDesignerComponent( + elementRef, + designItemContext, + designerRulesComposition + ); - onMounted(() => { - elementRef.value.componentInstance = componentInstance; - }); + onMounted(() => { + elementRef.value.componentInstance = componentInstance; + }); - const inputGroupProps = computed(() => ({ - ...props, - editable: false, - modelValue:null - })); + const inputGroupProps = computed(() => ({ + ...props, + editable: false, + modelValue: null + })); - context.expose(componentInstance.value); + context.expose(componentInstance.value); - return () => { - return ( - - ); - }; - } + return () => { + return ; + }; + } }); diff --git a/packages/mobile-ui-vue/components/switch/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/switch/src/designer/use-designer-rules.ts index 95e71077dc030c7108f1740107d100871fa1aff3..f73c931ad4ab562c036a372ab6d0e43cdd4b81c3 100644 --- a/packages/mobile-ui-vue/components/switch/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/switch/src/designer/use-designer-rules.ts @@ -1,4 +1,4 @@ -import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; +import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; import { SwitchProperty } from "../property-config/switch.property-config"; export function useInputGroupDesignerRules(designItemContext: DesignerItemContext, designerHostService): UseDesignerRules { @@ -6,8 +6,8 @@ export function useInputGroupDesignerRules(designItemContext: DesignerItemContex // 构造属性配置方法 function getPropsConfig(componentId: string, componentInstance: DesignerComponentInstance) { - const inputGroupProps = new SwitchProperty(componentId, designerHostService); - return inputGroupProps.getPropertyConfig(schema, componentInstance); + const inputGroupProps = new SwitchProperty(componentId, designerHostService); + return inputGroupProps.getPropertyConfig(schema, componentInstance); } return { getPropsConfig } as UseDesignerRules; diff --git a/packages/mobile-ui-vue/components/switch/src/property-config/switch.property-config.ts b/packages/mobile-ui-vue/components/switch/src/property-config/switch.property-config.ts index ed4cd54c1f82afdac8ed798ece8f3ca68b1e5b99..8e3ee681a1d02ff4216c1920a8b31a18ec2082ed 100644 --- a/packages/mobile-ui-vue/components/switch/src/property-config/switch.property-config.ts +++ b/packages/mobile-ui-vue/components/switch/src/property-config/switch.property-config.ts @@ -1,4 +1,4 @@ -import { InputBaseProperty } from '@farris/mobile-ui-vue/common/src/entity/input-base-property'; +import { InputBaseProperty } from '@farris/mobile-ui-vue/common'; export class SwitchProperty extends InputBaseProperty { constructor(componentId: string, designerHostService: any) { diff --git a/packages/mobile-ui-vue/components/textarea/src/designer/textarea.design.component.tsx b/packages/mobile-ui-vue/components/textarea/src/designer/textarea.design.component.tsx index e125d0ec7ca3f054cb80eb5526425ae1f606b58b..d346aec2569ac807a04ebc0580321c2e85db7bca 100644 --- a/packages/mobile-ui-vue/components/textarea/src/designer/textarea.design.component.tsx +++ b/packages/mobile-ui-vue/components/textarea/src/designer/textarea.design.component.tsx @@ -1,53 +1,49 @@ - -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -import { computed, defineComponent, inject, onMounted, readonly, ref, SetupContext } from 'vue'; -import { DesignerHostService, DesignerItemContext, useDesignerComponent } from '@farris/mobile-ui-vue/designer-canvas';import { TEXTAREA_NAME, textareaProps, TextareaProps } from '../textarea.props'; +import { computed, defineComponent, inject, onMounted, ref } from 'vue'; +import { + DesignerHostService, + DesignerItemContext, + extractProperties, + useDesignerComponent +} from '@farris/mobile-ui-vue/common'; import { useTextareaDesignerRules } from './use-designer-rules'; -import Textarea from '../..'; - +import { textareaProps } from '../textarea.props'; +import Textarea from '../textarea.component'; export default defineComponent({ - name: 'FmTextareaDesign', - props: textareaProps, - emits: [] as (string[] & ThisType) | undefined, - setup(props: TextareaProps, context: SetupContext) { - const elementRef = ref(); - const designerHostService = inject('designer-host-service'); - const designItemContext = inject('design-item-context') as DesignerItemContext; - const designerRulesComposition = useTextareaDesignerRules(designItemContext, designerHostService); - const componentInstance = useDesignerComponent(elementRef, designItemContext, designerRulesComposition); - - onMounted(() => { - elementRef.value.componentInstance = componentInstance; - }); + name: 'FmTextareaDesign', + inheritAttrs: false, + props: extractProperties(textareaProps, ['placeholder', 'rows', 'showWordLimit', 'maxLength']), + setup(props, context) { + const elementRef = ref(); + const designerHostService = inject('designer-host-service'); + const designItemContext = inject( + 'design-item-context' + ) as DesignerItemContext; + const designerRulesComposition = useTextareaDesignerRules( + designItemContext, + designerHostService + ); + const componentInstance = useDesignerComponent( + elementRef, + designItemContext, + designerRulesComposition + ); - const inputGroupProps = computed(() => ({ - ...props, - type:"textarea", - editable: false, - modelValue:null - })); + onMounted(() => { + elementRef.value.componentInstance = componentInstance; + }); + + context.expose(componentInstance.value); - context.expose(componentInstance.value); + const inputProps = computed(() => { + return { + ...props, + editable: false, + }; + }); - return () => { - return ( - - ); - }; - } + return () => { + return ; + }; + } }); diff --git a/packages/mobile-ui-vue/components/textarea/src/designer/use-designer-rules.ts b/packages/mobile-ui-vue/components/textarea/src/designer/use-designer-rules.ts index 4686fe300d4000683cf56a3898484d6575c12458..8359c1491343b5846f479d82d999da50655a8a06 100644 --- a/packages/mobile-ui-vue/components/textarea/src/designer/use-designer-rules.ts +++ b/packages/mobile-ui-vue/components/textarea/src/designer/use-designer-rules.ts @@ -1,4 +1,4 @@ -import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/designer-canvas"; +import { ComponentSchema, DesignerComponentInstance, DesignerItemContext, UseDesignerRules } from "@farris/mobile-ui-vue/common"; import { TextareaProperty } from "../property-config/textarea.property-config"; export function useTextareaDesignerRules(designItemContext: DesignerItemContext, designerHostService): UseDesignerRules { diff --git a/packages/mobile-ui-vue/components/textarea/src/property-config/textarea.property-config.ts b/packages/mobile-ui-vue/components/textarea/src/property-config/textarea.property-config.ts index b43218b55be92a00305d3c84cdc822d3b4632332..bf92847b94a57f1ce302b44f8e83815fd194dcf5 100644 --- a/packages/mobile-ui-vue/components/textarea/src/property-config/textarea.property-config.ts +++ b/packages/mobile-ui-vue/components/textarea/src/property-config/textarea.property-config.ts @@ -1,39 +1,48 @@ -import { InputBaseProperty } from "@farris/mobile-ui-vue/common/src/entity/input-base-property"; +import { InputBaseProperty } from '@farris/mobile-ui-vue/common'; export class TextareaProperty extends InputBaseProperty { + constructor(componentId: string, designerHostService: any) { + super(componentId, designerHostService); + this.labelAlignReadonly = true; + } + getBasicProperties(propertyData, componentInstance){ + propertyData.labelAlign = 'top'; - constructor(componentId: string, designerHostService: any) { - super(componentId, designerHostService); - } - - getEditorProperties(propertyData: any) { - return this.getComponentConfig(propertyData, { type: "textarea" }, { - rows: { - description: "", - title: "文本区域可见的行数", - type: "number", - editor: { - min: 0, - nullable:true - } - }, - showCount: { - description: "", - title: "展示输入文本数量", - type: "boolean" - }, - maxLength: { - description: "文本最大长度", - title: "最大长度", - type: "number" - }, - autoHeight: { - description: "", - title: "自动高度", - type: "boolean" - }, - }); - } - - + return super.getBasicProperties(propertyData, componentInstance); + } + getEditorProperties(propertyData: any) { + return this.getComponentConfig( + propertyData, + { type: 'textarea' }, + { + rows: { + description: '', + title: '文本区域可见的行数', + type: 'number', + editor: { + min: 1, + nullable: true + } + }, + maxLength: { + description: '最大字数', + title: '最大字数', + type: 'number', + editor: { + nullable: true + } + }, + showCount: { + description: '', + title: '展示输入文本数量', + type: 'boolean' + }, + autoHeight: { + description: '', + title: '自动高度', + type: 'boolean' + } + } + ); + } } diff --git a/packages/mobile-ui-vue/components/textarea/src/schema/schema-mapper.ts b/packages/mobile-ui-vue/components/textarea/src/schema/schema-mapper.ts index 42b3a02141cbb40a799489f47e0c50df2a3e29f9..55ccab23420924c9e0c30a565a9a51c23d2a403d 100644 --- a/packages/mobile-ui-vue/components/textarea/src/schema/schema-mapper.ts +++ b/packages/mobile-ui-vue/components/textarea/src/schema/schema-mapper.ts @@ -2,5 +2,6 @@ import { MapperFunction, resolveAppearance } from '@farris/mobile-ui-vue/dynamic export const schemaMapper = new Map([ ['appearance', resolveAppearance], - ['binding', 'modelValue'] + ['binding', 'modelValue'], + ['showCount', 'showWordLimit'], ]); diff --git a/packages/mobile-ui-vue/components/textarea/src/schema/textarea.schema.json b/packages/mobile-ui-vue/components/textarea/src/schema/textarea.schema.json index 44635921d58dd44046b62b70c135f6899cf07ba9..d35c71704773613719e774820710c9c7dad2017c 100644 --- a/packages/mobile-ui-vue/components/textarea/src/schema/textarea.schema.json +++ b/packages/mobile-ui-vue/components/textarea/src/schema/textarea.schema.json @@ -62,7 +62,8 @@ }, "rows": { "description": "最大行数", - "type": "number" + "type": "number", + "default": 2 }, "autoHeight": { "description": "自动高度", diff --git a/packages/mobile-ui-vue/components/textarea/src/textarea.component.tsx b/packages/mobile-ui-vue/components/textarea/src/textarea.component.tsx index 3c626226999b867c27f60a10a78c43dfc08bf8aa..8714bcd9b5ee6cb5f2310485c2f2e5dcf72f1133 100644 --- a/packages/mobile-ui-vue/components/textarea/src/textarea.component.tsx +++ b/packages/mobile-ui-vue/components/textarea/src/textarea.component.tsx @@ -1,35 +1,14 @@ -/** - * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - import { defineComponent } from 'vue'; import InputGroup from "@farris/mobile-ui-vue/input-group"; -import { TEXTAREA_NAME, textareaProps, TextareaProps } from './textarea.props'; +import { TEXTAREA_NAME, textareaProps } from './textarea.props'; export default defineComponent({ name: TEXTAREA_NAME, props: textareaProps, - setup(props: TextareaProps, context) { - const { emit } = context; - - const handleValueChange = (value: string | number) => { - emit('update:modelValue', value); - }; + setup(props) { return () => ( - + ); } }); diff --git a/packages/mobile-ui-vue/components/textarea/src/textarea.props.ts b/packages/mobile-ui-vue/components/textarea/src/textarea.props.ts index 4eb0aa16e86e908e071be975a8d1ac9e83c4ebe6..18f8b328dac93fd5082977a2da9f5a2c7a246141 100644 --- a/packages/mobile-ui-vue/components/textarea/src/textarea.props.ts +++ b/packages/mobile-ui-vue/components/textarea/src/textarea.props.ts @@ -1,5 +1,5 @@ -import { ExtractPropTypes } from 'vue'; -import { inputCommonProps } from '@farris/mobile-ui-vue/input-group'; +import { ExtractPropTypes, PropType } from 'vue'; +import { inputProps, InputType } from '@farris/mobile-ui-vue/input-group'; import { getPropsResolverGenerator } from '@farris/mobile-ui-vue/dynamic-resolver'; import textareaSchema from './schema/textarea.schema.json'; import { schemaMapper } from './schema/schema-mapper'; @@ -8,19 +8,11 @@ import { schemaResolver } from './schema/schema-resolver'; export const TEXTAREA_NAME = 'FmTextarea'; export const textareaProps = { - ...inputCommonProps, + ...inputProps, - autoHeight: { type: Boolean, default: undefined }, - - rows: { type: Number, default: undefined }, - - maxHeight: { type: Number, default: undefined }, - - minHeight: { type: Number, default: undefined }, - - showWordLimit: { type: Boolean, default: undefined } -} as Record; + type: { type: String as PropType, default: InputType.textarea }, +}; export type TextareaProps = ExtractPropTypes; -export const propsResolverGenerator = getPropsResolverGenerator(textareaProps, textareaSchema, schemaMapper, schemaResolver); +export const propsResolverGenerator = getPropsResolverGenerator(textareaProps, textareaSchema, schemaMapper, schemaResolver); diff --git a/packages/mobile-ui-vue/demos/button/add.vue b/packages/mobile-ui-vue/demos/button/add.vue index 1004e9dba9a7ce772a8100c51293b2caa8a35b9a..1510603d34fd2339976d024276871094e0eab35f 100644 --- a/packages/mobile-ui-vue/demos/button/add.vue +++ b/packages/mobile-ui-vue/demos/button/add.vue @@ -1,7 +1,3 @@ - - - - diff --git a/packages/mobile-ui-vue/demos/button/base.vue b/packages/mobile-ui-vue/demos/button/base.vue index 336dddcddfb18b59f382a8d39d4403bbbf7747c6..6caa6bce94900cbdc8d9d33ce5342c632b80d919 100644 --- a/packages/mobile-ui-vue/demos/button/base.vue +++ b/packages/mobile-ui-vue/demos/button/base.vue @@ -5,9 +5,5 @@ 成功按钮 警告按钮 危险按钮 - 信息按钮 - - - diff --git a/packages/mobile-ui-vue/demos/button/block.vue b/packages/mobile-ui-vue/demos/button/block.vue index ac1b62ab74951d8f0305fdb27ff6a5721fbb5093..b8cadd0af898c8118e7914ec7e1f37e2f7410628 100644 --- a/packages/mobile-ui-vue/demos/button/block.vue +++ b/packages/mobile-ui-vue/demos/button/block.vue @@ -1,7 +1,3 @@ - - - - diff --git a/packages/mobile-ui-vue/demos/button/color.vue b/packages/mobile-ui-vue/demos/button/color.vue index 954659decfa54001f1d8ddf0e235b09809720d8f..18d1ed76361c1061dfdacb925f208704db5de487 100644 --- a/packages/mobile-ui-vue/demos/button/color.vue +++ b/packages/mobile-ui-vue/demos/button/color.vue @@ -3,7 +3,3 @@ 单色按钮 渐变色按钮 - - - - diff --git a/packages/mobile-ui-vue/demos/button/disabled.vue b/packages/mobile-ui-vue/demos/button/disabled.vue index 6e242fa688c2b692eaa92a1907f697f96bd563d8..6313e98fe33d41ff7b3010dcaa8745fc292520af 100644 --- a/packages/mobile-ui-vue/demos/button/disabled.vue +++ b/packages/mobile-ui-vue/demos/button/disabled.vue @@ -2,7 +2,3 @@ 禁用状态 禁用状态 - - - - diff --git a/packages/mobile-ui-vue/demos/button/icon.vue b/packages/mobile-ui-vue/demos/button/icon.vue index 2f94fe14bc35f3bfd18c4ecc093fcfddc8d94b26..a8c161cde4173fc6831c1d6298c4111406f5e670 100644 --- a/packages/mobile-ui-vue/demos/button/icon.vue +++ b/packages/mobile-ui-vue/demos/button/icon.vue @@ -2,7 +2,3 @@ 按钮 - - - - diff --git a/packages/mobile-ui-vue/demos/button/loading.vue b/packages/mobile-ui-vue/demos/button/loading.vue index 1659578b827af52d90e0da3188b831e1acd58717..eb010eb779f52f75503a6eacc417ca3bb6c7be83 100644 --- a/packages/mobile-ui-vue/demos/button/loading.vue +++ b/packages/mobile-ui-vue/demos/button/loading.vue @@ -3,7 +3,3 @@ - - - - diff --git a/packages/mobile-ui-vue/demos/button/plain.vue b/packages/mobile-ui-vue/demos/button/plain.vue index 200028ea59bddfa68165b058c024e7606a32c2bb..9a82b77133e24bb0602c926ab9948dec65df65bb 100644 --- a/packages/mobile-ui-vue/demos/button/plain.vue +++ b/packages/mobile-ui-vue/demos/button/plain.vue @@ -3,7 +3,3 @@ 线框按钮 线框按钮 - - - - diff --git a/packages/mobile-ui-vue/demos/button/round.vue b/packages/mobile-ui-vue/demos/button/round.vue index c7d8c18833e459455e5e35dcbe378be9a8148627..558edd35c7fe0d58dcad1328b407e4033d0ed020 100644 --- a/packages/mobile-ui-vue/demos/button/round.vue +++ b/packages/mobile-ui-vue/demos/button/round.vue @@ -3,6 +3,3 @@ 圆角按钮 - - - diff --git a/packages/mobile-ui-vue/demos/button/size.vue b/packages/mobile-ui-vue/demos/button/size.vue index b023d231a9105fa89f3c441c9c633719366706cd..3ef91c052595108bbe8ce7bf49759e8998327a69 100644 --- a/packages/mobile-ui-vue/demos/button/size.vue +++ b/packages/mobile-ui-vue/demos/button/size.vue @@ -1,11 +1,6 @@ - - - - diff --git a/packages/mobile-ui-vue/demos/input/text-area.vue b/packages/mobile-ui-vue/demos/input/text-area.vue index 4be137c5d50f564490d08de90e1a818a56ce0933..1b4af6f69c17960a9d967431461427ca8c68fb8a 100644 --- a/packages/mobile-ui-vue/demos/input/text-area.vue +++ b/packages/mobile-ui-vue/demos/input/text-area.vue @@ -3,5 +3,5 @@ - + diff --git a/packages/mobile-ui-vue/index.html b/packages/mobile-ui-vue/index.html index 23f687958c77ffa05b66cfceb5f3320d8887e496..e8b75dbc3b81404fbcd6aae64d4da7d9e9691ef1 100644 --- a/packages/mobile-ui-vue/index.html +++ b/packages/mobile-ui-vue/index.html @@ -5,7 +5,7 @@ - + Farris Mobile