Vue 若依框架 form-generator添加表格组件和动态表单组件

效果图:

 在若依框架自带的流程表单配置基础上添加这两个组件

config.js

// 表单属性【右面板】
export const formConf = {formRef: 'elForm',formModel: 'formData',other: 'other',size: 'medium',labelPosition: 'right',labelWidth: 100,formRules: 'rules',gutter: 15,disabled: false,span: 24,formBtns: true,tableName: '',//关联表名flowName: '',//关联流程flowId: '',//关联流程id
}// 输入型组件 【左面板】
export const inputComponents = [{__config__: {label: '文本',width: '200px',prop: '',align: '',labelWidth: null,labelHeight: null,showLabel: false,changeTag: true,tag: 'ts-text',tagIcon: 'edit',defaultValue: undefined,style: {fonWeight: 'bold'},required: false,layout: 'colFormItem',span: 24,document: 'https://element.eleme.cn/#/zh-CN/component/input',// 正则校验规则regList: []},// 组件的插槽属性__slot__: {span: '文本'},// 其余的为可直接写在组件标签上的属性style: { width: '100%' },clearable: true,'prefix-icon': '','suffix-icon': '',maxlength: null,'show-word-limit': false,readonly: false,disabled: false},{__config__: {label: '操作人',showLabel: true,width: '200px',prop: '',align: '',labelWidth: null,labelHeight: null,changeTag: true,tag: 'ts-signature',tagIcon: 'icon-account',defaultValue: undefined,style: {fonWeight: 'bold'},required: false,layout: 'colFormItem',span: 24,document: 'https://element.eleme.cn/#/zh-CN/component/input',// 正则校验规则regList: []},// 组件的插槽属性__slot__: {span: '文本'},// 其余的为可直接写在组件标签上的属性style: { width: '100%' },clearable: true,'prefix-icon': '','suffix-icon': '',maxlength: null,'show-word-limit': false,readonly: false,disabled: false},{// 组件的自定义配置__config__: {label: '单行文本',labelWidth: null,showLabel: true,changeTag: true,tag: 'el-input',tagIcon: 'input',defaultValue: undefined,required: true,layout: 'colFormItem',span: 24,document: 'https://element.eleme.cn/#/zh-CN/component/input',// 正则校验规则regList: []},// 组件的插槽属性__slot__: {prepend: '',append: ''},// 其余的为可直接写在组件标签上的属性placeholder: '请输入',style: {width: '100%'},clearable: true,'prefix-icon': '','suffix-icon': '',maxlength: null,'show-word-limit': false,readonly: false,disabled: false},{__config__: {label: '多行文本',labelWidth: null,showLabel: true,tag: 'el-input',tagIcon: 'textarea',defaultValue: undefined,required: true,layout: 'colFormItem',span: 24,regList: [],changeTag: true,document: 'https://element.eleme.cn/#/zh-CN/component/input'},type: 'textarea',placeholder: '请输入',autosize: {minRows: 4,maxRows: 4},style: {width: '100%'},maxlength: null,'show-word-limit': false,readonly: false,disabled: false},{__config__: {label: '密码',showLabel: true,labelWidth: null,changeTag: true,tag: 'el-input',tagIcon: 'password',defaultValue: undefined,layout: 'colFormItem',span: 24,required: true,regList: [],document: 'https://element.eleme.cn/#/zh-CN/component/input'},__slot__: {prepend: '',append: ''},placeholder: '请输入','show-password': true,style: {width: '100%'},clearable: true,'prefix-icon': '','suffix-icon': '',maxlength: null,'show-word-limit': false,readonly: false,disabled: false},{__config__: {label: '计数器',showLabel: true,changeTag: true,labelWidth: null,tag: 'el-input-number',tagIcon: 'number',defaultValue: undefined,span: 24,layout: 'colFormItem',required: true,regList: [],document: 'https://element.eleme.cn/#/zh-CN/component/input-number'},placeholder: '',min: undefined,max: undefined,step: 1,'step-strictly': false,precision: undefined,'controls-position': '',disabled: false},{__config__: {label: '编辑器',showLabel: true,changeTag: true,labelWidth: null,tag: 'tinymce',tagIcon: 'keyInput',defaultValue: null,span: 24,layout: 'colFormItem',required: true,regList: [],document: 'http://tinymce.ax-z.cn'},placeholder: '请输入',height: 300, // 编辑器高度branding: false // 隐藏右下角品牌烙印},{__config__: {layout: 'tsSubform', // 拖拽处理方法tagIcon: 'row',tag: 'ts-sub-form', // 组件名称label: '子表单',showLabel: false,defaultValue: [], // v-modelchildren: [] // 子节点},addButton: true, // 默认可添加deleteButton: true, // 默认可删除displayShow: 'transverse',canEdit: true // 默认可编辑,为false时添加和删除都不可用,并且表单为disabled状态}
]// 选择型组件 【左面板】
export const selectComponents = [{__config__: {label: '下拉选择',showLabel: true,labelWidth: null,tag: 'el-select',tagIcon: 'select',layout: 'colFormItem',span: 24,required: true,regList: [],dataType: 'dynamic',dataTypeDetail: 'dynamic',dictType: '',changeTag: true,document: 'https://element.eleme.cn/#/zh-CN/component/select'},__slot__: {options: [{label: '选项一',value: 1}, {label: '选项二',value: 2}]},placeholder: '请选择',style: {width: '100%'},clearable: true,disabled: false,filterable: false,multiple: false},{__config__: {label: '部门选择',showLabel: true,labelWidth: null,tag: 'ts-select-tree',tagIcon: 'select',layout: 'colFormItem',span: 24,required: true,regList: [],dataType: 'dynamic',dataTypeDetail: 'dynamic',dictType: '',changeTag: true,document: 'https://element.eleme.cn/#/zh-CN/component/select'},__slot__: {options: [{"id": 100,"label": "A集团","children": [{"id": 367,"label": "AB发电公司","children": [{"id": 368,"label": "A电厂"},{"id": 369,"label": "B电厂"}]},{"id": 370,"label": "ABC发电公司","children": [{"id": 371,"label": "A发电厂"}]}]}]},placeholder: '请选择',style: {width: '100%'},clearable: true,disabled: false,filterable: false,multiple: false},{__config__: {label: '级联选择',url: 'https://www.fastmock.site/mock/f8d7a54fb1e60561e2f720d5a810009d/fg/cascaderList',method: 'get',dataPath: 'list',dataConsumer: 'options',showLabel: true,labelWidth: null,tag: 'el-cascader',tagIcon: 'cascader',layout: 'colFormItem',defaultValue: [],dataType: 'dynamic',span: 24,required: true,regList: [],changeTag: true,document: 'https://element.eleme.cn/#/zh-CN/component/cascader'},options: [{id: 1,value: 1,label: '选项1',children: [{id: 2,value: 2,label: '选项1-1'}]}],placeholder: '请选择',style: {width: '100%'},props: {props: {multiple: false,label: 'label',value: 'value',children: 'children'}},'show-all-levels': true,disabled: false,clearable: true,filterable: false,separator: '/'},{__config__: {label: '单选框组',labelWidth: null,showLabel: true,tag: 'el-radio-group',tagIcon: 'radio',changeTag: true,defaultValue: undefined,layout: 'colFormItem',span: 24,optionType: 'default',regList: [],required: true,border: false,document: 'https://element.eleme.cn/#/zh-CN/component/radio'},__slot__: {options: [{label: '选项一',value: 1}, {label: '选项二',value: 2}]},style: {},size: 'medium',disabled: false},{__config__: {label: '多选框组',tag: 'el-checkbox-group',tagIcon: 'checkbox',defaultValue: [],span: 24,showLabel: true,labelWidth: null,layout: 'colFormItem',optionType: 'default',required: true,regList: [],changeTag: true,border: false,document: 'https://element.eleme.cn/#/zh-CN/component/checkbox'},__slot__: {options: [{label: '选项一',value: 1}, {label: '选项二',value: 2}]},style: {},size: 'medium',min: null,max: null,disabled: false},{__config__: {label: '开关',tag: 'el-switch',tagIcon: 'switch',defaultValue: false,span: 24,showLabel: true,labelWidth: null,layout: 'colFormItem',required: true,regList: [],changeTag: true,document: 'https://element.eleme.cn/#/zh-CN/component/switch'},style: {},disabled: false,'active-text': '','inactive-text': '','active-color': null,'inactive-color': null,'active-value': true,'inactive-value': false},{__config__: {label: '滑块',tag: 'el-slider',tagIcon: 'slider',defaultValue: null,span: 24,showLabel: true,layout: 'colFormItem',labelWidth: null,required: true,regList: [],changeTag: true,document: 'https://element.eleme.cn/#/zh-CN/component/slider'},disabled: false,min: 0,max: 100,step: 1,'show-stops': false,range: false},{__config__: {label: '时间选择',tag: 'el-time-picker',tagIcon: 'time',defaultValue: null,span: 24,showLabel: true,layout: 'colFormItem',labelWidth: null,required: true,regList: [],changeTag: true,document: 'https://element.eleme.cn/#/zh-CN/component/time-picker'},placeholder: '请选择',style: {width: '100%'},disabled: false,clearable: true,'picker-options': {selectableRange: '00:00:00-23:59:59'},format: 'HH:mm:ss','value-format': 'HH:mm:ss'},{__config__: {label: '时间范围',tag: 'el-time-picker',tagIcon: 'time-range',span: 24,showLabel: true,labelWidth: null,layout: 'colFormItem',defaultValue: null,required: true,regList: [],changeTag: true,document: 'https://element.eleme.cn/#/zh-CN/component/time-picker'},style: {width: '100%'},disabled: false,clearable: true,'is-range': true,'range-separator': '至','start-placeholder': '开始时间','end-placeholder': '结束时间',format: 'HH:mm:ss','value-format': 'HH:mm:ss'},{__config__: {label: '日期选择',tag: 'el-date-picker',tagIcon: 'date',defaultValue: null,showLabel: true,labelWidth: null,span: 24,layout: 'colFormItem',required: true,regList: [],changeTag: true,document: 'https://element.eleme.cn/#/zh-CN/component/date-picker'},placeholder: '请选择',type: 'date',style: {width: '100%'},disabled: false,clearable: true,format: 'yyyy-MM-dd','value-format': 'yyyy-MM-dd',readonly: false},{__config__: {label: '日期范围',tag: 'el-date-picker',tagIcon: 'date-range',defaultValue: null,span: 24,showLabel: true,labelWidth: null,required: true,layout: 'colFormItem',regList: [],changeTag: true,document: 'https://element.eleme.cn/#/zh-CN/component/date-picker'},style: {width: '100%'},type: 'daterange','range-separator': '至','start-placeholder': '开始日期','end-placeholder': '结束日期',disabled: false,clearable: true,format: 'yyyy-MM-dd','value-format': 'yyyy-MM-dd',readonly: false},{__config__: {label: '评分',tag: 'el-rate',tagIcon: 'rate',defaultValue: 0,span: 24,showLabel: true,labelWidth: null,layout: 'colFormItem',required: true,regList: [],changeTag: true,document: 'https://element.eleme.cn/#/zh-CN/component/rate'},style: {},max: 5,'allow-half': false,'show-text': false,'show-score': false,disabled: false},{__config__: {label: '颜色选择',tag: 'el-color-picker',tagIcon: 'color',span: 24,defaultValue: null,showLabel: true,labelWidth: null,layout: 'colFormItem',required: true,regList: [],changeTag: true,document: 'https://element.eleme.cn/#/zh-CN/component/color-picker'},'show-alpha': false,'color-format': '',disabled: false,size: 'medium'},{__config__: {label: '上传',tag: 'el-upload',tagIcon: 'upload',layout: 'colFormItem',defaultValue: null,showLabel: true,labelWidth: null,required: true,span: 24,showTip: false,buttonText: '点击上传',regList: [],changeTag: true,fileSize: 2,sizeUnit: 'MB',document: 'https://element.eleme.cn/#/zh-CN/component/upload'},__slot__: {'list-type': true},action: 'https://jsonplaceholder.typicode.com/posts/',disabled: false,accept: '',name: 'file','auto-upload': true,'list-type': 'text',multiple: false}
]// 布局型组件 【左面板】
export const layoutComponents = [{__config__: {layout: 'rowFormItem',tagIcon: 'row',label: '行容器',layoutTree: true,document: 'https://element.eleme.cn/#/zh-CN/component/layout#row-attributes'},type: 'default',justify: 'start',align: 'top'},{__config__: {label: '按钮',showLabel: true,changeTag: true,labelWidth: null,tag: 'el-button',tagIcon: 'button',span: 24,layout: 'colFormItem',document: 'https://element.eleme.cn/#/zh-CN/component/button'},__slot__: {default: '主要按钮'},type: 'primary',icon: 'el-icon-search',round: false,size: 'medium',plain: false,circle: false,disabled: false},// {//   __config__: {//     layout: 'colFormItem',//     tagIcon: 'table',//     tag: 'el-table',//     document: 'https://element.eleme.cn/#/zh-CN/component/table',//     span: 24,//     formId: 101,//     renderKey: 1595761764203,//     componentName: 'row101',//     showLabel: true,//     changeTag: true,//     labelWidth: null,//     label: '表格[开发中]',//     dataType: 'dynamic',//     method: 'get',//     dataPath: 'list',//     dataConsumer: 'data',//     url: 'https://www.fastmock.site/mock/f8d7a54fb1e60561e2f720d5a810009d/fg/tableData',//     children: [{//       __config__: {//         layout: 'raw',//         tag: 'el-table-column',//         renderKey: 15957617660153//       },//       prop: 'date',//       label: '日期'//     }, {//       __config__: {//         layout: 'raw',//         tag: 'el-table-column',//         renderKey: 15957617660152//       },//       prop: 'address',//       label: '地址'//     }, {//       __config__: {//         layout: 'raw',//         tag: 'el-table-column',//         renderKey: 15957617660151//       },//       prop: 'name',//       label: '名称'//     }, {//       __config__: {//         layout: 'raw',//         tag: 'el-table-column',//         renderKey: 1595774496335,//         children: [//           {//             __config__: {//               label: '按钮',//               tag: 'el-button',//               tagIcon: 'button',//               layout: 'raw',//               renderKey: 1595779809901//             },//             __slot__: {//               default: '主要按钮'//             },//             type: 'primary',//             icon: 'el-icon-search',//             round: false,//             size: 'medium'//           }//         ]//       },//       label: '操作'//     }]//   },//   data: [],//   directives: [{//     name: 'loading',//     value: true//   }],//   border: true,//   type: 'default',//   justify: 'start',//   align: 'top'// }{__config__: {layout: 'colFormItem',tagIcon: 'table',tag: 'ts-designer-table',span: 24,formId: 101,componentName: 'row101',showLabel: false,changeTag: true,labelWidth: null,data: [],label: '表格布局',class: 'ts-designer-table',children: [{__config__: {layout: 'raw',tag: 'ts-designer-tr',opDomain: '',children: [{__config__: {layout: 'raw',tag: 'ts-designer-td',children: [{__config__: {layout: 'rowFormItem',type: 'TsDesignerTable',children: []},align: 'middle',justify: 'default',type: 'default'}]},style: {border: '1px solid #000',width: '',background: ''},colspan: 1,rowspan: 1}]}}]},border: true,type: 'default',justify: 'start',align: 'top'},{__config__: {formId: 102,label: '标签页', // 在home.vue页面左侧呈现的组件名称tagIcon: 'table', // 在home.vue页面左侧呈现的组件图标showLabel: false, // 是否在中间可视化区域默认显示labelchangeTag: false, // 是否在右侧操作面板可进行组件类型切换labelWidth: null, // 组件默认宽度defaultValue: 'first',componentName: 'row89757',tag: 'el-tabs', // 组件的名称span: 24, // 默认栅格布局数值layout: 'tsElTabs' // 在DraggableItem.vue中默认处理的方法},children: [{label: '用户管理',children: [], // 主要用于存储拖拽进来的子组件name: 'first'},{children: [],label: '配置管理',name: 'second'}],// 从这里开始就是el-tabs标签的属性 主要是在home.vue页面的右侧操作面板进行操作更改type: 'card', // 风格类型closable: false, // 标签是否可关闭addable: false, // 标签是否可增加editable: false, // 标签是否同时可增加和关闭'tab-position': 'top', // 选项卡所在位置stretch: false // 标签的宽度是否自撑开}
]

html.js

/* eslint-disable max-len */
import { trigger } from './config'let confGlobal
let someSpanIsNot24export function dialogWrapper(str) {return `<el-dialog v-bind="$attrs" v-on="$listeners" @open="onOpen" @close="onClose" title="Dialog Title">${str}<div slot="footer"><el-button @click="close">取消</el-button><el-button type="primary" @click="handleConfirm">确定</el-button></div></el-dialog>`
}export function vueTemplate(str) {return `<template><div>${str}</div></template>`
}export function vueScript(str) {return `<script>${str}</script>`
}export function cssStyle(cssStr) {return `<style>${cssStr}</style>`
}function buildFormTemplate(conf, child, type) {let labelPosition = ''if (conf.labelPosition !== 'right') {labelPosition = `label-position="${conf.labelPosition}"`}const disabled = conf.disabled ? `:disabled="${conf.disabled}"` : ''let str = `<el-form ref="${conf.formRef}" :model="${conf.formModel}" :rules="${conf.formRules}" size="${conf.size}" ${disabled} label-width="${conf.labelWidth}px" ${labelPosition}>${child}${buildFromBtns(conf, type)}</el-form>`if (someSpanIsNot24) {str = `<el-row :gutter="${conf.gutter}">${str}</el-row>`}return str
}function buildFromBtns(conf, type) {let str = ''if (conf.formBtns && type === 'file') {str = `<el-form-item size="large"><el-button type="primary" @click="submitForm">提交</el-button><el-button @click="resetForm">重置</el-button></el-form-item>`if (someSpanIsNot24) {str = `<el-col :span="24">${str}</el-col>`}}return str
}// span不为24的用el-col包裹
function colWrapper(element, str) {if (someSpanIsNot24 || element.span !== 24) {return `<el-col :span="${element.span}">${str}</el-col>`}return str
}const layouts = {colFormItem(element) {let labelWidth = ''if (element.labelWidth && element.labelWidth !== confGlobal.labelWidth) {labelWidth = `label-width="${element.labelWidth}px"`}const required = !trigger[element.tag] && element.required ? 'required' : ''const tagDom = tags[element.tag] ? tags[element.tag](element) : nulllet str = `<el-form-item ${labelWidth} label="${element.label}" prop="${element.vModel}" ${required}>${tagDom}</el-form-item>`str = colWrapper(element, str)return str},rowFormItem(element) {const type = element.type === 'default' ? '' : `type="${element.type}"`const justify = element.type === 'default' ? '' : `justify="${element.justify}"`const align = element.type === 'default' ? '' : `align="${element.align}"`const gutter = element.gutter ? `gutter="${element.gutter}"` : ''const children = element.children.map(el => layouts[el.layout](el))let str = `<el-row ${type} ${justify} ${align} ${gutter}>${children.join('\n')}</el-row>`str = colWrapper(element, str)return str},tsSubform(scheme) {const dataName = `:table-data="other.subForm${scheme.__config__.formId}"`const value = `v-model="other.subForm${scheme.__config__.formId}Data"`const addButton = `:addButton="other.addButton${scheme.__config__.formId}"`const deleteButton = `:deleteButton="other.deleteButton${scheme.__config__.formId}"`const displayShow = `:displayShow="other.displayShow${scheme.__config__.formId}"`const canEdit = `:canEdit="other.canEdit${scheme.__config__.formId}"`return `<ts-sub-form ${dataName} ${value} ${addButton} ${deleteButton} ${displayShow} ${canEdit}></ts-sub-form>`},raw(scheme) {let str = ''if (scheme.style && scheme.style.display) {return str}if (scheme.__config__.tag === 'ts-designer-tr' || scheme.__config__.tag === 'ts-designer-td') {const config = scheme.__config__const tagDom = tags[config.tag] ? tags[config.tag](scheme) : nullstr = `${tagDom}`}return str},tsElTabs(scheme) {const config = scheme.__config__const tagDom = tags[config.tag] ? tags[config.tag](scheme) : nulllet str = tagDomstr = colWrapper(scheme, str)return str}}const tags = {'el-button': el => {const {tag, disabled} = attrBuilder(el)const type = el.type ? `type="${el.type}"` : ''const icon = el.icon ? `icon="${el.icon}"` : ''const size = el.size ? `size="${el.size}"` : ''let child = buildElButtonChild(el)if (child) child = `\n${child}\n` // 换行return `<${el.tag} ${type} ${icon} ${size} ${disabled}>${child}</${el.tag}>`},'el-input': el => {const {disabled, vModel, clearable, placeholder, width} = attrBuilder(el)const maxlength = el.maxlength ? `:maxlength="${el.maxlength}"` : ''const showWordLimit = el['show-word-limit'] ? 'show-word-limit' : ''const readonly = el.readonly ? 'readonly' : ''const prefixIcon = el['prefix-icon'] ? `prefix-icon='${el['prefix-icon']}'` : ''const suffixIcon = el['suffix-icon'] ? `suffix-icon='${el['suffix-icon']}'` : ''const showPassword = el['show-password'] ? 'show-password' : ''const type = el.type ? `type="${el.type}"` : ''const autosize = el.autosize && el.autosize.minRows? `:autosize="{minRows: ${el.autosize.minRows}, maxRows: ${el.autosize.maxRows}}"`: ''let child = buildElInputChild(el)if (child) child = `\n${child}\n` // 换行return `<${el.tag} ${vModel} ${type} ${placeholder} ${maxlength} ${showWordLimit} ${readonly} ${disabled} ${clearable} ${prefixIcon} ${suffixIcon} ${showPassword} ${autosize} ${width}>${child}</${el.tag}>`},'el-input-number': el => {const { disabled, vModel, placeholder } = attrBuilder(el)const controlsPosition = el['controls-position'] ? `controls-position=${el['controls-position']}` : ''const min = el.min ? `:min='${el.min}'` : ''const max = el.max ? `:max='${el.max}'` : ''const step = el.step ? `:step='${el.step}'` : ''const stepStrictly = el['step-strictly'] ? 'step-strictly' : ''const precision = el.precision ? `:precision='${el.precision}'` : ''return `<${el.tag} ${vModel} ${placeholder} ${step} ${stepStrictly} ${precision} ${controlsPosition} ${min} ${max} ${disabled}></${el.tag}>`},'el-select': el => {const {disabled, vModel, clearable, placeholder, width} = attrBuilder(el)const filterable = el.filterable ? 'filterable' : ''const multiple = el.multiple ? 'multiple' : ''let child = buildElSelectChild(el)if (child) child = `\n${child}\n` // 换行return `<${el.tag} ${vModel} ${placeholder} ${disabled} ${multiple} ${filterable} ${clearable} ${width}>${child}</${el.tag}>`},'el-radio-group': el => {const { disabled, vModel } = attrBuilder(el)const size = `size="${el.size}"`let child = buildElRadioGroupChild(el)if (child) child = `\n${child}\n` // 换行return `<${el.tag} ${vModel} ${size} ${disabled}>${child}</${el.tag}>`},'el-checkbox-group': el => {const { disabled, vModel } = attrBuilder(el)const size = `size="${el.size}"`const min = el.min ? `:min="${el.min}"` : ''const max = el.max ? `:max="${el.max}"` : ''let child = buildElCheckboxGroupChild(el)if (child) child = `\n${child}\n` // 换行return `<${el.tag} ${vModel} ${min} ${max} ${size} ${disabled}>${child}</${el.tag}>`},'el-switch': el => {const { disabled, vModel } = attrBuilder(el)const activeText = el['active-text'] ? `active-text="${el['active-text']}"` : ''const inactiveText = el['inactive-text'] ? `inactive-text="${el['inactive-text']}"` : ''const activeColor = el['active-color'] ? `active-color="${el['active-color']}"` : ''const inactiveColor = el['inactive-color'] ? `inactive-color="${el['inactive-color']}"` : ''const activeValue = el['active-value'] !== true ? `:active-value='${JSON.stringify(el['active-value'])}'` : ''const inactiveValue = el['inactive-value'] !== false ? `:inactive-value='${JSON.stringify(el['inactive-value'])}'` : ''return `<${el.tag} ${vModel} ${activeText} ${inactiveText} ${activeColor} ${inactiveColor} ${activeValue} ${inactiveValue} ${disabled}></${el.tag}>`},'el-cascader': el => {const {disabled, vModel, clearable, placeholder, width} = attrBuilder(el)const options = el.options ? `:options="${el.vModel}Options"` : ''const props = el.props ? `:props="${el.vModel}Props"` : ''const showAllLevels = el['show-all-levels'] ? '' : ':show-all-levels="false"'const filterable = el.filterable ? 'filterable' : ''const separator = el.separator === '/' ? '' : `separator="${el.separator}"`return `<${el.tag} ${vModel} ${options} ${props} ${width} ${showAllLevels} ${placeholder} ${separator} ${filterable} ${clearable} ${disabled}></${el.tag}>`},'el-slider': el => {const { disabled, vModel } = attrBuilder(el)const min = el.min ? `:min='${el.min}'` : ''const max = el.max ? `:max='${el.max}'` : ''const step = el.step ? `:step='${el.step}'` : ''const range = el.range ? 'range' : ''const showStops = el['show-stops'] ? `:show-stops="${el['show-stops']}"` : ''return `<${el.tag} ${min} ${max} ${step} ${vModel} ${range} ${showStops} ${disabled}></${el.tag}>`},'el-time-picker': el => {const {disabled, vModel, clearable, placeholder, width} = attrBuilder(el)const startPlaceholder = el['start-placeholder'] ? `start-placeholder="${el['start-placeholder']}"` : ''const endPlaceholder = el['end-placeholder'] ? `end-placeholder="${el['end-placeholder']}"` : ''const rangeSeparator = el['range-separator'] ? `range-separator="${el['range-separator']}"` : ''const isRange = el['is-range'] ? 'is-range' : ''const format = el.format ? `format="${el.format}"` : ''const valueFormat = el['value-format'] ? `value-format="${el['value-format']}"` : ''const pickerOptions = el['picker-options'] ? `:picker-options='${JSON.stringify(el['picker-options'])}'` : ''return `<${el.tag} ${vModel} ${isRange} ${format} ${valueFormat} ${pickerOptions} ${width} ${placeholder} ${startPlaceholder} ${endPlaceholder} ${rangeSeparator} ${clearable} ${disabled}></${el.tag}>`},'el-date-picker': el => {const {disabled, vModel, clearable, placeholder, width} = attrBuilder(el)const startPlaceholder = el['start-placeholder'] ? `start-placeholder="${el['start-placeholder']}"` : ''const endPlaceholder = el['end-placeholder'] ? `end-placeholder="${el['end-placeholder']}"` : ''const rangeSeparator = el['range-separator'] ? `range-separator="${el['range-separator']}"` : ''const format = el.format ? `format="${el.format}"` : ''const valueFormat = el['value-format'] ? `value-format="${el['value-format']}"` : ''const type = el.type === 'date' ? '' : `type="${el.type}"`const readonly = el.readonly ? 'readonly' : ''return `<${el.tag} ${type} ${vModel} ${format} ${valueFormat} ${width} ${placeholder} ${startPlaceholder} ${endPlaceholder} ${rangeSeparator} ${clearable} ${readonly} ${disabled}></${el.tag}>`},'el-rate': el => {const { disabled, vModel } = attrBuilder(el)const max = el.max ? `:max='${el.max}'` : ''const allowHalf = el['allow-half'] ? 'allow-half' : ''const showText = el['show-text'] ? 'show-text' : ''const showScore = el['show-score'] ? 'show-score' : ''return `<${el.tag} ${vModel} ${allowHalf} ${showText} ${showScore} ${disabled}></${el.tag}>`},'el-color-picker': el => {const { disabled, vModel } = attrBuilder(el)const size = `size="${el.size}"`const showAlpha = el['show-alpha'] ? 'show-alpha' : ''const colorFormat = el['color-format'] ? `color-format="${el['color-format']}"` : ''return `<${el.tag} ${vModel} ${size} ${showAlpha} ${colorFormat} ${disabled}></${el.tag}>`},'el-upload': el => {const disabled = el.disabled ? ':disabled=\'true\'' : ''const action = el.action ? `:action="${el.vModel}Action"` : ''const multiple = el.multiple ? 'multiple' : ''const listType = el['list-type'] !== 'text' ? `list-type="${el['list-type']}"` : ''const accept = el.accept ? `accept="${el.accept}"` : ''const name = el.name !== 'file' ? `name="${el.name}"` : ''const autoUpload = el['auto-upload'] === false ? ':auto-upload="false"' : ''const beforeUpload = `:before-upload="${el.vModel}BeforeUpload"`const fileList = `:file-list="${el.vModel}fileList"`const ref = `ref="${el.vModel}"`let child = buildElUploadChild(el)if (child) child = `\n${child}\n` // 换行return `<${el.tag} ${ref} ${fileList} ${action} ${autoUpload} ${multiple} ${beforeUpload} ${listType} ${accept} ${name} ${disabled}>${child}</${el.tag}>`},'ts-sub-form': el => {const dataName = `:table-data="other.subForm${el.__config__.formId}"`const value = `v-model="other.subForm${el.__config__.formId}Data"`const addButton = `:addButton="other.addButton${el.__config__.formId}"`const deleteButton = `:deleteButton="other.deleteButton${el.__config__.formId}"`const displayShow = `:displayShow="other.displayShow${el.__config__.formId}"`const canEdit = `:canEdit="other.canEdit${el.__config__.formId}"`return `<ts-sub-form ${dataName} ${value} ${addButton} ${deleteButton} ${displayShow} ${canEdit}></ts-sub-form>`},'ts-text': el => {const {clearable, placeholder, width} = attrBuilder(el)const text = el.__slot__.spanconst { style } = ellet styles = ''// eslint-disable-next-line guard-for-in,no-restricted-syntaxfor (const key in style) {styles += `${key}:${style[key]};`}return `<div ${clearable} style="${styles}" ${placeholder}><span>${text}</span></div>`},'ts-designer-table': el => {const child = tsDesignerAttrBuilder(el)return `<table class="ts-designer-table">${child}</table>`},'ts-designer-tr': el => {const child = tsDesignerAttrBuilder(el)return `<tr >${child}</tr>`},'ts-designer-td': el => {const child = tsDesignerTdAttrBuilder(el)const { style } = ellet syles = ''// eslint-disable-next-line guard-for-in,no-restricted-syntaxfor (const key in style) {syles += `${key}:${style[key]};`}syles = `"${syles}"`return `<td class="ts-designer-td" style=${syles} colspan=${el.colspan} rowspan=${el.rowspan}>${child}</td>`},'el-tabs': el => {const { tag, vModel } = attrBuilder(el)const type = el.type ? `type="${el.type}"` : ''const closable = el.closable ? `type="${el.closable}"` : ''const tabPosition = el['tab-position'] ? `tab-position="${el['tab-position']}"` : ''const child = exportTabsChild(el)return `<${tag} ${type} ${vModel} ${closable} ${tabPosition}>${child}</${tag}>`}
}
function exportTabsChild(scheme) {debuggerconst childrenList = []const { children } = schemefor (let i = 0; i < children.length; i++) {let childHtml = []for (let j = 0; j < children[i].children.length; j++) {if (children[i].children[j]) {const oneChildHtml = layouts[children[i].children[j].__config__.layout](children[i].children[j])childHtml.push(oneChildHtml)}}childHtml = childHtml.join('\n')childrenList.push(`<el-tab-pane label='${children[i].label}'>${childHtml}</el-tab-pane>`)}return childrenList.join('\n')
}
function attrBuilder(el) {return {vModel: `v-model="${confGlobal.formModel}.${el.vModel}"`,clearable: el.clearable ? 'clearable' : '',placeholder: el.placeholder ? `placeholder="${el.placeholder}"` : '',width: el.style && el.style.width ? ':style="{width: \'100%\'}"' : '',disabled: el.disabled ? ':disabled=\'true\'' : ''}
}
function tsDesignerAttrBuilder(el) {const children = []for (let i = 0; i < el.__config__.children.length; i++) {if (el.__config__.children[i]) {const trHtml = layouts[el.__config__.children[i].__config__.layout](el.__config__.children[i])children.push(`${trHtml}`)}}return children.join('\n')
}function tsDesignerTdAttrBuilder(el) {const children = []const trHtml = layouts[el.__config__.children[0].__config__.layout](el.__config__.children[0])children.push(`${trHtml}`)return children.join('\n')
}
// el-buttin 子级
function buildElButtonChild(conf) {const children = []if (conf.default) {children.push(conf.default)}return children.join('\n')
}// el-input innerHTML
function buildElInputChild(conf) {const children = []if (conf.prepend) {children.push(`<template slot="prepend">${conf.prepend}</template>`)}if (conf.append) {children.push(`<template slot="append">${conf.append}</template>`)}return children.join('\n')
}function buildElSelectChild(conf) {const children = []if (conf.options && conf.options.length) {children.push(`<el-option v-for="(item, index) in ${conf.vModel}Options" :key="index" :label="item.label" :value="item.value" :disabled="item.disabled"></el-option>`)}return children.join('\n')
}function buildElRadioGroupChild(conf) {const children = []if (conf.options && conf.options.length) {const tag = conf.optionType === 'button' ? 'el-radio-button' : 'el-radio'const border = conf.border ? 'border' : ''children.push(`<${tag} v-for="(item, index) in ${conf.vModel}Options" :key="index" :label="item.value" :disabled="item.disabled" ${border}>{{item.label}}</${tag}>`)}return children.join('\n')
}function buildElCheckboxGroupChild(conf) {const children = []if (conf.options && conf.options.length) {const tag = conf.optionType === 'button' ? 'el-checkbox-button' : 'el-checkbox'const border = conf.border ? 'border' : ''children.push(`<${tag} v-for="(item, index) in ${conf.vModel}Options" :key="index" :label="item.value" :disabled="item.disabled" ${border}>{{item.label}}</${tag}>`)}return children.join('\n')
}function buildElUploadChild(conf) {const list = []if (conf['list-type'] === 'picture-card') list.push('<i class="el-icon-plus"></i>')else list.push(`<el-button size="small" type="primary" icon="el-icon-upload">${conf.buttonText}</el-button>`)if (conf.showTip) list.push(`<div slot="tip" class="el-upload__tip">只能上传不超过 ${conf.fileSize}${conf.sizeUnit} 的${conf.accept}文件</div>`)return list.join('\n')
}export function makeUpHtml(conf, type) {const htmlList = []confGlobal = confsomeSpanIsNot24 = conf.fields.some(item => item.span !== 24)conf.fields.forEach(el => {htmlList.push(layouts[el.layout](el))})const htmlStr = htmlList.join('\n')let temp = buildFormTemplate(conf, htmlStr, type)if (type === 'dialog') {temp = dialogWrapper(temp)}confGlobal = nullreturn temp
}

js.js

import { isArray } from 'util'
import { exportDefault, titleCase, deepClone } from '@/utils/index'
import ruleTrigger from './ruleTrigger'const units = {KB: '1024',MB: '1024 / 1024',GB: '1024 / 1024 / 1024'
}
let confGlobal
const inheritAttrs = {file: '',dialog: 'inheritAttrs: false,'
}/*** 组装js 【入口函数】* @param {Object} formConfig 整个表单配置* @param {String} type 生成类型,文件或弹窗等*/
export function makeUpJs(formConfig, type) {confGlobal = formConfig = deepClone(formConfig)const dataList = []const ruleList = []const optionsList = []const propsList = []const methodList = mixinMethod(type)const uploadVarList = []const created = []const other = []formConfig.fields.forEach(el => {buildAttributes(el, dataList, ruleList, optionsList, methodList, propsList, uploadVarList, created, other)})const script = buildexport(formConfig,type,dataList.join('\n'),ruleList.join('\n'),optionsList.join('\n'),uploadVarList.join('\n'),propsList.join('\n'),methodList.join('\n'),created.join('\n'),other.join('\n'))confGlobal = nullreturn script
}// 构建组件属性
// eslint-disable-next-line max-len
function buildAttributes(scheme, dataList, ruleList, optionsList, methodList, propsList, uploadVarList, created, other) {const config = scheme.__config__const slot = scheme.__slot__buildData(scheme, dataList, other)buildRules(scheme, ruleList)// 主要就是这一段代码的新增,其他地方都没有更改if (config.tag === 'el-tabs') {scheme.children.forEach(item => {item.children.forEach(el => {buildAttributes(el, dataList, ruleList, optionsList, methodList, propsList, uploadVarList, created)})})}// 特殊处理options属性if (scheme.options || (slot && slot.options && slot.options.length)) {buildOptions(scheme, optionsList)if (config.dataType === 'dynamic') {const model = `${scheme.__vModel__}Options`const options = titleCase(model)const methodName = `get${options}`buildOptionMethod(methodName, model, methodList, scheme)callInCreated(methodName, created)}}// 处理propsif (scheme.props && scheme.props.props) {buildProps(scheme, propsList)}// 处理el-upload的actionif (scheme.action && config.tag === 'el-upload') {uploadVarList.push(`${scheme.__vModel__}Action: '${scheme.action}',${scheme.__vModel__}fileList: [],`)methodList.push(buildBeforeUpload(scheme))// 非自动上传时,生成手动上传的函数if (!scheme['auto-upload']) {methodList.push(buildSubmitUpload(scheme))}}// 构建子级组件属性if (config.children) {config.children.forEach(item => {buildAttributes(item, dataList, ruleList, optionsList, methodList, propsList, uploadVarList, created)})}
}// 在Created调用函数
function callInCreated(methodName, created) {created.push(`this.${methodName}()`)
}// 混入处理函数
function mixinMethod(type) {const list = []; constminxins = {file: confGlobal.formBtns ? {submitForm: `submitForm() {this.$refs['${confGlobal.formRef}'].validate(valid => {if(!valid) return// TODO 提交表单})},`,resetForm: `resetForm() {this.$refs['${confGlobal.formRef}'].resetFields()},`} : null,dialog: {onOpen: 'onOpen() {},',onClose: `onClose() {this.$refs['${confGlobal.formRef}'].resetFields()},`,close: `close() {this.$emit('update:visible', false)},`,handelConfirm: `handelConfirm() {this.$refs['${confGlobal.formRef}'].validate(valid => {if(!valid) returnthis.close()})},`}}const methods = minxins[type]if (methods) {Object.keys(methods).forEach(key => {list.push(methods[key])})}return list
}// 构建data
function buildData(scheme, dataList, other) {const config = scheme.__config__if (config.tag === 'ts-sub-form') {const subformData = []if (scheme.__config__.children.length > 0) {scheme.__config__.children.forEach(item => {const basicsData = JSON.parse(JSON.stringify(item))basicsData.__config__.prop = item.__vModel__basicsData.disabled = item.disabledbasicsData.readonly = item.readonlysubformData.push(basicsData)})}other.push(`subForm${config.formId}: ${JSON.stringify(subformData)},`)other.push(`subForm${config.formId}Data: ${JSON.stringify(config.defaultValue)},`)other.push(`addButton${config.formId}: ${JSON.stringify(scheme.addButton)},`)other.push(`canEdit${config.formId}: ${JSON.stringify(scheme.canEdit)},`)other.push(`deleteButton${config.formId}: ${JSON.stringify(scheme.deleteButton)},`)other.push(`displayShow${config.formId}: ${JSON.stringify(scheme.displayShow)},`)return} if (scheme.__vModel__ === undefined) returnconst defaultValue = JSON.stringify(config.defaultValue)dataList.push(`${scheme.__vModel__}: ${defaultValue},`)
}// 构建校验规则
function buildRules(scheme, ruleList) {const config = scheme.__config__if (scheme.__vModel__ === undefined) returnconst rules = []if (ruleTrigger[config.tag]) {if (config.required) {const type = isArray(config.defaultValue) ? 'type: \'array\',' : ''let message = isArray(config.defaultValue) ? `请至少选择一个${config.label}` : scheme.placeholderif (message === undefined) message = `${config.label}不能为空`rules.push(`{ required: true, ${type} message: '${message}', trigger: '${ruleTrigger[config.tag]}' }`)}if (config.regList && isArray(config.regList)) {config.regList.forEach(item => {if (item.pattern) {rules.push(`{ pattern: ${eval(item.pattern)}, message: '${item.message}', trigger: '${ruleTrigger[config.tag]}' }`)}})}ruleList.push(`${scheme.__vModel__}: [${rules.join(',')}],`)}
}// 构建options
function buildOptions(scheme, optionsList) {if (scheme.__vModel__ === undefined) return// el-cascader直接有options属性,其他组件都是定义在slot中,所以有两处判断let { options } = schemeif (!options) options = scheme.__slot__.optionsif (scheme.__config__.dataType === 'dynamic') { options = [] }const str = `${scheme.__vModel__}Options: ${JSON.stringify(options)},`optionsList.push(str)
}function buildProps(scheme, propsList) {const str = `${scheme.__vModel__}Props: ${JSON.stringify(scheme.props.props)},`propsList.push(str)
}// el-upload的BeforeUpload
function buildBeforeUpload(scheme) {const config = scheme.__config__const unitNum = units[config.sizeUnit]; let rightSizeCode = ''; let acceptCode = ''; constreturnList = []if (config.fileSize) {rightSizeCode = `let isRightSize = file.size / ${unitNum} < ${config.fileSize}if(!isRightSize){this.$message.error('文件大小超过 ${config.fileSize}${config.sizeUnit}')}`returnList.push('isRightSize')}if (scheme.accept) {acceptCode = `let isAccept = new RegExp('${scheme.accept}').test(file.type)if(!isAccept){this.$message.error('应该选择${scheme.accept}类型的文件')}`returnList.push('isAccept')}const str = `${scheme.__vModel__}BeforeUpload(file) {${rightSizeCode}${acceptCode}return ${returnList.join('&&')}},`return returnList.length ? str : ''
}// el-upload的submit
function buildSubmitUpload(scheme) {const str = `submitUpload() {this.$refs['${scheme.__vModel__}'].submit()},`return str
}function buildOptionMethod(methodName, model, methodList, scheme) {const config = scheme.__config__const str = `${methodName}() {// 注意:this.$axios是通过Vue.prototype.$axios = axios挂载产生的this.$axios({method: '${config.method}',url: '${config.url}'}).then(resp => {var { data } = respthis.${model} = data.${config.dataPath}})},`methodList.push(str)
}// js整体拼接
function buildexport(conf, type, data, rules, selectOptions, uploadVar, props, methods, created, other) {const str = `${exportDefault}{${inheritAttrs[type]}components: {},props: [],data () {return {${conf.other}: {${other}},${conf.formModel}: {${data}},${conf.formRules}: {${rules}},${uploadVar}${selectOptions}${props}}},computed: {},watch: {},created () {${created}},mounted () {},methods: {${methods}}
}`return str
}

表格组件源码要的私聊我!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/285708.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

LeetCode每日一题[c++]-322.零钱兑换

题目描述 给你一个整数数组 coins &#xff0c;表示不同面额的硬币&#xff1b;以及一个整数 amount &#xff0c;表示总金额。 计算并返回可以凑成总金额所需的 最少的硬币个数 。如果没有任何一种硬币组合能组成总金额&#xff0c;返回 -1 。 你可以认为每种硬币的数量是无…

游戏提示steam_api64.dll丢失怎样修复?教你5种快速修复的方法

在计算机系统中&#xff0c;如果未能成功找到或加载steam_api64.dll文件&#xff0c;可能会引发一系列的问题和故障现象。这个特定的DLL文件是Steam平台的核心组件之一&#xff0c;对于运行基于Steam平台的游戏或应用至关重要。当系统提示“找不到steam_api64.dll”时&#xff…

抖音视频关键词爬虫批量采集软件|视频提取下载工具

视频关键词批量采集软件 — 助力您快速获取所需视频 主要功能&#xff1a; 关键词批量提取视频和单独视频提取&#xff0c;提取后下载功能。 功能解析&#xff1a; 1. 关键词批量提取视频的解析 通过输入关键词进行视频搜索和提取。例如&#xff0c;输入“汽车配件”&#x…

N9010B EXA 信号分析仪 10 Hz 至 44 GHz

N9010B EXA 信号分析仪 10 Hz 至 44 GHz 产品综述 <<<<频率范围&#xff1a;10 Hz 至 44 GHz>>> keysight N9010B EXA 信号分析仪&#xff0c;10 Hz 至 44 GHz无论是增强产品性能还是提高测试吞吐量&#xff0c;您的通用型信号分析仪都要有能力满足各…

为什么电商系统一定要跟企业ERP做数据对接?

一篇文章告诉你&#xff0c;为什么电商系统一定要跟企业ERP做数据对接&#xff1f; 在电商日益发展的情况下&#xff0c;每个电商企业的单量越来越大。但是电商系统对于财务来说并不友好&#xff0c;所以企业会另外上一套财务系统方便财务做账和企业内部管理。那如果还是按照之…

后端常问面经之操作系统

请简要描述线程与进程的关系,区别及优缺点&#xff1f; 本质区别&#xff1a;进程是操作系统资源分配的基本单位&#xff0c;而线程是任务调度和执行的基本单位 在开销方面&#xff1a;每个进程都有独立的代码和数据空间&#xff08;程序上下文&#xff09;&#xff0c;程序之…

产品经理面试自我介绍,这3大错误千万别犯!

金三银四求职季&#xff0c;你是不是也有面试的冲动&#xff01;但面试并不是头脑一热就能取得好结果&#xff0c;在此之前&#xff0c;必须得有周全的准备&#xff0c;才能应对好面试官的“连环问”&#xff01; 所以&#xff0c;今天这篇产品经理面试干货分享给大家~ 今天文…

MySQL-1.数据库的基本操作

1. 数据库的基本操作 show databases; information_schema&#xff1a;信息图式&#xff0c;存储服务器管理数据库的信息 mysql&#xff1a;存放系统信息&#xff0c;用户名密码等 performance_schema&#xff1a;性能图式 sys&#xff1a;系统文件 1.1 创建数据库-studen…

流畅的 Python 第二版(GPT 重译)(六)

第三部分&#xff1a;类和协议 第十一章&#xff1a;一个 Python 风格的对象 使库或框架成为 Pythonic 是为了让 Python 程序员尽可能轻松和自然地学会如何执行任务。 Python 和 JavaScript 框架的创造者 Martijn Faassen。 由于 Python 数据模型&#xff0c;您定义的类型可以…

【设计模式】实战篇

目录标题 【实战一】模板方法模式抽象类子类 【实战一】模板方法模式 抽象类 定义一个抽象类&#xff1a;FarmWorkNodeRecord&#xff1a;表示其记录是用来操作计划的节点对象的。 public abstract class FarmWorkNodeRecordService {// 模拟Mapperprivate String plantPlan…

Arduino中的map函数

一、案例 val analogRead(dyPin); //读取模拟口的模拟量数值 dyValuemap(val,0,1023,0,500);//这个函数是将电位器调节的模拟量的值按比例转换成对应的电压量 问题&#xff0c;为什么不是0~499呢&#xff1f; 其实也行↓ 当map(val, 0, 1023, 0, 500)被调用时&#xff0…

关于异业联盟模式做成小程序的可行性分析

随着移动互联网的快速发展&#xff0c;小程序作为一种轻量级应用&#xff0c;受到了越来越多企业和用户的青睐。而异业联盟模式则是一种有效的商业合作方式&#xff0c;能够实现资源共享、优势互补和共同发展。将异业联盟模式做成小程序&#xff0c;不仅可以提高用户体验&#…

[论文笔记] Dual-Channel Span for Aspect Sentiment Triplet Extraction

一种利用句法依赖和词性相关性信息来过滤噪声&#xff08;无关跨度&#xff09;的基于span方法。 会议EMNLP 2023作者Pan Li, Ping Li, Kai Zhang团队Southwest Petroleum University论文地址https://aclanthology.org/2023.emnlp-main.17/代码地址https://github.com/bert-ply…

海外盲盒APP系统开发,探寻盲盒的海外机遇

目前&#xff0c;盲盒在我国受到了消费者的欢迎。在各类影视动漫的火热下&#xff0c;热衷于娱乐消费的年轻人成为了盲盒的主要消费人群。 在国外&#xff0c;盲盒也同样深受海外消费者的喜爱。近几年&#xff0c;盲盒在海外的销售量急速上升&#xff0c;创下了新高。 随着盲…

Windows 7 一键恢复 - 联想拯救系统

Windows 7 一键恢复 - 联想拯救系统 1. 联想拯救系统1.1. OEM 分区1.2. 一键恢复 References 1. 联想拯救系统 1.1. OEM 分区 计算机 -> 管理 -> 存储 -> 磁盘管理 1.2. 一键恢复 重新启动电脑 F11 -> 从初始备份恢复 References [1] Yongqiang Cheng, https…

2024年国产最好的家用投影仪!当贝极米坚果稳居口碑销量前三

国产投影仪在2024年已经极为成熟&#xff0c;也具有极为丰富的挑选余地。但如何选择合适的品牌和型号&#xff0c;一直是很多人的困惑。不过国产家用投影仪哪个最好&#xff0c;性价比最高都其实非常容易分辨。这次也来盘点下2024年最新排行榜&#xff0c;给大家无需复杂攻略即…

蓝桥杯day7刷题日记

P8697 [蓝桥杯 2019 国 C] 最长子序列 思路&#xff1a;直接遍历&#xff0c;和子序列相同就记录&#xff0c;不然就下一位 #include <iostream> #include <string> using namespace std; int res;int main() {string s,t;cin>>s>>t;int i0,j0;while…

Linux中的常用基础操作

ls 列出当前目录下的子目录和文件 ls -a 列出当前目录下的所有内容&#xff08;包括以.开头的隐藏文件&#xff09; ls [目录名] 列出指定目录下的子目录和文件 ls -l 或 ll 以列表的形式列出当前目录下子目录和文件的详细信息 pwd 显示当前所在目录的路径 ctrll 清屏 cd…

报表控件Stimulsoft Reports、Dashboards 和 Forms 新版v2024.2发布!

我们很高兴地宣布发布用于创建报告、仪表板和表单的最新版本的 Stimulsoft 产品 - 2024.2&#xff01;在此更新中&#xff0c;您将找到适用于 Python 应用程序和服务的产品、新的仪表板元素、我们的组件与 .NET 8.0 的兼容性、仪表板交互性的增强功能等等。 Stimulsoft Ultima…

vulhub中Apache Shiro 1.2.4反序列化漏洞复现(CVE-2016-4437)

Apache Shiro是一款开源安全框架&#xff0c;提供身份验证、授权、密码学和会话管理。Shiro框架直观、易用&#xff0c;同时也能提供健壮的安全性。 Apache Shiro 1.2.4及以前版本中&#xff0c;加密的用户信息序列化后存储在名为remember-me的Cookie中。攻击者可以使用Shiro的…