From ab262bbe2c64ba086a14f181e5a27eba4b46b555 Mon Sep 17 00:00:00 2001 From: king <18310653075@163.com> Date: 星期五, 13 十月 2023 17:59:53 +0800 Subject: [PATCH] 2023-10-13 --- src/menu/components/table/edit-table/index.scss | 5 src/tabviews/zshare/actionList/index.scss | 8 src/views/systemproc/proc/index.jsx | 2 src/menu/components/table/normal-table/columns/editColumn/formconfig.jsx | 12 src/templates/zshare/modalform/index.jsx | 52 ++ src/menu/components/share/pastecomponent/index.jsx | 16 src/templates/zshare/formconfig.jsx | 2 src/menu/components/table/base-table/columns/editColumn/formconfig.jsx | 12 src/menu/components/share/actioncomponent/index.jsx | 10 src/menu/modulecell/index.jsx | 4 /dev/null | 88 ---- src/views/tabledesign/source.jsx | 24 src/menu/components/table/base-table/index.scss | 3 src/menu/components/table/normal-table/index.scss | 3 src/tabviews/zshare/topSearch/index.scss | 2 src/menu/components/table/normal-table/index.jsx | 16 src/menu/components/table/edit-table/columns/editColumn/index.jsx | 62 ++ src/menu/components/table/normal-table/columns/index.jsx | 34 + src/templates/zshare/modalform/modaleditable/index.jsx | 519 ++++++++++++----------- src/views/systemproc/transfer/index.jsx | 289 +++++++++++++ src/views/systemproc/transfer/index.scss | 18 src/templates/zshare/modalform/modaleditable/index.scss | 12 src/menu/components/table/edit-table/columns/editColumn/formconfig.jsx | 12 src/templates/sharecomponent/searchcomponent/searchform/index.jsx | 62 ++ 24 files changed, 877 insertions(+), 390 deletions(-) diff --git a/src/menu/components/share/actioncomponent/index.jsx b/src/menu/components/share/actioncomponent/index.jsx index 3599e68..a66f2fa 100644 --- a/src/menu/components/share/actioncomponent/index.jsx +++ b/src/menu/components/share/actioncomponent/index.jsx @@ -407,10 +407,11 @@ btn.style = item.style || {} if (btn.class) { if (btn.class !== item.class || btn.show !== item.show || !btn.style.color || (item.focus && !btn.style.color)) { - if (btn.show === 'icon') { - btn.style.color = color[btn.class] - btn.style.backgroundColor = 'transparent' - } else if (btn.class === 'default') { + // if (btn.show === 'icon') { + // btn.style.color = color[btn.class] + // btn.style.backgroundColor = 'transparent' + // } + if (btn.class === 'default') { btn.style.color = 'rgba(0, 0, 0, 0.65)' btn.style.backgroundColor = '#fff' btn.style.borderColor = '#d9d9d9' @@ -419,6 +420,7 @@ btn.style.color = color[_c] btn.style.backgroundColor = '#fff' btn.style.borderColor = color[_c] + btn.style.borderWidth = '1px' } else if (btn.class === 'gray') { btn.style.color = 'rgba(0, 0, 0, 0.65)' btn.style.backgroundColor = color[btn.class] diff --git a/src/menu/components/share/pastecomponent/index.jsx b/src/menu/components/share/pastecomponent/index.jsx index 5c2b417..d809808 100644 --- a/src/menu/components/share/pastecomponent/index.jsx +++ b/src/menu/components/share/pastecomponent/index.jsx @@ -170,11 +170,23 @@ let keys = config.cols.map(col => (col.field || '$empty')) + let cols = [] res.cols.forEach(col => { - if (!keys.includes(col.field)) { - config.cols.push(col) + if (!col.field || !keys.includes(col.field)) { + cols.push(col) } }) + + if (cols.length === 0) { + notification.warning({ + top: 92, + message: '鏄剧ず鍒楀凡瀛樺湪锛�', + duration: 5 + }) + return + } else { + config.cols.push(...cols) + } } this.props.updateConfig(config, type) diff --git a/src/menu/components/table/base-table/columns/editColumn/formconfig.jsx b/src/menu/components/table/base-table/columns/editColumn/formconfig.jsx index 0ebdd54..aed7101 100644 --- a/src/menu/components/table/base-table/columns/editColumn/formconfig.jsx +++ b/src/menu/components/table/base-table/columns/editColumn/formconfig.jsx @@ -33,6 +33,12 @@ value: 'number', text: '鏁板瓧' }, { + value: 'custom', + text: '鑷畾涔夊垪' + }, { + value: 'formula', + text: '鍏紡' + }, { value: 'picture', text: '鍥剧墖' }, { @@ -45,14 +51,8 @@ value: 'textarea', text: '澶氳鏂囨湰' }, { - value: 'custom', - text: '鑷畾涔夊垪' - }, { value: 'colspan', text: '鍚堝苟鍒�' - }, { - value: 'formula', - text: '鍏紡' }, { value: 'index', text: '搴忓彿' diff --git a/src/menu/components/table/base-table/index.scss b/src/menu/components/table/base-table/index.scss index 408f2e5..80333d5 100644 --- a/src/menu/components/table/base-table/index.scss +++ b/src/menu/components/table/base-table/index.scss @@ -47,6 +47,9 @@ padding-top: 10px; min-height: 55px; } + button { + min-width: 60px; + } } .model-menu-action-list:not(.length0):not(.length1):not(.length2):not(.length3):not(.length4):not(.length5):not(.length6):not(.length7):not(.length8):not(.length9) { margin-bottom: 20px; diff --git a/src/menu/components/table/edit-table/columns/editColumn/formconfig.jsx b/src/menu/components/table/edit-table/columns/editColumn/formconfig.jsx index 9b72d05..8d56325 100644 --- a/src/menu/components/table/edit-table/columns/editColumn/formconfig.jsx +++ b/src/menu/components/table/edit-table/columns/editColumn/formconfig.jsx @@ -25,18 +25,18 @@ value: 'number', text: '鏁板瓧' }, { - value: 'textarea', - text: '澶氳鏂囨湰' - }, { value: 'custom', text: '鑷畾涔夊垪' }, { - value: 'colspan', - text: '鍚堝苟鍒�' - }, { value: 'formula', text: '鍏紡' }, { + value: 'textarea', + text: '澶氳鏂囨湰' + }, { + value: 'colspan', + text: '鍚堝苟鍒�' + }, { value: 'index', text: '搴忓彿' }] diff --git a/src/menu/components/table/edit-table/columns/editColumn/index.jsx b/src/menu/components/table/edit-table/columns/editColumn/index.jsx index bfc6cad..595109f 100644 --- a/src/menu/components/table/edit-table/columns/editColumn/index.jsx +++ b/src/menu/components/table/edit-table/columns/editColumn/index.jsx @@ -382,8 +382,19 @@ className = 'text-area' let linkSubFields = this.record.linkSubField || [] + + let columns = [] + + columns.push({ title: 'Value', key: 'Value', strict: true }) + columns.push({ title: 'Text', key: 'Text' }) + + linkSubFields.forEach(field => { + if (field === 'Value' || field === 'Text') return + + columns.push({ title: transfield[field] || field, key: field }) + }) - content = <EditTable type={'select'} module="form" transfield={transfield} linkSubFields={linkSubFields} onChange={this.changeOptions}/> + content = <EditTable columns={columns} module="form" onChange={this.changeOptions}/> } fields.push( @@ -403,6 +414,29 @@ ) }) return fields + } + + transfer = (options) => { + if (options.length === 0) return options + + let isNumber = true + options.forEach(item => { + if (!item.Value || isNaN(item.Value)) { + isNumber = false + } + }) + + if (isNumber) { + return options.map(item => { + item.Value = +item.Value + return item + }) + } else { + return options.map(item => { + item.Value = item.Value + '' + return item + }) + } } handleSubmit = () => { @@ -431,6 +465,32 @@ cols.forEach(col => { values.formula = values.formula.replace(col.reg, col.value) }) + } else if (values.type === 'text' && values.editable === 'true' && values.editType === 'select') { + if (values.resourceType === '0') { + values.options = values.options || [] + + values.options = this.transfer(values.options) + + if (values.options.filter(op => op.Text === '').length > 0) { + notification.warning({ + top: 92, + message: '鎻愮ず鏂囨湰锛圱ext锛変笉鍙负绌猴紒', + duration: 5 + }) + return + } else { + let arr = values.options.map(m => m.Value) + let _arr = Array.from(new Set(arr)) + if (arr.length > _arr.length) { + notification.warning({ + top: 92, + message: 'Value鍊间笉鍙噸澶嶏紒', + duration: 5 + }) + return + } + } + } } if (values.dataSource && /\s/.test(values.dataSource)) { diff --git a/src/menu/components/table/edit-table/index.scss b/src/menu/components/table/edit-table/index.scss index 60bc249..cfe7fcc 100644 --- a/src/menu/components/table/edit-table/index.scss +++ b/src/menu/components/table/edit-table/index.scss @@ -6,7 +6,7 @@ background-repeat: no-repeat; background-size: cover; min-height: 100px; - + .model-table-search-list { padding: 10px 0px 15px; min-height: 65px; @@ -73,6 +73,9 @@ padding-top: 10px; min-height: 55px; } + button { + min-width: 60px; + } } .ant-btn.mk-link { diff --git a/src/menu/components/table/normal-table/columns/editColumn/formconfig.jsx b/src/menu/components/table/normal-table/columns/editColumn/formconfig.jsx index f915309..8dd1c49 100644 --- a/src/menu/components/table/normal-table/columns/editColumn/formconfig.jsx +++ b/src/menu/components/table/normal-table/columns/editColumn/formconfig.jsx @@ -40,6 +40,12 @@ value: 'number', text: '鏁板瓧' }, { + value: 'custom', + text: '鑷畾涔夊垪' + }, { + value: 'formula', + text: '鍏紡' + }, { value: 'picture', text: '鍥剧墖' }, { @@ -52,14 +58,8 @@ value: 'textarea', text: '澶氳鏂囨湰' }, { - value: 'custom', - text: '鑷畾涔夊垪' - }, { value: 'colspan', text: '鍚堝苟鍒�' - }, { - value: 'formula', - text: '鍏紡' }, { value: 'index', text: '搴忓彿' diff --git a/src/menu/components/table/normal-table/columns/index.jsx b/src/menu/components/table/normal-table/columns/index.jsx index 02653b8..cae43f6 100644 --- a/src/menu/components/table/normal-table/columns/index.jsx +++ b/src/menu/components/table/normal-table/columns/index.jsx @@ -37,6 +37,32 @@ this.props.updateCol({...column, marks: vals}) } + copycolumn = () => { + const { column } = this.props + + let oInput = document.createElement('input') + let val = { + copyType: 'cols', + cols: [column] + } + + let srcid = localStorage.getItem(window.location.href.split('#')[0] + 'srcId') + if (srcid) { + val.$srcId = srcid + } + + oInput.value = window.btoa(window.encodeURIComponent(JSON.stringify(val))) + document.body.appendChild(oInput) + oInput.select() + document.execCommand('Copy') + oInput.className = 'oInput' + oInput.style.display = 'none' + + message.success('澶嶅埗鎴愬姛銆�') + + document.body.removeChild(oInput) + } + shouldComponentUpdate (nextProps, nextState) { if (this.props.rowSpan !== nextProps.rowSpan || this.props.colSpan !== nextProps.colSpan) { @@ -76,6 +102,7 @@ {column.type === 'custom' ? <PlusOutlined className="plus" title="娣诲姞鍏冪礌" onClick={() => this.props.addElement(column)} /> : null} {column.type === 'custom' ? <PlusSquareOutlined className="plus" title="娣诲姞鎸夐挳" onClick={() => this.props.addElement(column, 'button')} /> : null} <EditOutlined className="edit" title="缂栬緫" onClick={() => this.props.editColumn(column)} /> + <CopyOutlined title="澶嶅埗鏄剧ず鍒�" style={{color: '#26C281'}} onClick={this.copycolumn} /> {column.type === 'custom' ? <PasteComponent options={['customCardElement', 'action']} updateConfig={(res, resolve) => this.props.pasteCell(column, res, resolve)} /> : null} {column.type === 'custom' ? <FontColorsOutlined className="style" title="璋冩暣鏍峰紡" onClick={() => this.props.changeStyle(column)}/> : null} <DeleteOutlined className="close" title="鍒犻櫎" onClick={this.deleteCol} /> @@ -597,6 +624,12 @@ }) } + addColumns = () => { + const { config } = this.props + + MKEmitter.emit('addColumns', config.uuid) + } + /** * @description 缁勪欢閿�姣侊紝娓呴櫎state鏇存柊锛屾竻闄ゅ揩鎹烽敭璁剧疆 */ @@ -623,6 +656,7 @@ return ( <div className={`normal-table-columns ${config.setting.laypage} ${config.wrap.tableType} ${config.wrap.mode || ''} table-vertical-${config.wrap.vertical || ''} table-col-${columns.length}`} id={tableId}> <div className="col-control"> + <PlusOutlined style={{color: '#26C281'}} title="娣诲姞鍒�" onClick={this.addColumns}/> <CopyOutlined title="澶嶅埗鏄剧ず鍒�" onClick={this.copycolumn} /> <MarkColumn columns={fields} type="line" marks={lineMarks} onSubmit={this.updateLineMarks} /> <FileSyncOutlined title="鍚屾瀛楁闆�" onClick={this.syncfield} /> diff --git a/src/menu/components/table/normal-table/index.jsx b/src/menu/components/table/normal-table/index.jsx index 4b011c7..5a6fd01 100644 --- a/src/menu/components/table/normal-table/index.jsx +++ b/src/menu/components/table/normal-table/index.jsx @@ -92,6 +92,7 @@ componentDidMount () { MKEmitter.addListener('completeSave', this.completeSave) + MKEmitter.addListener('addColumns', this.addColumns) } shouldComponentUpdate (nextProps, nextState) { @@ -106,6 +107,7 @@ return } MKEmitter.removeListener('completeSave', this.completeSave) + MKEmitter.removeListener('addColumns', this.addColumns) } completeSave = () => { @@ -210,12 +212,16 @@ this.updateComponent(_card) } - addColumns = () => { - let card = fromJS(this.state.card).toJS() + addColumns = (id) => { + const { card } = this.state - card.cols.push({ focus: true, uuid: Utils.getuuid(), label: 'label', field: '', type: 'text' }) + if (id && id !== card.uuid) return - this.setState({card}) + let _card = fromJS(card).toJS() + + _card.cols.push({ focus: true, uuid: Utils.getuuid(), label: 'label', field: '', type: 'text' }) + + this.setState({card: _card}) } addSearch = () => { @@ -365,7 +371,7 @@ <NormalHeader hideSearch="true" config={card} updateComponent={this.updateComponent}/> <Popover overlayClassName="mk-popover-control-wrap" mouseLeaveDelay={0.2} mouseEnterDelay={0.2} content={ <div className="mk-popover-control"> - <PlusOutlined className="plus" title="娣诲姞鍒�" onClick={this.addColumns}/> + <PlusOutlined className="plus" title="娣诲姞鍒�" onClick={() => this.addColumns()}/> {appType !== 'mob' ? <PlusCircleOutlined className="plus" title="娣诲姞鎼滅储" onClick={this.addSearch}/> : null} <PlusSquareOutlined className="plus" title="娣诲姞鎸夐挳" onClick={this.addButton}/> <NormalForm title="琛ㄦ牸璁剧疆" width={800} update={this.updateWrap} getForms={this.getWrapForms}> diff --git a/src/menu/components/table/normal-table/index.scss b/src/menu/components/table/normal-table/index.scss index c5c5f42..d14a40e 100644 --- a/src/menu/components/table/normal-table/index.scss +++ b/src/menu/components/table/normal-table/index.scss @@ -73,6 +73,9 @@ padding-top: 10px; min-height: 55px; } + button { + min-width: 60px; + } } .ant-btn.mk-link { diff --git a/src/menu/modulecell/index.jsx b/src/menu/modulecell/index.jsx index e88c740..e3825af 100644 --- a/src/menu/modulecell/index.jsx +++ b/src/menu/modulecell/index.jsx @@ -93,13 +93,13 @@ children: [ { subType: 'text', text: '鏂囨湰', type: 'col', $init: true }, { subType: 'number', text: '鏁板瓧', type: 'col', $init: true }, + { subType: 'custom', text: '鑷畾涔夊垪', type: 'col', $init: true }, + { subType: 'formula', text: '鍏紡', type: 'col', $init: true }, { subType: 'picture', text: '鍥剧墖', type: 'col', $init: true }, { subType: 'video', text: '瑙嗛', type: 'col', $init: true }, { subType: 'link', text: '閾炬帴', type: 'col', $init: true }, { subType: 'textarea', text: '澶氳鏂囨湰', type: 'col', $init: true }, - { subType: 'custom', text: '鑷畾涔夊垪', type: 'col', $init: true }, { subType: 'colspan', text: '鍚堝苟鍒�', type: 'col', $init: true }, - { subType: 'formula', text: '鍏紡', type: 'col', $init: true }, { subType: 'index', text: '搴忓彿', type: 'col', $init: true } ] } diff --git a/src/tabviews/zshare/actionList/index.scss b/src/tabviews/zshare/actionList/index.scss index 42c8bcc..1d31f09 100644 --- a/src/tabviews/zshare/actionList/index.scss +++ b/src/tabviews/zshare/actionList/index.scss @@ -1,17 +1,21 @@ .button-list.toolbar-button { position: relative; padding: 15px 0px 0px; - background: #ffffff; min-height: 55px; + background: transparent; button { - min-width: 65px; + min-width: 60px; margin-right: 15px; margin-bottom: 10px!important; overflow: hidden; min-height: 28px; height: auto; } + .ant-btn-icon-only { + width: auto; + padding: 0 15px; + } .loading-skeleton { background: -webkit-gradient(linear,left top,right top,color-stop(25%,#f5f5f5),color-stop(37%,#ffffff),color-stop(63%,#f5f5f5)); diff --git a/src/tabviews/zshare/topSearch/index.scss b/src/tabviews/zshare/topSearch/index.scss index 49746f8..cefe1d5 100644 --- a/src/tabviews/zshare/topSearch/index.scss +++ b/src/tabviews/zshare/topSearch/index.scss @@ -1,5 +1,5 @@ .mk-search-wrap { - background: #ffffff; + // background: #ffffff; .mk-search-col { display: inline-block; diff --git a/src/templates/sharecomponent/searchcomponent/searchform/index.jsx b/src/templates/sharecomponent/searchcomponent/searchform/index.jsx index 400b7d9..f0139ed 100644 --- a/src/templates/sharecomponent/searchcomponent/searchform/index.jsx +++ b/src/templates/sharecomponent/searchcomponent/searchform/index.jsx @@ -12,7 +12,6 @@ const ColorSketch = asyncComponent(() => import('@/mob/colorsketch')) const FieldsTable = asyncComponent(() => import('@/templates/zshare/modalform/fieldtable')) -const DataTable = asyncComponent(() => import('@/templates/zshare/modalform/datatable')) const EditTable = asyncComponent(() => import('@/templates/zshare/modalform/modaleditable')) const groupOptions = [ @@ -190,6 +189,14 @@ } } else if (type === 'checkcard') { reRequired.fields = false + reOptions.multiple = [{ + value: 'false', + text: '鍗曢��' + }, { + value: 'true', + text: '澶氶��' + }] + if (this.record.display === 'picture') { if (this.record.resourceType === '0') { // 鑷畾涔夎祫婧� shows.push('options', 'fields', 'picratio') @@ -203,6 +210,20 @@ shows.push('dataSource', 'cardValField', 'colorField', 'fields', 'orderBy', 'orderType', 'database') } } else { + let appType = sessionStorage.getItem('appType') + if (appType === '') { + reOptions.multiple = [{ + value: 'false', + text: '鍗曢��' + }, { + value: 'true', + text: '澶氶��' + }, { + value: 'dropdown', + text: '涓嬫媺鑿滃崟' + }] + } + reRequired.fields = true if (this.record.resourceType === '0') { // 鑷畾涔夎祫婧� shows.push('options', 'fields', 'selectStyle', 'border') @@ -349,6 +370,9 @@ this.record.match = 'like' _fieldval.match = 'like' } + } else if (key === 'display') { + this.record.multiple = 'false' + _fieldval.multiple = 'false' } else if (key === 'items') { let _initval = this.props.form.getFieldValue('initval') if (_initval && !value.includes(_initval[0])) { @@ -552,12 +576,44 @@ let type = this.record.type if (type !== 'checkcard') { - content = <EditTable type={type} module="search" transfield={{}} linkSubFields={[]} onChange={this.changeOptions}/> + let columns = [] + + if (type === 'link') { + columns.push({ title: 'ParentID', key: 'ParentID', strict: true }) + } + + columns.push({ title: 'Value', key: 'Value', strict: true }) + columns.push({ title: 'Text', key: 'Text' }) + + content = <EditTable columns={columns} module="search" onChange={this.changeOptions}/> } else { if (this.record.linkField) { type = 'link' } - content = <DataTable type={type} multiple={this.record.multiple} display={this.record.display} linkSubFields={[]} transfield={{}} fields={this.record.fields || []} onChange={this.changeOptions}/> + + let columns = [] + let fields = this.record.fields || [] + let keys = ['ParentID', 'pid'] + + if (type === 'link') { + columns.push({ title: 'ParentID', key: 'ParentID', strict: true }) + } else if (this.record.multiple === 'dropdown' && this.record.display === 'text') { + columns.push({ title: 'pid', key: 'pid', strict: true }) + } + columns.push({ title: 'Value', key: '$value', strict: true }) + + if (this.record.display === 'picture') { + columns.push({ title: 'url', key: '$url', type: 'file' }) + } else if (this.record.display === 'color') { + columns.push({ title: 'Color', key: '$color' }) + } + + fields.forEach(item => { + keys.push(item.field) + columns.push({ title: item.field, key: item.field }) + }) + + content = <EditTable columns={columns} onChange={this.changeOptions}/> } } else if (item.type === 'fields') { span = 24 diff --git a/src/templates/zshare/formconfig.jsx b/src/templates/zshare/formconfig.jsx index f2373e3..f82687b 100644 --- a/src/templates/zshare/formconfig.jsx +++ b/src/templates/zshare/formconfig.jsx @@ -560,6 +560,7 @@ key: 'dataSource', label: '鏁版嵁婧�', initVal: card.dataSource || '', + tooltip: '鏁版嵁鏉冮檺鏇挎崲绗� $@ -> /* 鎴� \'\'銆� @$ -> */ 鎴� \'\'', required: true }, { @@ -2924,6 +2925,7 @@ key: 'dataSource', label: '鏁版嵁婧�', initVal: card.dataSource || '', + tooltip: '鏁版嵁鏉冮檺鏇挎崲绗� $@ -> /* 鎴� \'\'銆� @$ -> */ 鎴� \'\'', placeholder: '绯荤粺鍙橀噺锛歮k_departmentcode銆乵k_organization銆乵k_user_type銆傚叕鍏卞�硷細@ID@銆丂BID@銆�', required: true, readonly: false diff --git a/src/templates/zshare/modalform/datatable/index.jsx b/src/templates/zshare/modalform/datatable/index.jsx deleted file mode 100644 index 8f3e62b..0000000 --- a/src/templates/zshare/modalform/datatable/index.jsx +++ /dev/null @@ -1,502 +0,0 @@ -import React, { Component } from 'react' -import PropTypes from 'prop-types' -import { is, fromJS } from 'immutable' -import { DndProvider, DragSource, DropTarget } from 'react-dnd' -import { Table, Input, Popconfirm, Form, notification, message } from 'antd' -import { PlusOutlined, EditOutlined, DeleteOutlined, SwapOutlined } from '@ant-design/icons' - -import Utils from '@/utils/utils.js' -import asyncComponent from '@/utils/asyncComponent' -// import FileUpload from '@/tabviews/zshare/fileupload' -import './index.scss' - -const SourceComponent = asyncComponent(() => import('@/menu/components/share/sourcecomponent')) -const EditableContext = React.createContext() -let dragingIndex = -1 - -class BodyRow extends React.Component { - render() { - const { isOver, moveAble, connectDragSource, connectDropTarget, moveRow, ...restProps } = this.props - let { className } = restProps - - if (isOver && moveAble) { - if (restProps.index > dragingIndex) { - className += ' drop-over-downward' - } - if (restProps.index < dragingIndex) { - className += ' drop-over-upward' - } - } - - if (moveAble) { - return connectDragSource( - connectDropTarget(<tr {...restProps} className={className} style={{...restProps.style, cursor: 'move'}} />), - ) - } else { - return (<tr {...restProps} className={className} style={restProps.style} />) - } - } -} - -const rowSource = { - beginDrag(props) { - dragingIndex = props.index - return { - index: props.index, - } - } -} - -const rowTarget = { - drop(props, monitor) { - const dragIndex = monitor.getItem().index - const hoverIndex = props.index - - if (dragIndex === hoverIndex) { - return - } - - props.moveRow(dragIndex, hoverIndex) - - monitor.getItem().index = hoverIndex - }, -} - -const DragableBodyRow = DropTarget('row', rowTarget, (connect, monitor) => ({ - connectDropTarget: connect.dropTarget(), - isOver: monitor.isOver(), -}))( - DragSource('row', rowSource, connect => ({ - connectDragSource: connect.dragSource(), - }))(BodyRow), -) - -class EditableCell extends Component { - getInput = (form) => { - const { inputType, record } = this.props - if (inputType === 'file') { - return <SourceComponent initialValue={record ? (record.$url || '') : ''} type="" placement="right"/> - // return <FileUpload config={{ - // initval: record ? (record.$url || '') : '', - // suffix: '', - // maxfile: 1, - // fileType: 'picture-card' - // }}/> - } else { - return <Input onPressEnter={() => this.getValue(form)} /> - } - } - - getValue = (form) => { - const { record } = this.props - form.validateFields((error, row) => { - if (error) { - return - } - - this.props.onSave({...record, ...row}) - }) - } - - renderCell = (form) => { - const { getFieldDecorator } = form - const { - editing, - dataIndex, - title, - record, - inputType, - index, - children, - onSave, - ...restProps - } = this.props; - - let _val = '' - - if (record && dataIndex) { - _val = record[dataIndex] - } - - return ( - <td {...restProps}> - {editing ? ( - <Form.Item style={{ margin: '0 -5px 0 -5px' }}> - {getFieldDecorator(dataIndex, { - // rules: [ - // { - // required: dataIndex === '$value', - // message: `Please Input ${title}!`, - // }, - // ], - initialValue: _val, - })(this.getInput(form))} - </Form.Item> - ) : ( - children - )} - </td> - ) - } - - render() { - return <EditableContext.Consumer>{this.renderCell}</EditableContext.Consumer> - } -} - -class EdiDataTable extends Component { - static propTpyes = { - transfield: PropTypes.object, // 瀛楁鍚嶇О - type: PropTypes.string, // 鏄惁涓哄叧鑱旇〃鍗� - display: PropTypes.string, // 鏁版嵁绫诲瀷锛屾枃鏈�佸浘鐗� - fields: PropTypes.array, // 瀛楁闆� - linkSubFields: PropTypes.array, // 濉厖瀛楁 - onChange: PropTypes.func // 鏁版嵁鍙樺寲 - } - - UNSAFE_componentWillMount () { - let data = this.props['data-__meta'].initialValue - - this.setState({ - data: data, - columns: this.getCloumns() - }) - } - - state = { - data: [], - editingKey: '', - columns: [] - } - - UNSAFE_componentWillReceiveProps (nextProps) { - if ( - !is(fromJS(this.props.fields), fromJS(nextProps.fields)) || - !is(fromJS(this.props.linkSubFields), fromJS(nextProps.linkSubFields)) || - this.props.display !== nextProps.display || - (nextProps.multiple && this.props.multiple !== nextProps.multiple) || - this.props.type !== nextProps.type - ) { - this.setState({editingKey: ''}, () => { - this.setState({ - columns: this.getCloumns() - }) - }) - } - } - - getCloumns = () => { - const { display, fields, linkSubFields, transfield, type, multiple } = this.props - let columns = [] - let keys = ['ParentID', 'pid'] - - if (display === 'picture') { - columns.push({ - title: 'url', - dataIndex: '$url', - inputType: 'file', - // width: '40%', - editable: true, - render: (text) => { - if (!text) return '' - return <span style={{display: 'block', width: '70px', height: '70px'}}><img style={{width: '100%', height: '100%'}} src={text} alt="" /></span> - } - }) - } else if (display === 'color') { - columns.push({ - title: 'Color', - dataIndex: '$color', - inputType: 'text', - editable: true, - render: (text) => { - if (!text) return '' - return <div style={{height: '20px', background: text}}></div> - } - }) - } - - fields.forEach(item => { - keys.push(item.field) - columns.push({ - title: item.field, - dataIndex: item.field, - editable: true, - }) - }) - - if (linkSubFields.length > 0) { - linkSubFields.forEach(m => { - if (keys.includes(m)) return - - columns.push({ - title: transfield[m] || m, - dataIndex: m, - editable: true, - }) - }) - } - - columns.unshift({ - title: 'Value', - dataIndex: '$value', - editable: true, - }) - - if (multiple === 'dropdown' && display === 'text') { - columns.unshift({ - title: 'pid', - dataIndex: 'pid', - editable: true, - }) - } - - if (type === 'link') { - columns.unshift({ - title: 'ParentID', - dataIndex: 'ParentID', - editable: true, - }) - } - - columns.push({ - title: '鎿嶄綔', - dataIndex: 'operation', - align: 'center', - width: '18%', - render: (text, record) => { - const { editingKey } = this.state - const editable = this.isEditing(record) - return editable ? ( - <span> - <EditableContext.Consumer> - {form => ( - <span onClick={() => this.save(form, record.key)} style={{ marginRight: 8 , color: '#1890ff', cursor: 'pointer'}}> - 淇濆瓨 - </span> - )} - </EditableContext.Consumer> - <span style={{ color: '#1890ff', cursor: 'pointer'}} onClick={() => this.cancel(record.key)}>鍙栨秷</span> - </span> - ) : ( - <div className={'operation-btn' + (editingKey !== '' ? ' disabled' : '')}> - <span className="primary" onClick={() => {editingKey === '' && this.edit(record.key)}}><EditOutlined /></span> - <span className="hide-control" title="鏄剧ず/闅愯棌" onClick={() => {editingKey === '' && this.handleHide(record.key)}}><SwapOutlined /></span> - {editingKey === '' ? <Popconfirm - overlayClassName="popover-confirm" - title="纭畾鍒犻櫎鍚�?" - onConfirm={() => this.handleDelete(record.key) - }> - <span className="danger"><DeleteOutlined /></span> - </Popconfirm> : null} - {editingKey !== '' ? <span className="danger"><DeleteOutlined /></span> : null} - </div> - ) - } - }) - - return columns - } - - isEditing = record => record.key === this.state.editingKey - - cancel = () => { - this.setState({ editingKey: '' }) - } - - onSave = (record) => { - const { type } = this.props - const newData = [...this.state.data] - const index = newData.findIndex(item => record.key === item.key) - - if (type === 'link') { - if (newData.filter(m => record.key !== m.key && record.$value === m.$value && record.ParentID === m.ParentID).length > 0) { - message.warning('鐩稿悓ParentID涓嬶紝姝alue鍊煎凡瀛樺湪锛�') - } - } else { - if (newData.filter(m => record.key !== m.key && record.$value === m.$value).length > 0) { - message.warning('姝alue鍊煎凡瀛樺湪锛�') - } - } - - if (index > -1) { - newData.splice(index, 1, record) - this.setState({ data: newData, editingKey: '' }, () => { - this.props.onChange(newData) - }) - } - } - - handleDelete = (key) => { - const { data } = this.state - let _data = data.filter(item => key !== item.key) - - this.setState({ - data: _data - }, () => { - this.props.onChange(_data) - }) - } - - save(form, key) { - const { type } = this.props - - form.validateFields((error, row) => { - if (error) { - return; - } - - const newData = [...this.state.data] - const index = newData.findIndex(item => key === item.key) - - if (type === 'link') { - if (newData.filter(m => key !== m.key && row.$value === m.$value && row.ParentID === m.ParentID).length > 0) { - message.warning('鐩稿悓ParentID涓嬶紝姝alue鍊煎凡瀛樺湪锛�') - } - } else { - if (newData.filter(m => key !== m.key && row.$value === m.$value).length > 0) { - message.warning('姝alue鍊煎凡瀛樺湪锛�') - } - } - - if (index > -1) { - const item = newData[index] - newData.splice(index, 1, { - ...item, - ...row, - }) - this.setState({ data: newData, editingKey: '' }, () => { - this.props.onChange(newData) - }) - } else { - newData.push(row); - this.setState({ data: newData, editingKey: '' }, () => { - this.props.onChange(newData) - }) - } - }) - } - - handleAdd = () => { - const { fields, display } = this.props - if (this.state.data.length >= 100) { - notification.warning({ - top: 92, - message: '鏈�澶氬彲娣诲姞100椤癸紒', - duration: 5 - }) - return - } - - let item = { key: Utils.getuuid(), $value: `${this.state.data.length + 1}`, ParentID: '' } - - if (display === 'picture') { - item.$url = '' - } else if (display === 'color') { - item.$color = '' - } - - fields.forEach(f => { - item[f.field] = `${this.state.data.length + 1}` - }) - - let data = [...this.state.data, item] - - this.setState({ data, editingKey: '' }, () => { - this.props.onChange(data) - }) - } - - edit(key) { - this.setState({ editingKey: key }) - } - - handleHide = (key) => { - let _data = this.state.data.map(item => { - if (item.key === key) { - item.Hide = !item.Hide - } - return item - }) - this.setState({ - data: _data - }, () => { - this.props.onChange(_data) - }) - } - - moveRow = (dragIndex, hoverIndex) => { - const { editingKey } = this.state - let _data = fromJS(this.state.data).toJS() - - if (editingKey) return - - _data.splice(hoverIndex, 0, ..._data.splice(dragIndex, 1)) - - this.setState({ - data: _data - }, () => { - this.props.onChange(_data) - }) - } - - render() { - const { display, fields } = this.props - - const components = { - body: { - row: DragableBodyRow, - cell: EditableCell - } - } - - const columns = this.state.columns.map(col => { - if (!col.editable) { - return col - } - return { - ...col, - onCell: record => ({ - record, - dataIndex: col.dataIndex, - inputType: col.inputType, - title: col.title, - editing: this.isEditing(record), - onSave: this.onSave, - }), - } - }) - - let addable = false - if (display === 'picture' || display === 'color') { - addable = true - } else if (fields && fields.length > 0) { - addable = true - } - - return ( - <EditableContext.Provider value={this.props.form}> - <div className="modal-card-data-table"> - {addable ? <PlusOutlined className="add-row" onClick={this.handleAdd} /> : null} - <DndProvider> - <Table - components={components} - bordered - rowKey="key" - dataSource={this.state.data} - columns={columns} - rowClassName={(record) => record.Hide ? 'editable-row hide' : 'editable-row'} - onRow={(record, index) => ({ - index, - moveAble: !this.state.editingKey, - moveRow: this.moveRow, - })} - pagination={false} - /> - </DndProvider> - </div> - </EditableContext.Provider> - ) - } -} - -export default Form.create()(EdiDataTable) \ No newline at end of file diff --git a/src/templates/zshare/modalform/datatable/index.scss b/src/templates/zshare/modalform/datatable/index.scss deleted file mode 100644 index ac76a17..0000000 --- a/src/templates/zshare/modalform/datatable/index.scss +++ /dev/null @@ -1,88 +0,0 @@ -.modal-card-data-table { - .add-row { - position: absolute; - z-index: 1; - right: 10px; - top: -30px; - padding: 5px; - font-size: 18px; - color: #26C281; - } - .editable-row { - .ant-form-explain { - position: absolute; - font-size: 12px; - margin-top: -4px; - } - .ant-form-item-control { - line-height: 1; - } - > td { - padding: 13px 10px; - word-break: break-all; - } - .fileupload-form-container .ant-upload-list-picture-card .ant-upload-list-item { - margin: 0; - padding: 2px; - .ant-upload-list-item-info > span { - height: 100%; - } - } - .ant-input { - padding: 0 5px; - } - } - .editable-row.hide { - td:not(:last-child) { - text-decoration: line-through; - } - } - .operation-btn { - font-size: 16px; - text-align: center; - span { - margin-right: 20px; - cursor: pointer; - } - span:last-child { - margin-right: 0px; - } - .primary { - color: #1890ff; - } - .hide-control { - color: rgb(142, 68, 173); - } - .danger { - color: #ff4d4f; - } - } - .operation-btn.disabled { - span { - cursor: default; - } - .primary { - color: rgba(0, 0, 0, .25); - } - .hide-control { - color: rgba(0, 0, 0, .25); - } - .danger { - color: rgba(0, 0, 0, .25); - } - } - tr.drop-over-downward td { - border-bottom: 2px dashed #1890ff; - } - tr.drop-over-upward td { - border-top: 2px dashed #1890ff; - } - .mk-source-wrap { - .ant-radio-button-wrapper + .ant-radio-button-wrapper { - border-radius: 0 4px 4px 0; - } - .ant-radio-button-wrapper:last-child { - display: none; - } - } -} diff --git a/src/templates/zshare/modalform/index.jsx b/src/templates/zshare/modalform/index.jsx index 43d8efa..6b480c0 100644 --- a/src/templates/zshare/modalform/index.jsx +++ b/src/templates/zshare/modalform/index.jsx @@ -15,7 +15,6 @@ const { TextArea } = Input const ColorSketch = asyncComponent(() => import('@/mob/colorsketch')) const FieldsTable = asyncComponent(() => import('./fieldtable')) -const DataTable = asyncComponent(() => import('./datatable')) const MkEditIcon = asyncComponent(() => import('@/components/mkIcon')) const modalTypeOptions = { @@ -457,13 +456,13 @@ this.record.options = this.record.options.map(cell => { cell.Value = cell.Value || cell.$value || '' cell.Text = cell[field] || '' - + delete cell.$value return cell }) } else { this.record.options = this.record.options.map(cell => { cell.Value = cell.Value || cell.$value || '' - + delete cell.$value return cell }) } @@ -778,7 +777,21 @@ linkSubFields = [] } } - content = <EditTable type={type} module="form" transfield={transfield} linkSubFields={linkSubFields} onChange={this.changeOptions}/> + + let columns = [] + if (type === 'link') { + columns.push({ title: 'ParentID', key: 'ParentID', strict: true }) + } + columns.push({ title: 'Value', key: 'Value', strict: true }) + columns.push({ title: 'Text', key: 'Text' }) + + linkSubFields.forEach(field => { + if (field === 'Value' || field === 'Text') return + + columns.push({ title: transfield[field] || field, key: field }) + }) + + content = <EditTable columns={columns} module="form" onChange={this.changeOptions}/> } else { if (this.record.multiple === 'true') { linkSubFields = [] @@ -786,7 +799,34 @@ if (this.record.linkField) { type = 'link' } - content = <DataTable type={type} display={this.record.display} linkSubFields={linkSubFields} transfield={transfield} fields={this.record.fields || []} onChange={this.changeOptions}/> + + let columns = [] + let fields = this.record.fields || [] + let keys = ['ParentID', 'pid'] + + if (type === 'link') { + columns.push({ title: 'ParentID', key: 'ParentID', strict: true }) + } + columns.push({ title: 'Value', key: '$value', strict: true }) + + if (this.record.display === 'picture') { + columns.push({ title: 'url', key: '$url', type: 'file' }) + } else if (this.record.display === 'color') { + columns.push({ title: 'Color', key: '$color' }) + } + + fields.forEach(item => { + keys.push(item.field) + columns.push({ title: item.field, key: item.field }) + }) + + linkSubFields.forEach(m => { + if (keys.includes(m)) return + + columns.push({ title: transfield[m] || m, key: m }) + }) + + content = <EditTable columns={columns} onChange={this.changeOptions}/> } } else if (item.type === 'fields') { span = 24 @@ -836,7 +876,7 @@ let isNumber = true options.forEach(item => { - if (!/^([0-9]|[1-9]\d{0,2})$/.test(item.Value)) { + if (!item.Value || isNaN(item.Value)) { isNumber = false } }) diff --git a/src/templates/zshare/modalform/modaleditable/index.jsx b/src/templates/zshare/modalform/modaleditable/index.jsx index b8ca161..0427a95 100644 --- a/src/templates/zshare/modalform/modaleditable/index.jsx +++ b/src/templates/zshare/modalform/modaleditable/index.jsx @@ -1,106 +1,138 @@ import React, {Component} from 'react' import PropTypes from 'prop-types' import { is, fromJS } from 'immutable' -import { Table, Input, Popconfirm, Form, message } from 'antd' -import { ArrowUpOutlined, ArrowDownOutlined, DeleteOutlined, PlusOutlined, SwapOutlined } from '@ant-design/icons' +import { DndProvider, DragSource, DropTarget } from 'react-dnd' +import { Table, Input, Popconfirm, message } from 'antd' +import { DeleteOutlined, PlusOutlined, SwapOutlined, DragOutlined } from '@ant-design/icons' import Utils from '@/utils/utils.js' +import asyncComponent from '@/utils/asyncComponent' import './index.scss' -const EditableContext = React.createContext() +const SourceComponent = asyncComponent(() => import('@/menu/components/share/sourcecomponent')) -const EditableRow = ({ form, index, ...props }) => ( - <EditableContext.Provider value={form}> - <tr {...props} /> - </EditableContext.Provider> +class MoveTd extends React.Component { + render() { + const { connectDragSource, connectDropTarget } = this.props + + return connectDragSource( + connectDropTarget(<td className="mk-move-col"><DragOutlined /></td>), + ) + } +} + +const rowSource = { + beginDrag(props) { + return { + index: props.index, + } + } +} + +const rowTarget = { + drop(props, monitor) { + const dragIndex = monitor.getItem().index + const hoverIndex = props.index + + if (dragIndex === hoverIndex) { + return + } + + props.moveRow(dragIndex, hoverIndex) + + monitor.getItem().index = hoverIndex + }, +} + +const DragableTd = DropTarget('td', rowTarget, connect => ({ + connectDropTarget: connect.dropTarget(), +}))( + DragSource('td', rowSource, (connect, monitor) => ({ + connectDragSource: connect.dragSource(), + // isDragging: monitor.isDragging() + }))(MoveTd), ) - -const EditableFormRow = Form.create()(EditableRow) class EditableCell extends Component { state = { - editing: false + editing: false, + value: '' } - toggleEdit = () => { - const editing = !this.state.editing - this.setState({ editing }, () => { - if (editing && this.input && this.input.select) { + trigger = () => { + const { dataIndex, record } = this.props + + this.setState({ editing: true, value: record[dataIndex] }, () => { + if (this.input && this.input.select) { this.input.select() - } else if (editing && this.input && this.input.focus) { + } else if (this.input && this.input.focus) { this.input.focus() } }) } - save = e => { - const { record, handleSave } = this.props - this.form.validateFields((error, values) => { - handleSave({ ...record, ...values }) - if (error && error[e.currentTarget.id]) { - return - } - this.toggleEdit() - }) + save = () => { + const { record, handleSave, dataIndex } = this.props + const { value } = this.state + + handleSave({ ...record, [dataIndex]: value }) + + this.setState({ editing: false, value: '' }) } - renderCell = form => { - this.form = form - const { children, dataIndex, record } = this.props + changeUrl = (val) => { + const { record, handleSave, dataIndex } = this.props + + handleSave({ ...record, [dataIndex]: val }) + } + + renderCell = () => { + const { dataIndex, inputType, record } = this.props const { editing } = this.state - return editing ? ( - <Form.Item style={{ margin: '0 -5px 0 -5px' }}> - {form.getFieldDecorator(dataIndex, { - rules: [ - { - required: dataIndex === 'Text', - message: '涓嶅彲涓虹┖.', - } - ], - initialValue: record[dataIndex] - })(<Input ref={node => (this.input = node)} autoComplete="off" onPressEnter={this.save} onBlur={this.save} />)} - </Form.Item> - ) : ( - <div - className="editable-cell-value-wrap" - onClick={this.toggleEdit} - > - {children} - </div> - ) + if (inputType === 'file') { + return <SourceComponent initialValue={record[dataIndex]} type="" onChange={this.changeUrl} placement="right"/> + } + + if (!editing) { + return ( + <div + className="editable-cell-value-wrap" + onClick={this.trigger} + > + {record[dataIndex]} + </div> + ) + } else { + return <Input ref={node => (this.input = node)} defaultValue={record[dataIndex]} autoComplete="off" onChange={(e) => this.setState({value: e.target.value})} onPressEnter={this.save} onBlur={this.save} /> + } } render() { - const { - editable, - dataIndex, - title, - record, - index, - handleSave, - children, - ...restProps - } = this.props + const { editable, dataIndex, index } = this.props + + if (dataIndex === '$move') { + return (<DragableTd key={index} {...this.props} />) + } + + if (editable) { + return ( + <td>{this.renderCell()}</td> + ) + } + return ( - <td {...restProps}> - {editable ? ( - <EditableContext.Consumer style={{padding: 0}}>{this.renderCell}</EditableContext.Consumer> - ) : ( - children - )} - </td> + <td {...this.props}/> ) } } class EditTable extends Component { static propTpyes = { - type: PropTypes.string, // 琛ㄥ崟绫诲瀷 - module: PropTypes.string, // 鍏冪礌绫诲瀷 - linkSubFields: PropTypes.array, // 鍏宠仈瀛楁 - transfield: PropTypes.object, // 琛ㄥ崟瀛楁鍚嶇О - onChange: PropTypes.func // 鏁版嵁鍙樺寲 + type: PropTypes.any, + module: PropTypes.string, + columns: PropTypes.array, + onChange: PropTypes.func } state = { @@ -110,38 +142,40 @@ } UNSAFE_componentWillMount () { - const { linkSubFields, type } = this.props - let data = this.props['data-__meta'].initialValue || [] - - const { columns } = this.getColumns(type, linkSubFields, data) + const { columns, value } = this.props + let data = value || [] this.setState({ - columns: columns, - dataSource: data, + columns: this.getColumns(), + dataSource: data.map(item => { + columns.forEach(n => { + if (item[n.key] !== undefined) return + item[n.key] = ['ParentID', '$url', '$color', '$value'].includes(n.key) ? '' : item.Text || '' + }) + return item + }), count: data.length }) } - handleUpDown = (record, direction) => { + moveRow = (dragId, hoverId) => { const { dataSource } = this.state - let index = 0 - - let _data = dataSource.filter((item, i) => { - if (item.key === record.key) { - index = i + let dragIndex = -1 + let hoverIndex = -1 + + dataSource.forEach((item, i) => { + if (item.key === dragId) { + dragIndex = i + } else if (item.key === hoverId) { + hoverIndex = i } - - return item.key !== record.key }) - if ((index === 0 && direction === 'up') || (index === dataSource.length - 1 && direction === 'down')) { - return - } + + if (dragIndex === -1 || hoverIndex === -1) return - if (direction === 'up') { - _data.splice(index - 1, 0, record) - } else { - _data.splice(index + 1, 0, record) - } + let _data = fromJS(dataSource).toJS() + + _data.splice(hoverIndex, 0, ..._data.splice(dragIndex, 1)) this.setState({ dataSource: _data @@ -150,13 +184,14 @@ }) } - handleHide = (record) => { + handleHide = (key) => { let _data = this.state.dataSource.map(item => { - if (item.key === record.key) { + if (item.key === key) { item.Hide = !item.Hide } return item }) + this.setState({ dataSource: _data }, () => { @@ -164,7 +199,7 @@ }) } - handleDelete = key => { + handleDelete = (key) => { const { dataSource } = this.state let _data = dataSource.filter(item => item.key !== key) @@ -173,22 +208,26 @@ }) } - handleAdd = (e) => { - e.stopPropagation() - const { linkSubFields } = this.props + handleAdd = () => { + const { columns } = this.props const { count, dataSource } = this.state - const newData = { - key: Utils.getuuid(), - Value: `${count}`, - Text: `${count}`, - ParentID: '' - } - linkSubFields.forEach(m => { - newData[m] = newData[m] || '' + let item = { key: Utils.getuuid() } + + columns.forEach(m => { + item[m.key] = '' }) - let _data = [...dataSource, newData] + if (item.Value === '') { + item.Value = `${count + 1}` + } + if (item.$value === '') { + item.$value = `${count + 1}` + } + + item.Text = `${count + 1}` + + let _data = [...dataSource, item] this.setState({ dataSource: _data, @@ -199,18 +238,49 @@ } handleSave = row => { - const { type } = this.props + const { columns, type } = this.props const newData = [...this.state.dataSource] const index = newData.findIndex(item => row.key === item.key) const item = newData[index] - if (type === 'link') { - if (newData.filter(m => row.key !== m.key && row.Value === m.Value && row.ParentID === m.ParentID).length > 0) { - message.warning('鐩稿悓ParentID涓嬶紝姝alue鍊煎凡瀛樺湪锛�') - } + if (type === 'proc') { + // if (!row.origin || /^\s+$/.test(row.origin)) { + // message.warning(columns[0].title + '涓虹┖鏃舵棤鏁堬紒') + // } } else { - if (newData.filter(m => row.key !== m.key && row.Value === m.Value).length > 0) { - message.warning('姝alue鍊煎凡瀛樺湪锛�') + let val = '' + let repeat = false + let _type = '' + columns.forEach(col => { + if (!col.strict) return + + if (col.key === 'ParentID') { + _type = 'mutil' + } + + val += row[col.key] + }) + + newData.forEach(item => { + if (row.key === item.key) return + + let _val = '' + columns.forEach(col => { + if (!col.strict) return + + _val += item[col.key] + }) + + if (val === _val) { + repeat = true + } + }) + if (repeat) { + if (_type === 'mutil') { + message.warning('鐩稿悓ParentID涓嬶紝姝alue鍊煎凡瀛樺湪锛�') + } else { + message.warning('姝alue鍊煎凡瀛樺湪锛�') + } } } @@ -223,112 +293,83 @@ }) } - getColumns = (type, linkSubFields, dataSource) => { - const { transfield } = this.props + getColumns = () => { + const { columns } = this.props - let _dataSource = fromJS(dataSource).toJS() - let fields = [] - let subFields = linkSubFields.filter(m => m !== 'Value' && m !== 'Text') - - if (subFields.length > 0) { - _dataSource = _dataSource.map(data => { - subFields.forEach(n => { - if (data[n] !== undefined) return - data[n] = data.Text || '' - }) - return data + let fields = [{ + title: ' ', + width: '60px', + dataIndex: '$move', + onCell: (record) => ({ + index: record.key, + dataIndex: '$move', + moveRow: this.moveRow }) - - fields = subFields.map(field => { - return { - title: transfield[field] || field, - $title: transfield[field] || field, - dataIndex: field, + }] + columns.forEach(n => { + let col = { + title: n.title, + dataIndex: n.key, + onCell: record => ({ + record, editable: true, - } - }) - } - - let columns = [ - { - title: 'Value', - $title: 'Value', - dataIndex: 'Value', - editable: true - }, - { - title: 'Text', - $title: 'Text', - dataIndex: 'Text', - editable: true - }, - ...fields, - { - title: '鎿嶄綔', - align: 'center', - width: '20%', - dataIndex: 'operation', - render: (text, record) => - this.state.dataSource.length >= 1 ? ( - <div style={{fontSize: '15px'}}> - <span className="operation-btn" onClick={() => this.handleUpDown(record, 'up')} style={{color: '#1890ff'}}><ArrowUpOutlined /></span> - <span className="operation-btn" onClick={() => this.handleUpDown(record, 'down')} style={{color: '#ff4d4f'}}><ArrowDownOutlined /></span> - <span className="operation-btn" title="鏄剧ず/闅愯棌" onClick={() => this.handleHide(record)} style={{color: 'rgb(142, 68, 173)'}}><SwapOutlined /></span> - <Popconfirm - title="纭畾鍒犻櫎鍚楋紵" - overlayClassName="popover-confirm" - onConfirm={() => this.handleDelete(record.key) - }> - <span style={{color: '#ff4d4f', cursor: 'pointer'}}><DeleteOutlined /></span> - </Popconfirm> - </div> - ) : null, + inputType: n.type || 'text', + dataIndex: n.key, + handleSave: this.handleSave + }) } - ] - if (type === 'link') { - columns.unshift({ - title: 'ParentID', - $title: 'ParentID', - dataIndex: 'ParentID', - editable: true - }) - } + if (n.width) { + col.width = n.width + } + if (n.fixed) { + delete col.onCell + } - return { - columns: columns.map(col => { - if (col.dataIndex !== 'operation') { - col.title = <div> - {col.$title} + fields.push(col) + }) + + fields.push({ + title: '鎿嶄綔', + align: 'center', + width: '110px', + dataIndex: 'operation', + render: (text, record) => + ( + <div style={{fontSize: '15px'}}> + <span className="operation-btn" title="鏄剧ず/闅愯棌" onClick={() => this.handleHide(record.key)} style={{color: 'rgb(142, 68, 173)'}}><SwapOutlined /></span> + <Popconfirm + title="纭畾鍒犻櫎鍚楋紵" + overlayClassName="popover-confirm" + onConfirm={() => this.handleDelete(record.key) + }> + <span style={{color: '#ff4d4f', cursor: 'pointer'}}><DeleteOutlined /></span> + </Popconfirm> </div> - } - return col - }), - dataSource: _dataSource - } + ) + }) + + return fields } - handleEmpty = (e) => { - e.stopPropagation() - const { linkSubFields, module } = this.props + handleEmpty = () => { + const { columns, module } = this.props const { dataSource } = this.state if (dataSource.filter(item => item.Value === '').length > 0) { message.warning('Value涓虹┖宸插瓨鍦紒') return } - const newData = { - key: Utils.getuuid(), - Value: '', - Text: module === 'form' ? '绌�' : '鍏ㄩ儴', - ParentID: '' - } - linkSubFields.forEach(m => { - newData[m] = newData[m] || '' + let item = { key: Utils.getuuid() } + + columns.forEach(m => { + item[m.key] = '' }) - let _data = [newData, ...dataSource] + item.Text = module === 'form' ? '绌�' : '鍏ㄩ儴' + + let _data = [item, ...dataSource] this.setState({ dataSource: _data, @@ -337,65 +378,57 @@ }) } - resetColumn = (type, linkSubFields) => { - const { columns, dataSource } = this.getColumns(type, linkSubFields, this.state.dataSource) + resetColumn = () => { + const { columns, value } = this.props + + let data = fromJS(value).toJS().map(item => { + columns.forEach(n => { + if (item[n.key] !== undefined) return + item[n.key] = ['ParentID', '$url', '$color', '$value'].includes(n.key) ? '' : item.Text || '' + }) + return item + }) - if (!is(fromJS(dataSource), fromJS(this.state.dataSource))) { - this.setState({ - columns, - dataSource - }, () => { - this.props.onChange(dataSource) - }) - } else { - this.setState({ - columns - }) - } + this.setState({ + columns: this.getColumns(), + dataSource: data, + count: data.length + }, () => { + this.props.onChange(data) + }) } UNSAFE_componentWillReceiveProps (nextProps) { - if (!is(fromJS(this.props.linkSubFields), fromJS(nextProps.linkSubFields)) || this.props.type !== nextProps.type) { - this.resetColumn(nextProps.type, nextProps.linkSubFields) + if (!is(fromJS(this.props.columns), fromJS(nextProps.columns))) { + this.setState({}, () => { + this.resetColumn() + }) } } render() { const { module } = this.props - const { dataSource } = this.state + const { dataSource, columns } = this.state const components = { body: { - row: EditableFormRow, cell: EditableCell } } - const columns = this.state.columns.map(col => { - if (!col.editable) { - return col - } - return { - ...col, - onCell: record => ({ - record, - editable: col.editable, - dataIndex: col.dataIndex, - title: col.title, - handleSave: this.handleSave - }) - } - }) + return ( <div className="common-modal-edit-table"> - <span className="add-row add-row-empty" onClick={this.handleEmpty}>{module === 'form' ? '绌�' : '鍏ㄩ儴'}</span> + {module ? <span className="add-row add-row-empty" onClick={this.handleEmpty}>{module === 'form' ? '绌�' : '鍏ㄩ儴'}</span> : null} <PlusOutlined className="add-row" onClick={this.handleAdd} /> - <Table - components={components} - rowClassName={(record) => record.Hide ? 'editable-row hide' : 'editable-row'} - bordered - dataSource={dataSource} - columns={columns} - pagination={false} - /> + <DndProvider> + <Table + components={components} + rowClassName={(record) => record.Hide ? 'editable-row hide' : 'editable-row'} + bordered + dataSource={dataSource} + columns={columns} + pagination={false} + /> + </DndProvider> </div> ) } diff --git a/src/templates/zshare/modalform/modaleditable/index.scss b/src/templates/zshare/modalform/modaleditable/index.scss index 7c097fd..3c93c9a 100644 --- a/src/templates/zshare/modalform/modaleditable/index.scss +++ b/src/templates/zshare/modalform/modaleditable/index.scss @@ -15,6 +15,15 @@ color: #1890ff; cursor: pointer; } + .mk-move-col { + text-align: center; + font-size: 16px; + cursor: move; + color: #c8c8c8; + } + .mk-source-wrap { + min-width: 150px; + } .ant-table-thead > tr > th { padding: 10px 16px; position: relative; @@ -23,7 +32,6 @@ position: absolute; right: 12px; font-size: 14px; - // top: 12px; color: #b8b8b8; } } @@ -52,7 +60,7 @@ } } .operation-btn { - margin-right: 10px; + margin-right: 15px; cursor: pointer; } .editable-row.hide { diff --git a/src/views/systemproc/proc/index.jsx b/src/views/systemproc/proc/index.jsx index 62ce63a..577e462 100644 --- a/src/views/systemproc/proc/index.jsx +++ b/src/views/systemproc/proc/index.jsx @@ -6,6 +6,7 @@ import Utils from '@/utils/utils.js' import Api from '@/api' import CodeMirror from '@/templates/zshare/codemirror' +import Transfer from '../transfer' import './index.scss' const { confirm } = Modal @@ -379,6 +380,7 @@ {!inputing ? <Search placeholder="璇疯緭鍏ュ瓨鍌ㄨ繃绋嬪悕绉�" defaultValue={procName} disabled={loading} enterButton="纭畾" onSearch={this.search}/> : null} </div> <div className="action-wrap"> + {!procName || loading || !content ? null : <Transfer procName={procName} content={content} />} <Button key="save" className="mk-btn mk-green" disabled={loading} onClick={() => this.save()}>淇濆瓨</Button> <Button key="prev" className="mk-btn mk-primary" disabled={!procName || loading} onClick={this.prev}>涓婁竴鐗堟湰</Button> <Button key="next" className="mk-btn mk-primary" disabled={!procName || loading} onClick={this.next}>涓嬩竴鐗堟湰</Button> diff --git a/src/views/systemproc/transfer/index.jsx b/src/views/systemproc/transfer/index.jsx new file mode 100644 index 0000000..1e44418 --- /dev/null +++ b/src/views/systemproc/transfer/index.jsx @@ -0,0 +1,289 @@ +import React, {Component} from 'react' +import PropTypes from 'prop-types' +import { is, fromJS } from 'immutable' +import { DndProvider } from 'react-dnd' +import HTML5Backend from 'react-dnd-html5-backend' +import { Button, Modal, notification, Form, Select } from 'antd' + +import Utils from '@/utils/utils.js' +import Api from '@/api' +import asyncComponent from '@/utils/asyncComponent' +import './index.scss' + +const EditTable = asyncComponent(() => import('@/templates/zshare/modalform/modaleditable')) + +class TransferWrap extends Component { + static propTpyes = { + MenuID: PropTypes.string + } + + state = { + visible: false, + loading: false, + VersionName: '', + translist: [], + options: [] + } + + shouldComponentUpdate (nextProps, nextState) { + return !is(fromJS(this.state), fromJS(nextState)) + } + + verifySubmit = () => { + const { content, procName } = this.props + const { VersionName, options } = this.state + let value = content.replace(/^(\s*)|(\s*)$/ig, '') + + if (!VersionName) { + notification.warning({ + top: 92, + message: '璇烽�夋嫨浼犺緭鍙�', + duration: 5 + }) + return + } else if (!value) { + notification.warning({ + top: 92, + message: '瀛樺偍杩囩▼涓嶅彲涓虹┖', + duration: 5 + }) + return + } + + let regs = [] + options.forEach(item => { + if (item.origin && !/^\s+$/.test(item.origin) && item.origin !== item.value) { + regs.push({reg: new RegExp(item.origin, 'g'), value: item.value}) + } + }) + + regs.forEach(item => { + value = value.replace(item.reg, item.value) + }) + + let chars = [ + {key: 'drop', reg: /(^|\s)drop\s/ig}, + {key: 'alter', reg: /(^|\s)alter\s/ig}, + {key: 'object', reg: /(^|\s)object(\s|\()/ig}, + {key: 'kill', reg: /(^|\s)kill\s/ig}, + {key: '--', reg: /--/ig}, + {key: ',,', reg: /,,/ig} + ] + + let error = '' + + if (!/create(\s+)proc/ig.test(value)) { + error = '鑴氭湰涓繀椤讳娇鐢╟reate proc' + } + + chars.forEach(char => { + if (!error && char.reg.test(value)) { + error = '涓嶅彲浣跨敤' + char.key + } + }) + + if (error) { + notification.warning({ + top: 92, + message: error, + duration: 5 + }) + return + } + + let dropfunc = `IF EXISTS (SELECT * FROM sys.objects WHERE object_id = OBJECT_ID('${procName}') AND type in (N'P', N'PC')) mdrpk PROCEDURE ${procName}` + + let dropParam = { + func: 's_sVersionDetail_Add', + BID: VersionName, + VType: 'VSQL', + VSQL: window.btoa(window.encodeURIComponent(dropfunc)) + } + + let addParam = { + func: 's_sVersionDetail_Add', + BID: VersionName, + VType: 'VSQL', + VSQL: window.btoa(window.encodeURIComponent(value)) + } + + this.setState({ + loading: true + }) + + Api.genericInterface(dropParam).then(result => { + if (!result.status) { + notification.warning({ + top: 92, + message: result.message, + duration: 5 + }) + this.setState({ + loading: false + }) + return + } + + delete result.status + delete result.message + delete result.ErrCode + delete result.ErrMesg + result.func = 's_sVersionDetail_CloudAdd' + + Api.genericInterface(addParam).then(res => { + if (!res.status) { + notification.warning({ + top: 92, + message: res.message, + duration: 5 + }) + this.setState({ + loading: false + }) + return + } + + delete res.status + delete res.message + delete res.ErrCode + delete res.ErrMesg + res.func = 's_sVersionDetail_CloudAdd' + + Api.getCloudConfig(result).then(re => { + if (!re.status) { + notification.warning({ + top: 92, + message: re.message, + duration: 5 + }) + this.setState({ + loading: false + }) + return + } + + Api.getCloudConfig(res).then(r => { + if (!r.status) { + notification.warning({ + top: 92, + message: r.message, + duration: 5 + }) + this.setState({ + loading: false + }) + return + } else { + notification.success({ + top: 92, + message: '娣诲姞鎴愬姛锛�', + duration: 3 + }) + this.setState({ + loading: false, + visible: false + }) + } + }) + }) + }) + }) + } + + getTransList = () => { + const { content } = this.props + let value = content.replace(/^(\s*)|(\s*)$/ig, '') + + if (!value) { + notification.warning({ + top: 92, + message: '瀛樺偍杩囩▼涓嶅彲涓虹┖', + duration: 5 + }) + return + } + + let param = { + func: 's_get_sVersion', + dataM: 'Y', + PageSize: 9999, + PageIndex: 1, + OrderCol: 'ID desc' + } + + let options = [] + + let list = value.match(/\s+[a-z0-9_]+\.(dbo)?\./ig) + list && list.forEach(str => { + str = str.replace(/^\s/, '') + options.push({ + key: Utils.getuuid(), + origin: str, + value: str + }) + }) + + this.setState({ + options: options, + VersionName: '', + visible: true, + loading: false + }) + + Api.getCloudConfig(param).then(result => { + if (result.status) { + this.setState({ + translist: result.data + }) + } else { + notification.warning({ + top: 92, + message: result.message, + duration: 5 + }) + } + }) + } + + changeOptions = (value) => { + this.setState({options: value}) + } + + render () { + const { visible, loading, translist, options } = this.state + const columns = [{ title: '鍘熶俊鎭�', key: 'origin', width: '50%', fixed: true }, { title: '鏇挎崲涓�', width: '50%', key: 'value' }] + + return ( + <> + <Button icon="pull-request" className="mk-border-green" onClick={this.getTransList}>浼犺緭鍙�</Button> + <Modal + title="鍔犲叆浼犺緭鍙�" + wrapClassName="proc-transfer" + visible={visible} + width={900} + maskClosable={false} + okText="纭畾" + onOk={this.verifySubmit} + onCancel={() => { this.setState({ visible: false }) }} + confirmLoading={loading} + destroyOnClose + > + <Form.Item label="浼犺緭鍙�"> + <Select onChange={(val) => this.setState({VersionName: val})}> + {translist.map(option => + <Select.Option key={option.VersionName} value={option.VersionName}>{`${option.ProgramName}(${option.VersionName})`}</Select.Option> + )} + </Select> + </Form.Item> + {options.length > 0 ? <DndProvider backend={HTML5Backend}> + <Form.Item label="鏇挎崲椤�"> + <EditTable type="proc" columns={columns} value={options} onChange={this.changeOptions}/> + </Form.Item> + </DndProvider> : null} + </Modal> + </> + ) + } +} + +export default TransferWrap \ No newline at end of file diff --git a/src/views/systemproc/transfer/index.scss b/src/views/systemproc/transfer/index.scss new file mode 100644 index 0000000..fbcf2ce --- /dev/null +++ b/src/views/systemproc/transfer/index.scss @@ -0,0 +1,18 @@ +.proc-transfer { + .ant-form-item { + display: flex; + .ant-form-item-control-wrapper { + flex: 10; + + .ant-select { + width: 300px; + } + } + } + .operation-btn { + display: none; + } + .add-row { + display: none; + } +} \ No newline at end of file diff --git a/src/views/tabledesign/source.jsx b/src/views/tabledesign/source.jsx index 5e43351..058c775 100644 --- a/src/views/tabledesign/source.jsx +++ b/src/views/tabledesign/source.jsx @@ -186,6 +186,18 @@ }, { type: 'col', + label: '鑷畾涔夊垪', + subType: 'custom', + $init: true + }, + { + type: 'col', + label: '鍏紡', + subType: 'formula', + $init: true + }, + { + type: 'col', label: '鍥剧墖', subType: 'picture', $init: true @@ -210,20 +222,8 @@ }, { type: 'col', - label: '鑷畾涔夊垪', - subType: 'custom', - $init: true - }, - { - type: 'col', label: '鍚堝苟鍒�', subType: 'colspan', - $init: true - }, - { - type: 'col', - label: '鍏紡', - subType: 'formula', $init: true }, { -- Gitblit v1.8.0