Browse Source

add editor radio other

fix style
old
wangqing 5 years ago
parent
commit
17632466e8
  1. 7
      src/assets/styles/form/home.scss
  2. 67
      src/components/parser/Parser.vue
  3. 43
      src/components/render/render.js
  4. 30
      src/components/render/slots/el-checkbox-group.js
  5. 30
      src/components/render/slots/el-radio-group.js
  6. 3
      src/components/tinymce/index.vue
  7. 2
      src/router/modules/root.js
  8. 1
      src/utils/convert.js
  9. 228
      src/views/form/DraggableItem.vue
  10. 2
      src/views/form/ProjectForm.vue
  11. 1969
      src/views/form/RightPanel.vue
  12. 2
      src/views/form/editor.vue
  13. 7
      src/views/project/MyProject.vue
  14. 28
      src/views/test.vue

7
src/assets/styles/form/home.scss

@ -1,5 +1,5 @@
$selectedColor: #f5f8ff;
$lighterBlue: #4aa0fa;
$selectedColor: #fafafa;
$lighterBlue: #e4efff;
.form-edit-container {
position: relative;
width: 100%;
@ -55,7 +55,7 @@ $lighterBlue: #4aa0fa;
left: 40px;
top: 0;
height: 100vh;
//background-color: rgba(255, 255, 255, 100);
}
.el-menu.el-menu--horizontal {
border-bottom: none;
@ -65,6 +65,7 @@ $lighterBlue: #4aa0fa;
overflow: hidden;
margin: 5px;
border-radius: 7px;
background-color: rgba(255, 255, 255, 100);
//text-align: center;
box-shadow: 0 1px 6px 0 rgba(0, 0, 0, 0.4);
border: 1px solid rgba(255, 255, 255, 100);

67
src/components/parser/Parser.vue

@ -160,19 +160,44 @@ function setValue(event, config, scheme) {
setValueLabel.call(this, event, config, scheme)
}
/**
* radio checkbox 其他输入框值处理
*/
function setOtherValueLabel(event, config) {
let value = this[this.formConf.formModel][config.__vModel__]
this.$set(this[this.formConf.labelFormModel], `${config.__vModel__}other`, event)
setValueLabel.call(this, value, config.__config__, config)
}
/**
* 保存选项的label值
* @param event
* @param config
* @param scheme
*/
function setValueLabel(event, config, scheme) {
let tagOptionKey = processType[config.tag]
if (tagOptionKey) {
if (event instanceof Array) {
let labelStr = ''
let labelArr = new Array()
event.forEach(item => {
let {label} = getObject(_.get(scheme, tagOptionKey), 'value', item)
labelStr += label + ','
//
if (item === 0) {
labelArr.push(this[this.formConf.labelFormModel][`${scheme.__vModel__}other`])
}else{
let {label} = getObject(_.get(scheme, tagOptionKey), 'value', item)
labelArr.push(label)
}
})
this.$set(this[this.formConf.labelFormModel], scheme.__vModel__, labelStr)
this.$set(this[this.formConf.labelFormModel], scheme.__vModel__, labelArr.join(','))
} else {
let item = _.find(_.get(scheme, tagOptionKey), {'value': event})
this.$set(this[this.formConf.labelFormModel], scheme.__vModel__, item.label)
//
if (event == 0) {
this.$set(this[this.formConf.labelFormModel], `${config.__vModel__}`, this[this.formConf.labelFormModel][`${config.__vModel__}other`])
} else {
let item = _.find(_.get(scheme, tagOptionKey), {'value': event})
this.$set(this[this.formConf.labelFormModel], scheme.__vModel__, item.label)
}
}
} else if (config.tag === 'el-upload') {
this.$set(this[this.formConf.labelFormModel], scheme.__vModel__, event)
@ -206,7 +231,7 @@ function buildListeners(scheme) {
listeners.input = event => setValue.call(this, event, config, scheme)
listeners.upload = (response, file, fileList) => setUpload.call(this, config, scheme, response, file, fileList)
listeners.deleteUpload = (file, fileList) => deleteUpload.call(this, config, scheme, file, fileList)
listeners.selectOtherChange = (event, config) => setOtherValueLabel.call(this, event, config)
return listeners
}
@ -328,3 +353,31 @@ export default {
}
}
</script>
<style scoped>
/deep/ .el-radio-group {
margin-left: 10px;
}
/deep/ .el-radio {
display: block;
height: 23px;
line-height: 23px;
}
/deep/ .el-checkbox-group {
margin-left: 10px;
}
/deep/ .el-checkbox {
display: block;
}
/deep/ .item-other-input {
margin-left: 20px;
-webkit-tap-highlight-color: rgba(255, 255, 255, 0);
}
/deep/ .item-other-input:focus {
outline: none;
}
</style>

43
src/components/render/render.js

@ -26,29 +26,28 @@ function vModel(dataObject, defaultValue) {
this.$emit('deleteUpload', file, fileList)
}
dataObject.attrs['on-exceed'] = (files, fileList) => {
this.$message.error(`最多上传${config.limit}个文件`);
this.$message.error(`最多上传${config.limit}个文件`)
},
dataObject.attrs['before-upload'] = (file) => {
let sizeUnitNum = 1
//文件大小判断
switch (config.sizeUnit) {
case 'KB':
sizeUnitNum = 1024
break
case 'MB':
sizeUnitNum = 1024 * 1024
break
case 'GB':
sizeUnitNum = 1024 * 1024 * 1024
break
dataObject.attrs['before-upload'] = (file) => {
let sizeUnitNum = 1
//文件大小判断
switch (config.sizeUnit) {
case 'KB':
sizeUnitNum = 1024
break
case 'MB':
sizeUnitNum = 1024 * 1024
break
case 'GB':
sizeUnitNum = 1024 * 1024 * 1024
break
}
let totalSize = config.fileSize * sizeUnitNum
if (file.size > totalSize) {
this.$message.error(`上传图片大小不能超过${config.fileSize}${config.sizeUnit}`)
return false
}
}
let totalSize= config.fileSize*sizeUnitNum
if (file.size> totalSize) {
this.$message.error(`上传图片大小不能超过${config.fileSize}${config.sizeUnit}`);
return false
}
console.log(dataObject)
}
} else {
dataObject.props.value = defaultValue
@ -65,7 +64,7 @@ function mountSlotFlies(h, confClone, children) {
Object.keys(childObjs).forEach(key => {
const childFunc = childObjs[key]
if (confClone.__slot__ && confClone.__slot__[key]) {
children.push(childFunc(h, confClone, key))
children.push(childFunc(h, confClone, key, this))
}
})
}

30
src/components/render/slots/el-checkbox-group.js

@ -1,13 +1,21 @@
export default {
options(h, conf, key) {
const list = []
conf.__slot__.options.forEach(item => {
if (conf.__config__.optionType === 'button') {
list.push(<el-checkbox-button label={item.value}>{item.label}</el-checkbox-button>)
} else {
list.push(<el-checkbox label={item.value} border={conf.border}>{item.label}</el-checkbox>)
}
})
return list
}
options(h, conf, key, that) {
const list = []
conf.__slot__.options.forEach(item => {
if (conf.__config__.optionType === 'button') {
list.push(<el-checkbox-button label={item.value}>{item.label}</el-checkbox-button>)
} else {
if (item.value == 0) {
list.push(<el-checkbox label={item.value}
border={conf.border}>{item.label}
<input class='item-other-input' onChange={event => {
that.$emit('selectOtherChange', event.target.value, conf)
}}/></el-checkbox>)
} else {
list.push(<el-checkbox label={item.value} border={conf.border}>{item.label}</el-checkbox>)
}
}
})
return list
}
}

30
src/components/render/slots/el-radio-group.js

@ -1,13 +1,21 @@
export default {
options(h, conf, key) {
const list = []
conf.__slot__.options.forEach(item => {
if (conf.__config__.optionType === 'button') {
list.push(<el-radio-button label={item.value}>{item.label}</el-radio-button>)
} else {
list.push(<el-radio label={item.value} border={conf.border}>{item.label}</el-radio>)
}
})
return list
}
options(h, conf, key, that) {
const list = []
conf.__slot__.options.forEach(item => {
if (conf.__config__.optionType === 'button') {
list.push(<el-radio-button label={item.value}>{item.label}</el-radio-button>)
} else {
if (item.value == 0) {
list.push(<el-radio label={item.value} border={conf.border} >
{item.label}<input class='item-other-input' onChange={event => {
that.$emit('selectOtherChange', event.target.value,conf)
}}/>
</el-radio>)
} else {
list.push(<el-radio label={item.value} border={conf.border}>{item.label}</el-radio>)
}
}
})
return list
}
}

3
src/components/tinymce/index.vue

@ -42,10 +42,11 @@ export default {
menubar: 'false',
skin_url: '/tinymce/skins/ui/tduck',
content_css : '/tinymce/skins/content/tduck' ,
toolbar_mode:'floating',
cache_suffix: '?v='+new Date(),
plugins,
toolbar,
toolbar_drawer:'sliding',
toolbar_mode:'sliding',
height: 200,
// fontsize_formats: "8pt 10pt 12pt 14pt 18pt 24pt 36pt",
branding: false,

2
src/router/modules/root.js

@ -2,7 +2,7 @@ export default [
{
path: '/test',
meta: {requireLogin: false},
component: () => import(/* webpackChunkName: 'root' */ '@/components/tinymce/example/Index')
component: () => import(/* webpackChunkName: 'root' */ '@/views/test')
},
{
path: '/redirect/:type',

1
src/utils/convert.js

@ -54,6 +54,7 @@ export function dbDataConvertForItemJson(data) {
_.set(jsonItem, param[key], value)
})
}
jsonItem.sort = data.sort
jsonItem.typeId = data.type
jsonItem.__config__.formId = data.formItemId
jsonItem.__config__.label = data.label

228
src/views/form/DraggableItem.vue

@ -3,118 +3,154 @@ import draggable from 'vuedraggable'
import render from '@/components/render/render'
const components = {
itemBtns(h, currentItem, index, list) {
const { copyItem, deleteItem } = this.$listeners
return [
<span class="drawing-item-copy" title="复制" onClick={event => {
copyItem(currentItem, list); event.stopPropagation()
}}>
<i class="el-icon-copy-document" />
itemBtns(h, currentItem, index, list) {
const {copyItem, deleteItem} = this.$listeners
return [
<span class="drawing-item-copy" title="复制" onClick={event => {
copyItem(currentItem, list)
event.stopPropagation()
}}>
<i class="el-icon-copy-document"/>
</span>,
<span class="drawing-item-delete" title="删除" onClick={event => {
deleteItem(index, list); event.stopPropagation()
}}>
<i class="el-icon-delete" />
<span class="drawing-item-delete" title="删除" onClick={event => {
deleteItem(index, list)
event.stopPropagation()
}}>
<i class="el-icon-delete"/>
</span>
]
}
]
}
}
const layouts = {
colFormItem(h, currentItem, index, list) {
const { activeItem, changeLabel } = this.$listeners
const config = currentItem.__config__
const child = renderChildren.apply(this, arguments)
let className = this.activeId === config.formId ? 'drawing-item active-from-item' : 'drawing-item'
if (this.formConf.unFocusedComponentBorder) className += ' unfocus-bordered'
let labelWidth = config.labelWidth ? `${config.labelWidth}px` : null
if (config.showLabel === false) labelWidth = '0'
return (
<el-col span={config.span} class={className}
nativeOnClick={event => { activeItem(currentItem); event.stopPropagation() }}>
<el-form-item label-width={labelWidth}
label={config.showLabel ? config.label : ''} required={config.required}>
<render key={config.renderKey} conf={currentItem} onInput={ event => {
this.$set(config, 'defaultValue', event)
}}>
{child}
</render>
</el-form-item>
{components.itemBtns.apply(this, arguments)}
</el-col>
)
},
rowFormItem(h, currentItem, index, list) {
const { activeItem } = this.$listeners
const config = currentItem.__config__
const className = this.activeId === config.formId
? 'drawing-row-item active-from-item'
: 'drawing-row-item'
let child = renderChildren.apply(this, arguments)
if (currentItem.type === 'flex') {
child = <el-row type={currentItem.type} justify={currentItem.justify} align={currentItem.align}>
{child}
colFormItem(h, currentItem, index, list) {
const {activeItem, changeLabel} = this.$listeners
const config = currentItem.__config__
const child = renderChildren.apply(this, arguments)
let className = this.activeId === config.formId ? 'drawing-item active-from-item' : 'drawing-item'
if (this.formConf.unFocusedComponentBorder) className += ' unfocus-bordered'
let labelWidth = config.labelWidth ? `${config.labelWidth}px` : null
if (config.showLabel === false) labelWidth = '0'
return (
<el-col span={config.span} class={className}
nativeOnClick={event => {
activeItem(currentItem)
event.stopPropagation()
}}>
<el-form-item label-width={labelWidth}
label={config.showLabel ? config.label : ''} required={config.required}>
<render key={config.renderKey} conf={currentItem} onInput={event => {
this.$set(config, 'defaultValue', event)
}}>
{child}
</render>
</el-form-item>
{components.itemBtns.apply(this, arguments)}
</el-col>
)
},
rowFormItem(h, currentItem, index, list) {
const {activeItem} = this.$listeners
const config = currentItem.__config__
const className = this.activeId === config.formId
? 'drawing-row-item active-from-item'
: 'drawing-row-item'
let child = renderChildren.apply(this, arguments)
if (currentItem.type === 'flex') {
child = <el-row type={currentItem.type} justify={currentItem.justify} align={currentItem.align}>
{child}
</el-row>
}
return (
<el-col span={config.span}>
<el-row gutter={config.gutter} class={className}
nativeOnClick={event => { activeItem(currentItem); event.stopPropagation() }}>
<span class="component-name">{config.componentName}</span>
<draggable list={config.children || []} animation={340}
group="componentsGroup" class="drag-wrapper">
}
return (
<el-col span={config.span}>
<el-row gutter={config.gutter} class={className}
nativeOnClick={event => {
activeItem(currentItem)
event.stopPropagation()
}}>
<span class="component-name">{config.componentName}</span>
<draggable list={config.children || []} animation={340}
group="componentsGroup" class="drag-wrapper">
{child}
</draggable>
{components.itemBtns.apply(this, arguments)}
</el-row>
</el-col>
)
},
raw(h, currentItem, index, list) {
const config = currentItem.__config__
const child = renderChildren.apply(this, arguments)
return <render key={config.renderKey} conf={currentItem} onInput={event => {
this.$set(config, 'defaultValue', event)
}}>
{child}
</draggable>
{components.itemBtns.apply(this, arguments)}
</el-row>
</el-col>
)
},
raw(h, currentItem, index, list) {
const config = currentItem.__config__
const child = renderChildren.apply(this, arguments)
return <render key={config.renderKey} conf={currentItem} onInput={ event => {
this.$set(config, 'defaultValue', event)
}}>
{child}
</render>
}
</render>
}
}
function renderChildren(h, currentItem, index, list) {
const config = currentItem.__config__
if (!Array.isArray(config.children)) return null
return config.children.map((el, i) => {
const layout = layouts[el.__config__.layout]
if (layout) {
return layout.call(this, h, el, i, config.children)
}
return layoutIsNotFound.call(this)
})
const config = currentItem.__config__
if (!Array.isArray(config.children)) return null
return config.children.map((el, i) => {
const layout = layouts[el.__config__.layout]
if (layout) {
return layout.call(this, h, el, i, config.children)
}
return layoutIsNotFound.call(this)
})
}
function layoutIsNotFound() {
throw new Error(`没有与${this.currentItem.__config__.layout}匹配的layout`)
throw new Error(`没有与${this.currentItem.__config__.layout}匹配的layout`)
}
export default {
components: {
render,
draggable
},
props: [
'currentItem',
'index',
'drawingList',
'activeId',
'formConf'
],
render(h) {
const layout = layouts[this.currentItem.__config__.layout]
components: {
render,
draggable
},
props: [
'currentItem',
'index',
'drawingList',
'activeId',
'formConf'
],
render(h) {
const layout = layouts[this.currentItem.__config__.layout]
if (layout) {
return layout.call(this, h, this.currentItem, this.index, this.drawingList)
if (layout) {
return layout.call(this, h, this.currentItem, this.index, this.drawingList)
}
return layoutIsNotFound.call(this)
}
return layoutIsNotFound.call(this)
}
}
</script>
<style scoped>
/deep/ .el-radio-group {
margin-left: 10px;
}
/deep/ .el-radio {
display: block;
height: 23px;
line-height: 23px;
}
/deep/ .el-checkbox-group {
margin-left: 10px;
}
/deep/ .el-checkbox {
display: block;
}
/deep/ .item-other-input {
margin-left: 20px;
-webkit-tap-highlight-color: rgba(255, 255, 255, 0);
}
/deep/ .item-other-input:focus {
outline: none;
}
</style>

2
src/views/form/ProjectForm.vue

@ -17,7 +17,7 @@
</h4>
<div
v-show="projectTheme.showDescribe"
class="form-name-text" v-html="formConf.description" >
class="form-name-text" v-html="formConf.description">
</div>
<el-divider>
</el-divider>

1969
src/views/form/RightPanel.vue

File diff suppressed because it is too large

2
src/views/form/editor.vue

@ -280,9 +280,9 @@ export default {
this.activeData = tempActiveData
this.activeId = this.idGlobal
}
this.onItemEnd(obj)
},
onItemEnd(obj) {
console.log(obj)
let params = {'projectKey': this.projectKey}
if (this.drawingList[obj.newIndex - 1]) {
let sort1 = this.drawingList[obj.newIndex - 1].sort

7
src/views/project/MyProject.vue

@ -69,6 +69,7 @@
<div v-if="dataShowType=='gird'" class="project-grid-container">
<div
v-if="projectList.length"
v-loading="projectListLoading"
class="project-grid-view"
>
<div v-for="p in projectList" :key="p.id" class="project-grid-item-view pointer" :span="4">
@ -194,6 +195,7 @@
</template>
<script>
import DataEmpty from '@/components/DataEmpty'
let projectStatusList = [
{code: 1, name: '未发布', color: '#006EFF'},
{code: 2, name: '收集中', color: '#34C82A'},
@ -216,7 +218,8 @@ export default {
status: null
},
projectStatusList: projectStatusList,
projectList: []
projectList: [],
projectListLoading: true
}
},
computed: {
@ -241,6 +244,7 @@ export default {
this.$router.push({path: '/project/form', query: {key: key, active: type}})
},
queryProjectPage() {
this.$api.get('/user/project/page', {
params: this.queryParams
}).then(res => {
@ -248,6 +252,7 @@ export default {
this.projectList = records
this.total = total
this.queryParams.size = size
this.projectListLoading = false
})
}
}

28
src/views/test.vue

@ -1,23 +1,26 @@
<template>
<div>
<Verify
ref="verify"
:mode="'pop'"
:captcha-type="'blockPuzzle'"
:img-size="{ width: '330px', height: '155px' }"
@success="success"
/>
<button @click="useVerify">调用验证组件</button>
<el-radio-group v-model="radio">
<el-radio :label="3">备选项</el-radio>
<el-radio :label="6">备选项</el-radio>
<el-radio :label="9">备选项</el-radio>
<el-radio :label="0">其他<input/>
</el-radio>
</el-radio-group>
</div>
</template>
<script>
//
import Verify from '@/components/verifition/Verify'
// import Verify from '@/components/verifition/Verify'
export default {
name: 'App',
components: {
Verify
},
data() {
return {
radio: 3
}
},
created() {
},
@ -34,3 +37,8 @@ export default {
}
}
</script>
<style scoped>
.el-radio {
display: block;
}
</style>

Loading…
Cancel
Save