1. Проблемы, которые существуют и требуют решения
Как правило, при фоновом OA вы обнаружите, что существует много форм повторяющегося кода, а логика в основном одинакова.Каждый раз, когда вы добавляете новую форму, вам нужно копировать в основном непротиворечивую структуру кода, а затем просто изменять соответствующие области для развития.
2. Ожидаемые результаты
Извлечение повторяющейся логики форм для формирования общих компонентов и создание форм с помощью согласованной конфигурации структуры данных JSON.
1. Как использовать
<common-form :form-option="formOption" :is-reset-form-flag="isResetFormFlag"></common-form>
Полученный реквизит:
isResetFormFlag: Обновлять ли флаг содержимого формы, используемый для запуска обновления формы.formModel
formOption: Настройка формы, ниже подробная инструкция по настройке
isDisabled: Редактируется ли форма
2. Единая конфигурация группы форм
{
name: 'channel-form',
data: {},
items: [
{
label: '类型',
name: 'biz_type',
type: 'select',
dataList: [{
index: 1,
text: '业务部'
}]
}
],
rules: {
name: [{ required: true, message: '请输入产品名称', trigger: 'blur' }]
},
btnList: [{
text: '保存',
type: 'primary',
onClick: this.commitForm
}]
}
3. Конфигурация группы из нескольких форм
formOption: {
name: 'channel-form',
data: {},
groups: [{
title: '',// 组标题
tips: ''// 组提示
items: [] // 组表单项,和单一组配置一致
}]
}
3. Логика реализации
Различные выходные данные в зависимости от конфигурацииform-item, элементы формы, требующие специальной обработки, проходят черезjsxПользовательская реализация по месту использования
Что такое JSX:Talent.v ue js.org/v2/expensive/hot…
Документация:egoist.wipe/2017/09/21/…
Причины использования JSX: Форма содержит большинство опций, но также есть много неясных ситуаций, которые необходимо реализовать извне.По сравнению с шаблонным методом, jsx более гибок в использовании.
В-четвертых, документ конфигурации
| узел | описывать | Типы | Это необходимо | Примечание |
|---|---|---|---|---|
| name | имя формы | String | нет | Имя по умолчанию oa-form |
| data | данные формы | Object | нет | Данные заполнения формы для асинхронного запроса редактирования сцены |
| groups | сформировать группу | Array | нет | Группы и элементы не должны существовать одновременно. Группы содержат элементы. Если группы пусты, будут отображаться внешние элементы. Если группы не пусты, будет отображаться только содержимое групп. |
| items | элемент формы | Array | нет | Поддерживаемые типы: поле ввода: ввод, текстовое поле; поле множественного выбора: флажок; поле переключателя: радио; раскрывающееся меню: выбор |
| rules | правила проверки формы | Object | нет | Имя узла должно полностью соответствовать имени конфигурации элементов. |
| btnList | список кнопок | Array | нет | Будет включать данные формы и ссылку на форму в функцию обратного вызова. |
6. Некоторые проблемы, с которыми сталкивается VUE JSX
поддержка v-модели: Babel-плагин-jsx-v-модель
syncОбозначение модификатора
visible={ this.dialogImgVisible } {...{on: {'update:visible': (val) => { this.dialogImgVisible = val }}}}
Семь, часть кода реализации
1. Создайте список
generateList (itemObj) {
let itemEle = []
for (let index = 0; index < itemObj.dataList.length; index++) {
const item = itemObj.dataList[index]
switch (itemObj.type) {
// 下拉菜单
case 'select':
itemEle.push(<el-option key={ item.index } label={ item.text } value={ item.index }></el-option>)
break
// 多选框
case 'checkbox':
itemEle.push(<el-checkbox label={ item.index }>{ item.text }</el-checkbox>)
break
// 单选框
case 'radio':
itemEle.push(<el-radio label={ item.index }>{ item.text }</el-radio>)
break
}
}
return itemEle
}
2. Создайте раскрывающееся меню
generateSelect (item) {
return <el-select v-model={ this.formModel[item.name] } style={ item.style || this.defaultStyle }>{ this.generateList(item) }</el-select>
}
Примечание. Аналогично реализованы и другие элементы.
3. функция визуализации
render (h) {
let ele = []
// 表单内容
if (this.isGroup) {
ele = this.generateGroup()
} else {
ele = this.generateFormItems(this.formOption.items)
}
// 按钮列表
let btnListEle = []
this.formOption.btnList.forEach((btn) => {
btnListEle.push(<el-button type={ btn.type } on-click={ () => { btn.onClick(this.$refs[this.formName], this.formModel) } }>{ btn.text }</el-button>)
})
return (
<div class="oa-form-container">
<el-form ref={ this.formName } model={ this.formModel } rules={ this.formOption.rules } inline={ this.inline } disabled={ this.isDisabled } label-width={ this.formOption.labelWidth || '150px'}>
{ ele }
<el-form-item label-width={ this.isGroup ? '0' : '150px'}>{ btnListEle }</el-form-item>
</el-form>
</div>
)
}
Восемь, наконец, вставьте форму пакета
<script>
export default {
props: {
// 表格列
columns: {
type: Array,
default: _ => { return [] }
},
// 表格数据
tableData: {
type: Array,
default: _ => { return [] }
},
// loading 标志
loading: {
type: Boolean,
default: false
}
},
methods: {
sortChange (obj) {
this.$emit('sortChange', obj)
}
},
render () {
return (
<el-table border stripe v-loading={ this.loading } element-loading-text="拼命加载中" data={ this.tableData } on-sort-change={ obj => { this.sortChange(obj) } } style="width: 100%">
{
this.columns.map(columnObj => {
return <el-table-column prop={ columnObj.prop } label={ columnObj.label } sortable={ columnObj.sortable } width={ columnObj.width }
{...{
scopedSlots: {
default: scope => {
return columnObj.hasOwnProperty('render') ? columnObj.render(scope.index, scope.row) : scope.row[columnObj.prop]
}
}
}}
>
</el-table-column>
})
}
</el-table>
)
}
}
</script>
1. Как использовать
<common-table :columns="columns" :table-data="tableData" :loading="loading" @sort-change="sortChange"></common-table>
2, конфигурация столбцов
{
label: '',
prop: '',
width: '100',
sortable: true
render: ()=>{}
}
Рендеринг пользовательской конфигурации, передайте функцию рендеринга, если есть функция рендеринга, сначала используется результат функции рендеринга.
Адрес на гитхабе:GitHub.com/Daily Tan Weijie…