¶Ô±ÈÐÂÎļþ |
| | |
| | | <template> |
| | | <PageWrapper title="表ååºç¡ç¤ºä¾" contentFullHeight> |
| | | <CollapseContainer title="åºç¡ç¤ºä¾"> |
| | | <BasicForm |
| | | autoFocusFirstItem |
| | | :labelWidth="200" |
| | | :schemas="schemas" |
| | | :actionColOptions="{ span: 24 }" |
| | | :labelCol="{ span: 8 }" |
| | | @submit="handleSubmit" |
| | | @reset="handleReset" |
| | | > |
| | | <template #jAreaLinkage="{ model, field }"> |
| | | <JAreaLinkage v-model:value="model[field]" :showArea="true" :showAll="false" /> |
| | | </template> |
| | | <template #localSearch="{ model, field }"> |
| | | <ApiSelect |
| | | :api="optionsListApi" |
| | | showSearch |
| | | v-model:value="model[field]" |
| | | optionFilterProp="label" |
| | | resultField="list" |
| | | labelField="name" |
| | | valueField="id" |
| | | /> |
| | | </template> |
| | | <template #selectA="{ model, field }"> |
| | | <a-select :options="optionsA" mode="multiple" v-model:value="model[field]" @change="valueSelectA = model[field]" allowClear /> |
| | | </template> |
| | | <template #selectB="{ model, field }"> |
| | | <a-select :options="optionsB" mode="multiple" v-model:value="model[field]" @change="valueSelectB = model[field]" allowClear /> |
| | | </template> |
| | | <template #remoteSearch="{ model, field }"> |
| | | <ApiSelect |
| | | :api="optionsListApi" |
| | | showSearch |
| | | v-model:value="model[field]" |
| | | :filterOption="false" |
| | | resultField="list" |
| | | labelField="name" |
| | | valueField="id" |
| | | @search="onSearch" |
| | | /> |
| | | </template> |
| | | </BasicForm> |
| | | </CollapseContainer> |
| | | </PageWrapper> |
| | | </template> |
| | | <script lang="ts"> |
| | | import { computed, defineComponent, unref, ref } from 'vue' |
| | | import { BasicForm, FormSchema, ApiSelect, JAreaLinkage } from '/@/components/Form/index' |
| | | import { CollapseContainer } from '/@/components/Container' |
| | | import { useMessage } from '/@/hooks/web/useMessage' |
| | | import { PageWrapper } from '/@/components/Page' |
| | | |
| | | import { optionsListApi } from '/@/api/demo/select' |
| | | import { useDebounceFn } from '@vueuse/core' |
| | | import { treeOptionsListApi } from '/@/api/demo/tree' |
| | | import { Select } from 'ant-design-vue' |
| | | import { cloneDeep } from 'lodash-es' |
| | | |
| | | const valueSelectA = ref<string[]>([]) |
| | | const valueSelectB = ref<string[]>([]) |
| | | const options = ref<Recordable[]>([]) |
| | | for (let i = 1; i < 10; i++) options.value.push({ label: 'é项' + i, value: `${i}` }) |
| | | |
| | | const optionsA = computed(() => { |
| | | return cloneDeep(unref(options)).map((op) => { |
| | | op.disabled = unref(valueSelectB).indexOf(op.value) !== -1 |
| | | return op |
| | | }) |
| | | }) |
| | | const optionsB = computed(() => { |
| | | return cloneDeep(unref(options)).map((op) => { |
| | | op.disabled = unref(valueSelectA).indexOf(op.value) !== -1 |
| | | return op |
| | | }) |
| | | }) |
| | | const provincesOptions = [ |
| | | { |
| | | id: 'guangdong', |
| | | label: '广ä¸ç', |
| | | value: '1', |
| | | key: '1', |
| | | }, |
| | | { |
| | | id: 'jiangsu', |
| | | label: 'æ±èç', |
| | | value: '2', |
| | | key: '2', |
| | | }, |
| | | ] |
| | | const citiesOptionsData = { |
| | | guangdong: [ |
| | | { |
| | | label: 'ç æµ·å¸', |
| | | value: '1', |
| | | key: '1', |
| | | }, |
| | | { |
| | | label: 'æ·±å³å¸', |
| | | value: '2', |
| | | key: '2', |
| | | }, |
| | | { |
| | | label: '广å·å¸', |
| | | value: '3', |
| | | key: '3', |
| | | }, |
| | | ], |
| | | jiangsu: [ |
| | | { |
| | | label: 'å京å¸', |
| | | value: '1', |
| | | key: '1', |
| | | }, |
| | | { |
| | | label: 'æ é¡å¸', |
| | | value: '2', |
| | | key: '2', |
| | | }, |
| | | { |
| | | label: 'èå·å¸', |
| | | value: '3', |
| | | key: '3', |
| | | }, |
| | | ], |
| | | } |
| | | |
| | | const schemas: FormSchema[] = [ |
| | | { |
| | | field: 'divider-basic', |
| | | component: 'Divider', |
| | | label: 'åºç¡å段', |
| | | }, |
| | | { |
| | | field: 'field1', |
| | | component: 'Input', |
| | | label: 'åæ®µ1', |
| | | |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | // componentProps:{}, |
| | | // can func |
| | | componentProps: ({ schema, formModel }) => { |
| | | console.log('form:', schema) |
| | | console.log('formModel:', formModel) |
| | | return { |
| | | placeholder: 'èªå®ä¹placeholder', |
| | | onChange: (e: any) => { |
| | | console.log(e) |
| | | }, |
| | | } |
| | | }, |
| | | renderComponentContent: () => { |
| | | return { |
| | | prefix: () => 'pSlot', |
| | | suffix: () => 'sSlot', |
| | | } |
| | | }, |
| | | }, |
| | | { |
| | | field: 'field2', |
| | | component: 'Input', |
| | | label: 'åæ®µ2', |
| | | defaultValue: '111', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | componentProps: { |
| | | onChange: (e: any) => { |
| | | console.log(e) |
| | | }, |
| | | }, |
| | | suffix: '天', |
| | | }, |
| | | { |
| | | field: 'field3', |
| | | component: 'DatePicker', |
| | | label: 'åæ®µ3', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | }, |
| | | { |
| | | field: 'field4', |
| | | component: 'Select', |
| | | label: 'åæ®µ4', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | componentProps: { |
| | | options: [ |
| | | { |
| | | label: 'é项1', |
| | | value: '1', |
| | | key: '1', |
| | | }, |
| | | { |
| | | label: 'é项2', |
| | | value: '2', |
| | | key: '2', |
| | | }, |
| | | ], |
| | | }, |
| | | }, |
| | | { |
| | | field: 'field5', |
| | | component: 'CheckboxGroup', |
| | | label: 'åæ®µ5', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | componentProps: { |
| | | options: [ |
| | | { |
| | | label: 'é项1', |
| | | value: '1', |
| | | }, |
| | | { |
| | | label: 'é项2', |
| | | value: '2', |
| | | }, |
| | | ], |
| | | }, |
| | | }, |
| | | { |
| | | field: 'field7', |
| | | component: 'RadioGroup', |
| | | label: 'åæ®µ7', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | componentProps: { |
| | | options: [ |
| | | { |
| | | label: 'é项1', |
| | | value: '1', |
| | | }, |
| | | { |
| | | label: 'é项2', |
| | | value: '2', |
| | | }, |
| | | ], |
| | | }, |
| | | }, |
| | | { |
| | | field: 'field8', |
| | | component: 'Checkbox', |
| | | label: 'åæ®µ8', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | renderComponentContent: 'Check', |
| | | }, |
| | | { |
| | | field: 'field9', |
| | | component: 'Switch', |
| | | label: 'åæ®µ9', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | }, |
| | | { |
| | | field: 'field10', |
| | | component: 'RadioButtonGroup', |
| | | label: 'åæ®µ10', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | componentProps: { |
| | | options: [ |
| | | { |
| | | label: 'é项1', |
| | | value: '1', |
| | | }, |
| | | { |
| | | label: 'é项2', |
| | | value: '2', |
| | | }, |
| | | ], |
| | | }, |
| | | }, |
| | | { |
| | | field: 'field11', |
| | | component: 'Cascader', |
| | | label: 'åæ®µ11', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | componentProps: { |
| | | options: [ |
| | | { |
| | | value: 'zhejiang', |
| | | label: 'Zhejiang', |
| | | children: [ |
| | | { |
| | | value: 'hangzhou', |
| | | label: 'Hangzhou', |
| | | children: [ |
| | | { |
| | | value: 'xihu', |
| | | label: 'West Lake', |
| | | }, |
| | | ], |
| | | }, |
| | | ], |
| | | }, |
| | | { |
| | | value: 'jiangsu', |
| | | label: 'Jiangsu', |
| | | children: [ |
| | | { |
| | | value: 'nanjing', |
| | | label: 'Nanjing', |
| | | children: [ |
| | | { |
| | | value: 'zhonghuamen', |
| | | label: 'Zhong Hua Men', |
| | | }, |
| | | ], |
| | | }, |
| | | ], |
| | | }, |
| | | ], |
| | | }, |
| | | }, |
| | | { |
| | | field: 'divider-api-select', |
| | | component: 'Divider', |
| | | label: 'è¿ç¨ä¸ææ¼ç¤º', |
| | | }, |
| | | { |
| | | field: 'field30', |
| | | component: 'ApiSelect', |
| | | label: 'æå è½½è¿ç¨ä¸æ', |
| | | required: true, |
| | | componentProps: { |
| | | // more details see /src/components/Form/src/components/ApiSelect.vue |
| | | api: optionsListApi, |
| | | params: { |
| | | id: 1, |
| | | }, |
| | | resultField: 'list', |
| | | // use name as label |
| | | labelField: 'name', |
| | | // use id as value |
| | | valueField: 'id', |
| | | // not request untill to select |
| | | immediate: false, |
| | | onChange: (e) => { |
| | | console.log('selected:', e) |
| | | }, |
| | | // atfer request callback |
| | | onOptionsChange: (options) => { |
| | | console.log('get options', options.length, options) |
| | | }, |
| | | }, |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | defaultValue: '0', |
| | | }, |
| | | { |
| | | field: 'field311', |
| | | component: 'JAreaLinkage', |
| | | label: 'çå¸åºéæ©', |
| | | helpMessage: ['JAreaLinkageç»ä»¶', 'çå¸åºéæ©'], |
| | | required: true, |
| | | slot: 'jAreaLinkage', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | defaultValue: ['130000', '130200'], |
| | | }, |
| | | { |
| | | field: 'field31', |
| | | component: 'Input', |
| | | label: '䏿æ¬å°æç´¢', |
| | | helpMessage: ['ApiSelectç»ä»¶', 'è¿ç¨æ°æ®æºæ¬å°æç´¢', 'åªåèµ·ä¸æ¬¡è¯·æ±è·åææé项'], |
| | | required: true, |
| | | slot: 'localSearch', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | defaultValue: '0', |
| | | }, |
| | | { |
| | | field: 'field32', |
| | | component: 'Input', |
| | | label: '䏿è¿ç¨æç´¢', |
| | | helpMessage: ['ApiSelectç»ä»¶', 'å°å
³é®è¯åéå°æ¥å£è¿è¡è¿ç¨æç´¢'], |
| | | required: true, |
| | | slot: 'remoteSearch', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | defaultValue: '0', |
| | | }, |
| | | { |
| | | field: 'field33', |
| | | component: 'ApiTreeSelect', |
| | | label: 'è¿ç¨ä¸ææ ', |
| | | helpMessage: ['ApiTreeSelectç»ä»¶', 'ä½¿ç¨æ¥å£æä¾çæ°æ®çæé项'], |
| | | required: true, |
| | | componentProps: { |
| | | api: treeOptionsListApi, |
| | | resultField: 'list', |
| | | }, |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | }, |
| | | { |
| | | field: 'field34', |
| | | component: 'ApiRadioGroup', |
| | | label: 'è¿ç¨Radio', |
| | | helpMessage: ['ApiRadioGroupç»ä»¶', 'ä½¿ç¨æ¥å£æä¾çæ°æ®çæé项'], |
| | | required: true, |
| | | componentProps: { |
| | | api: optionsListApi, |
| | | params: { |
| | | count: 2, |
| | | }, |
| | | resultField: 'list', |
| | | // use name as label |
| | | labelField: 'name', |
| | | // use id as value |
| | | valueField: 'id', |
| | | }, |
| | | defaultValue: '1', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | }, |
| | | { |
| | | field: 'field35', |
| | | component: 'ApiRadioGroup', |
| | | label: 'è¿ç¨Radio', |
| | | helpMessage: ['ApiRadioGroupç»ä»¶', 'ä½¿ç¨æ¥å£æä¾çæ°æ®çæé项'], |
| | | required: true, |
| | | componentProps: { |
| | | api: optionsListApi, |
| | | params: { |
| | | count: 2, |
| | | }, |
| | | resultField: 'list', |
| | | // use name as label |
| | | labelField: 'name', |
| | | // use id as value |
| | | valueField: 'id', |
| | | isBtn: true, |
| | | }, |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | }, |
| | | { |
| | | field: 'divider-linked', |
| | | component: 'Divider', |
| | | label: 'åæ®µèå¨', |
| | | }, |
| | | { |
| | | field: 'province', |
| | | component: 'Select', |
| | | label: 'ç份', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | componentProps: ({ formModel, formActionType }) => { |
| | | return { |
| | | options: provincesOptions, |
| | | placeholder: 'ç份ä¸åå¸èå¨', |
| | | onChange: (e: any) => { |
| | | // console.log(e) |
| | | let citiesOptions = e == 1 ? citiesOptionsData[provincesOptions[0].id] : citiesOptionsData[provincesOptions[1].id] |
| | | // console.log(citiesOptions) |
| | | if (e === undefined) { |
| | | citiesOptions = [] |
| | | } |
| | | formModel.city = undefined // reset city value |
| | | const { updateSchema } = formActionType |
| | | updateSchema({ |
| | | field: 'city', |
| | | componentProps: { |
| | | options: citiesOptions, |
| | | }, |
| | | }) |
| | | }, |
| | | } |
| | | }, |
| | | }, |
| | | { |
| | | field: 'city', |
| | | component: 'Select', |
| | | label: 'åå¸', |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | componentProps: { |
| | | options: [], // defalut [] |
| | | placeholder: 'ç份ä¸åå¸èå¨', |
| | | }, |
| | | }, |
| | | { |
| | | field: 'divider-selects', |
| | | component: 'Divider', |
| | | label: 'äºæ¥å¤é', |
| | | helpMessage: ['两个Selectå
±ç¨æ°æ®æº', 'ä½ä¸å¯éæ©å¯¹æ¹å·²éä¸ç项ç®'], |
| | | }, |
| | | { |
| | | field: 'selectA', |
| | | component: 'Select', |
| | | label: 'äºæ¥SelectA', |
| | | slot: 'selectA', |
| | | defaultValue: [], |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | }, |
| | | { |
| | | field: 'selectB', |
| | | component: 'Select', |
| | | label: 'äºæ¥SelectB', |
| | | slot: 'selectB', |
| | | defaultValue: [], |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | }, |
| | | { |
| | | field: 'divider-others', |
| | | component: 'Divider', |
| | | label: 'å
¶å®', |
| | | }, |
| | | { |
| | | field: 'field20', |
| | | component: 'InputNumber', |
| | | label: 'åæ®µ20', |
| | | required: true, |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | }, |
| | | { |
| | | field: 'field21', |
| | | component: 'Slider', |
| | | label: 'åæ®µ21', |
| | | componentProps: { |
| | | min: 0, |
| | | max: 100, |
| | | range: true, |
| | | marks: { |
| | | 20: '20°C', |
| | | 60: '60°C', |
| | | }, |
| | | }, |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | }, |
| | | { |
| | | field: 'field22', |
| | | component: 'Rate', |
| | | label: 'åæ®µ22', |
| | | defaultValue: 3, |
| | | colProps: { |
| | | span: 8, |
| | | }, |
| | | componentProps: { |
| | | disabled: false, |
| | | allowHalf: true, |
| | | }, |
| | | }, |
| | | ] |
| | | |
| | | export default defineComponent({ |
| | | components: { |
| | | BasicForm, |
| | | CollapseContainer, |
| | | PageWrapper, |
| | | ApiSelect, |
| | | JAreaLinkage, |
| | | ASelect: Select, |
| | | }, |
| | | setup() { |
| | | const check = ref(null) |
| | | const { createMessage } = useMessage() |
| | | const keyword = ref<string>('') |
| | | const searchParams = computed<Recordable>(() => { |
| | | return { keyword: unref(keyword) } |
| | | }) |
| | | |
| | | function onSearch(value: string) { |
| | | keyword.value = value |
| | | } |
| | | function areaChange(value) { |
| | | alert(value) |
| | | } |
| | | |
| | | return { |
| | | schemas, |
| | | optionsListApi, |
| | | optionsA, |
| | | optionsB, |
| | | valueSelectA, |
| | | valueSelectB, |
| | | onSearch: useDebounceFn(onSearch, 300), |
| | | searchParams, |
| | | handleReset: () => { |
| | | keyword.value = '' |
| | | }, |
| | | handleSubmit: (values: any) => { |
| | | createMessage.success('click search,values:' + JSON.stringify(values)) |
| | | }, |
| | | check, |
| | | } |
| | | }, |
| | | }) |
| | | </script> |