Commit f5999562 authored by shaoan123's avatar shaoan123

更改表字段界面样式

parent a23d6f15
Pipeline #31263 skipped with stages
......@@ -10,9 +10,10 @@ import {
Popconfirm,
notification,
Spin,
Tooltip
Tooltip,
Badge, Spac
} from 'antd';
import { EditOutlined, DeleteOutlined, FontColorsOutlined, PlusSquareOutlined,SortDescendingOutlined } from '@ant-design/icons';
import { EditOutlined, DeleteOutlined, FontColorsOutlined, PlusSquareOutlined, SortDescendingOutlined, DownOutlined } from '@ant-design/icons';
import PageContainer from '@/components/BasePageContainer';
import { CM_Table_LoadTable, removeTable, loadUnattachedTables } from '@/services/platform/bs'
import styles from './index.less'
......@@ -21,12 +22,13 @@ import AddTablelList from './components/Field/addTable'
import AffiliateAdd from './components/Field/affiliateAdd'
import FieldsConfig from './components/Field/fieldsConfig'
import LoadGroup from './components/Field/loadGroup'
import { useHistory } from 'react-router-dom';
const { Search } = Input;
const { Option } = Select;
const placeholder = "请输入表名"
const TableManager = () => {
const history = useHistory();
const [visible, setVisible] = useState(false); // 弹窗
const [type, setType] = useState(''); // 弹窗类型
const [formObj, setFormObj] = useState({});
......@@ -34,111 +36,9 @@ const TableManager = () => {
const [searchValue, setSearchValue] = useState('')
const [treeLoading, setTreeLoading] = useState(true)
const [tableList, setTableList] = useState([])
const columns = [
{
title: '名称',
dataIndex: 'tableName',
key: 'tableName',
width:300,
render: text => <a>{text}</a>,
},
{
title: '别名',
dataIndex: 'tableAlias',
key: 'tableAlias',
align: 'center',
width: 200,
},
{
title: '表格样式',
dataIndex: 'tableStyle',
key: 'tableStyle',
align: 'center',
width: 150,
},
{
title: '字段数量',
dataIndex: 'fieldCount',
key: 'fieldCount',
align: 'center'
},
{
title: '缺少字段',
dataIndex: 'missingFieldCount',
key: 'missingFieldCount',
align: 'center',
render: text => {
let dom = ReactHtmlParser(text)
return (<div>{dom}</div>)
}
},
{
title: '未附加',
dataIndex: 'extraFieldCount',
key: 'extraFieldCount',
align: 'center'
},
{
title: '分组数量',
dataIndex: 'groupCount',
key: 'groupCount',
align: 'center'
},
{
title: '操作',
width: 250,
ellipsis: true,
align: 'center',
render: (text, record) => (
<Space>
<Tooltip title="修改">
<EditOutlined
onClick={() => changeDesc(record)}
style={{ fontSize: '20px', color: '#1890FF' }}
/>
</Tooltip>
<Tooltip title="字段配置">
<FontColorsOutlined
onClick={() => fieldsConfig(record)}
style={{ fontSize: '16px', color: '#1890FF' }}
/>
</Tooltip>
<Tooltip title="附加">
<PlusSquareOutlined
onClick={() => add(record)}
style={{ fontSize: '16px', color: '#1890FF' }}
/>
</Tooltip>
<Tooltip title="分组与排序">
<SortDescendingOutlined
onClick={() => sort(record)}
style={{ fontSize: '16px', color: '#1890FF' }}
/>
</Tooltip>
<div onClick={e => e.stopPropagation()}>
<Popconfirm
title="是否删除该表?"
okText="确认"
cancelText="取消"
onConfirm={() => {
deleteChart(record);
}}
>
<Tooltip title="删除">
<DeleteOutlined
style={{ fontSize: '16px', color: '#e86060' }}
/>
</Tooltip>
</Popconfirm>
</div>
</Space>
),
},
];
const [groupArr, setGroupArr] = useState({})
const [tableData, setTableData] = useState([])
const [spread , setSpread]=useState([])
useEffect((record) => {
loadTable(searchValue)
getField()
......@@ -176,7 +76,7 @@ const TableManager = () => {
}
})
}
const onSubmit = prop => {
setVisible(false);
setFlag(flag + 1)
......@@ -195,11 +95,12 @@ const TableManager = () => {
//字段配置
const fieldsConfig = (record) => {
setFormObj(record);
setType('config');
setVisible(true);
history.push(`/platformCenter/bsmanger/filedConfig/${record.tableName}`)
// setType('config');
// setVisible(true);
}
//分组与排序
const sort = (record)=>{
const sort = (record) => {
setFormObj(record);
setType('sort');
setVisible(true);
......@@ -232,13 +133,182 @@ const TableManager = () => {
setTreeLoading(false)
if (res.msg === 'Ok') {
setTableData(res.data.root)
let groupData = formateArrDataA(res.data.root, 'groupName')
let newArr = []
Object.keys(groupData).map((item,index) => {
newArr.push({ type: item,key:index })
})
setGroupArr({ groupData, newArr })
}
}
)
}
const formateArrDataA = (initialArr, name) => {
// 判定传参是否符合规则
if (!(initialArr instanceof Array)) {
return '请传入正确格式的数组'
}
if (!name) {
return '请传入对象属性'
}
//先获取一下这个数组中有多少个"name"
let nameArr = []
for (let i in initialArr) {
if (nameArr.indexOf(initialArr[i][`${name}`]) === -1) {
nameArr.push(initialArr[i][`${name}`])
}
}
//新建一个包含多个list的结果对象
let tempObj = {}
// 根据不同的"name"生成多个数组
for (let k in nameArr) {
for (let j in initialArr) {
if (initialArr[j][`${name}`] == nameArr[k]) {
// 每次外循环时新建一个对应"name"的数组, 内循环时当前数组不变
tempObj[nameArr[k]] = tempObj[nameArr[k]] || []
tempObj[nameArr[k]].push(initialArr[j])
}
}
}
for (let key in tempObj) {
let arr = []
tempObj[key].map(item => {
tempObj[key] = arr;
arr.push(item)
})
}
return tempObj
}
const expandedRowRender = () => {
const columns1 = [
{
title: '名称',
dataIndex: 'tableName',
key: 'tableName',
width: 300,
render: text => <a>{text}</a>,
},
{
title: '别名',
dataIndex: 'tableAlias',
key: 'tableAlias',
align: 'center',
width: 200,
},
{
title: '表格样式',
dataIndex: 'tableStyle',
key: 'tableStyle',
align: 'center',
width: 150,
},
{
title: '字段数量',
dataIndex: 'fieldCount',
key: 'fieldCount',
align: 'center',
width: 200,
},
{
title: '缺少字段',
dataIndex: 'missingFieldCount',
key: 'missingFieldCount',
align: 'center',
width: 200,
render: text => {
let dom = ReactHtmlParser(text)
return (<div>{dom}</div>)
}
},
{
title: '未附加',
dataIndex: 'extraFieldCount',
key: 'extraFieldCount',
align: 'center',
width: 200,
},
{
title: '分组数量',
dataIndex: 'groupCount',
key: 'groupCount',
align: 'center',
width: 200,
},
{
title: '操作',
width: 250,
ellipsis: true,
key: 'tableID',
align: 'center',
render: (text, record) => (
<Space>
<Tooltip title="修改">
<EditOutlined
onClick={() => changeDesc(record)}
style={{ fontSize: '20px', color: '#1890FF' }}
/>
</Tooltip>
<Tooltip title="字段配置">
<FontColorsOutlined
onClick={() => fieldsConfig(record)}
style={{ fontSize: '16px', color: '#1890FF' }}
/>
</Tooltip>
<Tooltip title="附加">
<PlusSquareOutlined
onClick={() => add(record)}
style={{ fontSize: '16px', color: '#1890FF' }}
/>
</Tooltip>
<Tooltip title="分组与排序">
<SortDescendingOutlined
onClick={() => sort(record)}
style={{ fontSize: '16px', color: '#1890FF' }}
/>
</Tooltip>
<div onClick={e => e.stopPropagation()}>
<Popconfirm
title="是否删除该表?"
okText="确认"
cancelText="取消"
onConfirm={() => {
deleteChart(record);
}}
>
<Tooltip title="删除">
<DeleteOutlined
style={{ fontSize: '16px', color: '#e86060' }}
/>
</Tooltip>
</Popconfirm>
</div>
</Space>
),
},
];
return <Table columns={columns1} dataSource={spread} pagination={false} />;
};
const columns = [
{ title: '类型', dataIndex: 'type', key: 'type' },
];
const openClick=(status, item)=>{
if (!status) return
let arr = []
groupArr.groupData[item.type].map((item,index)=>{
arr.push({...item,key:index})
})
setSpread(arr)
}
return (
<Spin tip="loading..." spinning={treeLoading}>
<PageContainer>
<div className={styles.tablemanager_container}>
<div className={styles.operate_bar}>
<div className={styles.fast_search}>
......@@ -259,7 +329,7 @@ const TableManager = () => {
</div>
<div className={styles.table_container}>
<Table
{/* <Table
columns={columns}
dataSource={tableData}
//pagination={{ pageSize: 10 }}
......@@ -275,6 +345,24 @@ const TableManager = () => {
showQuickJumper: true,
showSizeChanger: true,
}}
/> */}
<Table
className="components-table-demo-nested"
columns={columns}
expandable={{ expandedRowRender }}
dataSource={groupArr.newArr}
onExpand={openClick} // 展开时触发的回调
size="small"
style={{height:'8rem'}}
pagination={{
showTotal: (total, range) =>
`第${range[0]}-${range[1]} 条/共 ${total} 条`,
pageSizeOptions: [10, 20, 50, 100],
defaultPageSize: 20,
showQuickJumper: true,
showSizeChanger: true,
}}
/>
</div>
</div>
......@@ -313,7 +401,7 @@ const TableManager = () => {
callBackSubmit={onSubmit}
/>
)}
{visible && type === 'sort' && (
{visible && type === 'sort' && (
<LoadGroup
visible={visible}
type={type}
......
import React, { useState, useEffect, useCallback, useRef } from 'react';
import { Form, Modal, Space, Divider, Radio, Checkbox } from 'antd';
import {
} from '@/services/platform/bs'
import styles from './index.less'
import Sortable from 'sortablejs';
const CheckboxGroup = Checkbox.Group;
const AddModal = props => {
const { callBackSubmit = () => { }, isType, formObj, visible, filed, characterValue, newCheckedList } = props;
const [loading, setLoading] = useState(false);
const [value, setValue] = useState('');
const [checkValue, setCheckValue] = useState([]);
const [form] = Form.useForm();
const [title, setTitle] = useState([])
const { Item } = Form;
const [checkedList, setCheckedList] = useState([]);//选中的复选框内容
const [indeterminate, setIndeterminate] = useState([]);
const [checkAll, setCheckAll] = useState([]);
const [selectData, setSelectData] = useState([])
let objArr = []
const onChangeList = (list, index) => {
const checkedListArr = [...checkedList]
checkedListArr[index] = list
setCheckedList(checkedListArr);
};
const onCheckAllChange = e => {
const indeterminateArr = [...indeterminate]
const checkAllArr = [...checkAll]
const checkedListArr = [...checkedList]
checkAllArr[e.target.index] = e.target.checked
indeterminateArr[e.target.index] = false
e.target.checked ? checkedListArr[e.target.index] = e.target.checkvalue : checkedListArr[e.target.index] = []
setCheckedList(checkedListArr);
setIndeterminate(indeterminateArr);
setCheckAll(checkAllArr);
};
//监听用户选择的字段名
useEffect(() => {
selectAll()
}, [checkedList]);
const selectAll = () => {
objArr = []
checkedList.map(item => {
objArr = objArr.concat(item)
})
setSelectData(objArr)
}
const onSubmit = () => {
isType === 'rule' ? callBackSubmit(`${value === '无' || value === '' ? '' : value + ','}${checkValue.join(',')}`) : callBackSubmit({ checkedList, str: selectData.join(",") });
};
useEffect(() => {
if (isType != '' && isType === 'rule') {
setValue(formObj.numerical)
setCheckValue(formObj.rule)
}
else if (isType === 'characteristics') {
let arr = Object.keys(filed)
setTitle(arr)
console.log('arr', arr);
let indeterminateArr = []
let checkAllArr = []
arr.map((item, index) => {
indeterminateArr.push(true)
checkAllArr.push(false)
})
setCheckedList(newCheckedList)
setIndeterminate(indeterminateArr)
setCheckAll(checkAllArr)
let newArr = characterValue.length? characterValue.split(","):[]
setSelectData(newArr)
draftSort()
}
}, [visible]);
//单选框变化时触发的事件
const handleChange = (e) => {
setValue(e.target.value)
if (e.target.value === '无') {
setCheckValue([])
}
}
//复选框变化时触发的事件
const onChange = (e) => {
setCheckValue(e)
if (e.length && value == '无') {
setValue('')
}
}
//拖拽初始化及逻辑
const draftSort = () => {
let el = document.getElementById('doctor-drag-items');
if (el) {
let sortable = Sortable.create(el, {
animation: 100, //动画参数
onEnd: function (evt) { //拖拽完毕之后发生,只需关注该事件
let arr = [];
let len = evt.from.children.length;
for (let i = 0; i < len; i++) {
arr.push(evt.from.children[i].getAttribute('drag-id'))
}
setSelectData(arr)
}
});
}
}
return (
<Modal
title={isType === 'rule' ? '选择验证规则' : '字段集选择'}
bodyStyle={{ width: '100%', minHeight: '100px' }}
style={{ top: '10px' }}
width="700px"
destroyOnClose
centered ={true}
maskClosable={false}
cancelText="取消"
okText="确认"
{...props}
onOk={() => onSubmit()}
confirmLoading={loading}
forceRender={true}
getContainer={false}
>
{visible && isType === 'rule' && (
<>
<Radio.Group onChange={handleChange} value={value}>
<Space direction="vertical">
<Radio value='无'>无(清空选中)</Radio>
<Radio value='number'>数值(number)</Radio>
<Radio value='digits'>整数(digits)</Radio>
<Radio value='email'>邮箱(email)</Radio>
<Radio value='identity'>身份证号(identity)</Radio>
<Radio value='mobile'>手机号(mobile)</Radio>
<Radio value='bankAccount'>银行卡号(bankAccount)</Radio>
<Radio value='timeControl'>时间控制(timeControl)</Radio>
</Space>
</Radio.Group>
<Checkbox.Group style={{ width: '100%', marginTop: '1rem' }} onChange={onChange} value={checkValue}>
<Space direction="vertical">
<Checkbox value="required">必填(required)</Checkbox>
<Checkbox value="emphasis">强调(emphasis)</Checkbox>
<Checkbox value="sensitive">敏感(sensitive)</Checkbox>
</Space>
</Checkbox.Group>
</>
)}
{visible && isType === 'characteristics' && (
<div className={styles.listCard}>
<div className={styles.cardItem} style={{ borderRight: '1px solid #99bbe8' }}>
<Divider orientation="left" style={{ margin: '0 0 10px 0', backgroundColor: '#dfe8f6' }}>待选字段列表</Divider>
<div className={styles.cardContent}>
{title.map((item, index) => {
return <div className={styles.cardItemData} key={index}>
<Divider orientation="left" style={{ margin: '0 0 10px 0', color: '#15428b', borderTopColor: '#99bbe8' }}>{item} <Checkbox indeterminate={indeterminate[index]} onChange={onCheckAllChange} index={index} checkvalue={filed[item]} checked={checkAll[index]}> </Checkbox></Divider>
<CheckboxGroup options={filed[item]} value={checkedList[index]} onChange={(e) => onChangeList(e, index)} /></div>
})}
</div>
</div>
<div className={styles.cardItem}>
<Divider orientation="left" style={{ margin: '0 0 10px 0', backgroundColor: '#dfe8f6' }}>已选字段列表</Divider>
<div className={styles.cardContent}>
<div className={styles.doctorTable}>
<table>
<thead>
<tr>
<td>字段名</td>
</tr>
</thead>
<tbody id='doctor-drag-items'>
{selectData && selectData.length > 0 ?
selectData.map((item, index) => {
return <tr drag-id={item} key={index} style={{ cursor: 'move' }}>
<td><span title={item}>{item}</span></td>
</tr>
})
: <tr><td colSpan='10' style={{ textAlign: 'center' }}>暂无数据</td></tr>
}
</tbody>
</table>
</div>
</div>
</div>
</div>
)
}
</Modal>
);
};
export default AddModal;
import React, { useState, useEffect } from 'react';
import { Form, Modal, Input, Select, Radio, Checkbox, notification, Tooltip } from 'antd';
import {
getField, loadTableFields, LoadEventFields, LoadEventType, UpdateFields
} from '@/services/platform/bs'
import styles from './index.less'
import ChangeAdd from './changeAdd'
import { PlusSquareOutlined } from '@ant-design/icons';
import { shape } from 'prop-types';
const AddModal = props => {
const { callBackSubmit = () => { }, isType, itemData, isVisible, formObj1 } = props;
const [loading, setLoading] = useState(false);
const [fieldName, setFieldName] = useState([]); // 弹窗
const [eventList, setEventList] = useState([]); // 事件
const [filed, setFiled] = useState({}); // 事件
const [verification, setVerification] = useState([]);
const [Shape, setShape] = useState('文本')
const [characteristics, setCharacteristics] = useState(['文本', '数值', '唯一值文本', '多行文本', '编码', '地址', '本人部门', '本人姓名', '本人ID', '选择器', '搜索选择器', '值选择器', '值复选器', '业务选择器', '可编辑值选择器', '平铺值选择器', '站点选择器', '人员选择器', '人员选择器新', '城市选择器', '台账选择器', '附件', '可预览附件', '图片', '可预览图片', '录音', '视频', '日期时间', '日期', '日期月份', '日期年份', '日期周', '时分秒', '设备选择', '坐标控件', '区域控件', '路径控件', '智能抄表', '二维码识别', '设备二维码', '位置坐标'])
const [visible, setVisible] = useState(false); // 弹窗
const [isShow, setIsShow] = useState(false); // 弹窗
const [type, setType] = useState(''); // 弹窗类型
const [formObj, setFormObj] = useState({ rule: [], numerical: '' });
const [characterValue, setCharacterValue] = useState('')
const [pramData, setPramData] = useState({ Unit: '', ExceptionEvent: '', Group: '', RowSpan: 0, ColSpan: 0, ReadOnly: false, EditableLater: false, ExceptionValue: '', Preset: '', picture: false, must: false, coordinates: false })
const [checkedList, setCheckedList] = useState([]);//选中的复选框内容
const { TextArea } = Input;
const [form] = Form.useForm();
const { Item } = Form;
// 提交
const onSubmit = () => {
form.validateFields().then(validate => {
if (validate) {
setLoading(true);
let obj = form.getFieldsValue();
console.log('obj', obj);
let data = [{ Unit: pramData.Unit || '', StoreType: "nvarchar(255)", Group: pramData.Group || '', Shape, ExceptionEvent: pramData.ExceptionEvent || '', RowSpan: pramData.RowSpan || 0, ColSpan: pramData.ColSpan || 0, ReadOnly: pramData.ReadOnly || false, EditableLater: pramData.EditableLater || false, ExceptionValue: pramData.ExceptionValue || '', Preset: pramData.Preset || '', ID: Number(itemData.ID), Name: obj.Name, Alias: obj.Alias, SyncEvent: obj.SyncEvent, ValidationRule: obj.ValidationRule, ExceptionEventFields: characterValue }]
switch (Shape) {
case '编码':
data[0].Config = `${obj.code}.${obj.prefix ? obj.prefix : ''}`;
break
case '坐标控件':
pramData.coordinates ? data[0].Config = '当前坐标' : data[0].Config = '';
break
case '图片': case '可预览图片':
data[0].Preset = pramData.picture ? '拍照相册' : '';
data[0].ValidationRule = pramData.must ? 'required' : ''
break
default:
data[0].Config = obj.Config;
}
UpdateFields(data).then(res => {
setLoading(false);
if (res.msg === "Ok" || res.msg === "") {
form.resetFields();
callBackSubmit();
notification.success({
message: '提示',
duration: 3,
description: '修改成功',
});
} else {
notification.error({
message: '提示',
duration: 3,
description: res.msg,
});
}
})
}
});
};
useEffect(() => {
if (isType != '') {
let req1 = getField({ fieldID: itemData.ID })
let req2 = loadTableFields({ tableName: formObj1 })
let req3 = LoadEventType({})
Promise.all([req1, req2, req3]).then(res => {
res[1].msg === 'Ok' && setFieldName(res[1].data.root)
res[2].msg === 'Ok' && setEventList(res[2].data.root)
if (res[0].msg === 'Ok') {
form.setFieldsValue({ ...res[0].data.root })
if (res[0].data.root.ExceptionEventFields === '') {
setCharacterValue('')
setIsShow(false)
} else {
setIsShow(true)
setCharacterValue(res[0].data.root.ExceptionEventFields)
}
setShape(res[0].data.root.Shape)
let coordinates = false, picture = false, must = false
switch (res[0].data.root.Shape) {
case '坐标控件':
res[0].data.root.Config === "当前坐标" ? coordinates = true : coordinates = false
break
case '图片': case '可预览图片':
res[0].data.root.Preset === "拍照相册" ? picture = true : picture = false;
res[0].data.root.ValidationRule === "required" ? must = true : must = false
break
case '编码':
let code = res[0].data.root.Config.split(".")
form.setFieldsValue({ code: code[0] || '', prefix: code[1] === "undefined" ? '' : code[1] });
break
}
setPramData({ ...res[0].data.root, coordinates, must, picture })
}
})
}
}, [isVisible]);
const layout = {
layout: 'horizontal',
labelCol: {
span: 4,
},
wrapperCol: {
span: 17,
},
};
const handleChange = (value) => {
form.setFieldsValue({ schemename: value });
}
const onOK = prop => {
setVisible(false);
if (type === 'rule') {
form.setFieldsValue({ ValidationRule: prop });
} else {
setCheckedList(prop.checkedList)
setCharacterValue(prop.str)
}
};
const add = (type) => {
let obj = form.getFieldsValue();
let data = { ...formObj }
if (obj.ValidationRule) {
let arr = obj.ValidationRule.split(",")
arr.map(item => {
switch (item) {
case 'required':
data.rule.push(item);
break;
case 'emphasis':
data.rule.push(item);
break;
case 'sensitive':
data.rule.push(item);
break;
default:
data.numerical = item
}
})
} else {
data = { rule: [], numerical: '' }
}
setType(type);
setFormObj(data)
setVisible(true);
}
const handleEvent = (value, e) => {
let data = { ...pramData }
data.ExceptionEvent = e.name
if (e.tablename) {
getFieldData(e.tablename)
setPramData(data)
} else {
setIsShow(false)
setFiled({})
setCharacterValue('')
}
}
const getFieldData = (value) => {
LoadEventFields({ eventTableName: value, distinctFields: '' }).then(res => {
if (res.msg === 'Ok') {
setFiled(formateArrDataA(res.data.root, 'group'))
setIsShow(true)
}
})
}
const formateArrDataA = (initialArr, name) => {
// 判定传参是否符合规则
if (!(initialArr instanceof Array)) {
return '请传入正确格式的数组'
}
if (!name) {
return '请传入对象属性'
}
//先获取一下这个数组中有多少个"name"
let nameArr = []
for (let i in initialArr) {
if (nameArr.indexOf(initialArr[i][`${name}`]) === -1) {
nameArr.push(initialArr[i][`${name}`])
}
}
//新建一个包含多个list的结果对象
let tempObj = {}
// 根据不同的"name"生成多个数组
for (let k in nameArr) {
for (let j in initialArr) {
if (initialArr[j][`${name}`] == nameArr[k]) {
// 每次外循环时新建一个对应"name"的数组, 内循环时当前数组不变
tempObj[nameArr[k]] = tempObj[nameArr[k]] || []
tempObj[nameArr[k]].push(initialArr[j])
}
}
}
for (let key in tempObj) {
let arr = []
tempObj[key].map(item => {
tempObj[key] = arr;
arr.push(item.fieldName)
})
}
return tempObj
}
const handleCharacteristics = (value) => {
let data = { ...pramData }
setShape(value)
data.must = false
data.coordinates = false
data.picture = false
data.Preset = ''
setPramData(data)
form.setFieldsValue({ ValidationRule: '' });
if (value.indexOf("日期") != -1 || value === "时分秒") {
form.setFieldsValue({ Config: undefined });
}
}
const onCharacterValue = (e) => {
setCharacterValue(e.target.value)
}
const onChangeReady = (e, str) => {
let data = { ...pramData }
switch (str) {
case 'ReadOnly':
data.ReadOnly = e.target.checked;
break;
case 'EditableLater':
data.EditableLater = e.target.checked
break;
case 'must':
data.must = e.target.checked
break;
case 'picture':
data.picture = e.target.checked
break;
case 'coordinates':
data.coordinates = e.target.checked
break;
}
setPramData(data)
}
const handleInput = (e, str) => {
let data = { ...pramData }
switch (str) {
case 'Unit':
data.Unit = e.target.value;
break;
case 'RowSpan':
data.RowSpan = e.target.value;
break;
case 'Preset':
data.Preset = e.target.value;
break;
case 'ExceptionValue':
data.ExceptionValue = e.target.value;
break;
default:
break
}
setPramData(data)
}
const handleSeparator = (value) => {
let data = { ...pramData }
switch (value) {
case '6':
data.Preset = '是'
form.setFieldsValue({ Config: '是,否' });
break;
case '7':
data.Preset = '否'
form.setFieldsValue({ Config: '是,否' });
break;
case '8':
data.Preset = '否'
form.setFieldsValue({ Config: '否,是' });
break;
}
setPramData(data)
}
return (
<>
<Modal
title='修改'
bodyStyle={{ width: '100%', minHeight: '100px' }}
width="700px"
destroyOnClose
maskClosable={false}
centered ={true}
cancelText="取消"
okText="确认"
{...props}
visible={isVisible}
onOk={() => onSubmit()}
confirmLoading={loading}
forceRender={true}
getContainer={false}
>
{isVisible && (
<Form form={form} {...layout} >
<Item
label="字段名"
name="Name"
rules={[{ required: true, message: '请输入表名' }]}
>
<Input placeholder="请输入别名" disabled/>
</Item>
<Item
label="别名"
name="Alias"
>
<Input placeholder="请输入别名" allowClear />
</Item>
<Item
name="ReadOnly"
label="属性"
>
<div>
<Checkbox checked={pramData.ReadOnly} onChange={(e) => onChangeReady(e, 'ReadOnly')}>只读</Checkbox>
<Checkbox checked={pramData.EditableLater} onChange={(e) => onChangeReady(e, 'EditableLater')}>允许补正(事后修改)</Checkbox>
</div>
</Item>
<Item
label="同步"
name="SyncEvent"
>
<Radio.Group>
<Radio value={0} style={{ marginRight: '0.5rem' }}>不同步</Radio>
<Radio value={1} style={{ marginRight: '0.5rem' }}>工单 → 事件</Radio>
<Radio value={2} >事件(上报时) → 工单</Radio>
</Radio.Group>
</Item>
<Item
label="形态"
>
<div className={styles.listEvent}>
<Select style={{ width: '42%' }} value={Shape} onChange={handleCharacteristics}>
{characteristics.length ? characteristics.map((item, index) => { return <Select.Option key={index} value={item}>{item}</Select.Option>; }) : ''}
</Select>
<div className={styles.unit}>单位:<Input style={{ width: '5rem' }} placeholder="" allowClear value={pramData.Unit} onChange={(e) => handleInput(e, 'Unit')} /></div>
<div className={styles.unit}>宽:<Input style={{ width: '4rem' }} placeholder="" allowClear value={pramData.RowSpan} onChange={(e) => handleInput(e, 'RowSpan')} /></div>
</div>
</Item>
{(() => {
switch (Shape) {
case '编码':
return <>
<Item
label="前缀"
name="prefix"
>
<Input style={{ width: '95%' }} placeholder="" allowClear />
</Item>
<Item
label="编码方式"
name="code"
>
<Radio.Group>
<Radio value='年份编码' style={{ marginRight: '0.5rem' }}>XJ-2019-000001(前缀-年份-六位编码)</Radio>
<Radio value='年月编码' style={{ marginRight: '0.5rem' }}>XJ-201909-000001(前缀-年份月份-六位编码)</Radio>
<Radio value='一般编码' defaultChecked >XJ00000001(前缀 八位编码)</Radio>
</Radio.Group>
</Item>
</>
case '值选择器': case '值复选器': case '可编辑值选择器': case '平铺值选择器':
return <> <Item
label="可选值"
name="Config"
>
<TextArea allowClear />
</Item>
<Item
colon={false}
label=" "
> <div style={{ display: 'flex', alignItems: 'center' }}>
<span style={{ marginRight: '0.4rem' }}>以英文逗号为分隔符填写,或其他分隔符粘贴:</span>
<Select onChange={handleSeparator} style={{ width: '30%' }}>
<Select.Option value='0'>以,分隔(英文逗号)</Select.Option>
<Select.Option value='1'>以/分隔(正斜杠)</Select.Option>
<Select.Option value='2'>以\\分隔(反斜杠)</Select.Option>
<Select.Option value='3'>以、分隔(中文顿号)</Select.Option>
<Select.Option value='4'>以;分隔(英文分号)</Select.Option>
<Select.Option value='5'>以;分隔(中文分号)</Select.Option>
<Select.Option value='6'>(是)/否</Select.Option>
<Select.Option value='7'>是/(否)</Select.Option>
<Select.Option value='8'>(否)/是</Select.Option>
</Select>
</div>
</Item>
</>
case '图片': case '可预览图片':
return <Item
name="ReadOnly"
label="选项"
>
<div>
<Checkbox checked={pramData.picture} onChange={(e) => onChangeReady(e, 'picture')}>允许从相册选取</Checkbox>
<Checkbox checked={pramData.must} onChange={(e) => onChangeReady(e, 'must')}>必填字段</Checkbox>
</div>
</Item>
case '日期时间': case '日期': case '日期月份': case '日期年份': case '日期周': case '时分秒':
return <Item
label="选项"
name="Config"
>
<Radio.Group style={{ marginTop: '0.3rem' }}>
<Radio value='默认为空' defaultChecked style={{ width: '18rem', marginBottom: '0.5rem' }}>默认为空</Radio>
<Radio value='' >默认为当前时间</Radio>
<Radio value='不可选择' style={{ width: '18rem' }}>锁定为当前时间(通过用户点击刷新)</Radio>
<Radio value='不超过当前时间' >不超过当前时间</Radio>
</Radio.Group>
</Item>
case '坐标控件':
return <Item
label="选项"
name="Config"
>
<div>
<Checkbox value='当前坐标' style={{ marginRight: '0.2rem' }} checked={pramData.coordinates} onChange={(e) => onChangeReady(e, 'coordinates')}></Checkbox>锁定为当前位置坐标
</div>
</Item>
default:
return <Item
label="配置"
name="Config"
>
<TextArea allowClear />
</Item>
}
}
)()}
{Shape === '图片' || Shape === '可预览图片' ? '' :
<Item
label="预设值"
>
<div className={styles.listEvent}>
<Input style={{ width: '40%', height: '1.8rem' }} value={pramData.Preset} onChange={(e) => handleInput(e, 'Preset')} placeholder="" allowClear />
<Item
style={{ marginLeft: '1rem' }}
label="验证"
name="ValidationRule"
style={{ margin: '0 0 0 1rem' }}
>
<Input style={{ width: '95%' }} placeholder="" allowClear />
</Item>
<Tooltip title="选择验证规则">
<PlusSquareOutlined
onClick={() => add('rule')}
style={{ fontSize: '24px', color: '#1890FF', display: 'flex', alignItems: 'center' }}
/>
</Tooltip>
</div>
</Item>
}
<Item
label="异常值"
>
<div className={styles.listEvent}>
<Input style={{ width: '40%', height: '1.8rem' }} value={pramData.ExceptionValue} onChange={(e) => handleInput(e, 'ExceptionValue')} placeholder="" allowClear />
<Item
style={{ marginLeft: '1rem' }}
label="触发事件"
name="ExceptionEvent"
style={{ margin: '0 0 0 1rem' }}
>
<Select style={{ width: '12rem' }} onChange={handleEvent}>
{eventList.length ? eventList.map((item, index) => { return <Select.Option key={index} tablename={item.TableName} name={item.Name} value={item.ID}>{item.Name}</Select.Option>; }) : ''}
</Select>
</Item>
</div>
</Item>
<Item
label="字段集"
>
<div className={styles.listEvent}>
<Input style={{ width: '93%' }} placeholder="" disabled={!isShow} onChange={onCharacterValue} allowClear value={characterValue} />
<Tooltip title={!isShow ? '' : '字符集选择'}>
<PlusSquareOutlined
onClick={() => !isShow ? '' : add('characteristics')}
style={{ fontSize: '24px', color: !isShow ? 'gray' : '#1890FF', cursor: !isShow ? 'no-drop' : 'pointer', display: 'flex', alignItems: 'center', marginLeft: '0.5rem' }}
/>
</Tooltip>
</div>
</Item>
</Form>
)}
</Modal>
<ChangeAdd
visible={visible}
onCancel={() => setVisible(false)}
callBackSubmit={onOK}
newCheckedList={checkedList}
isType={type}
filed={filed}
characterValue={characterValue}
formObj={formObj} />
</>
);
};
export default AddModal;
import React, { useState, useEffect } from 'react';
import {
Form,
Modal,
Space,
Table,
Button,
Popconfirm,
Spin,
notification,
} from 'antd';
import { reloadTableFields, removeFields } from '@/services/platform/bs';
import FieldEditor from './fieldEditor';
import { useHistory } from 'react-router-dom';
import styles from './index.less'
const AddModal = props => {
const history = useHistory();
const [tableData, setTableData] = useState([]);
const { callBackSubmit = () => { }, type, visible } = props;
const [loading, setLoading] = useState(false);
const [treeLoading, setTreeLoading] = useState(false);
const [formObj, setFormObj] = useState('');
const [form] = Form.useForm();
const [flag, setFlag] = useState(0); // 弹窗类型
const [isVisible, setIsVisible] = useState(false); // 弹窗
const [isType, setIsType] = useState(''); // 弹窗类型
const [itemData, setItemData] = useState({});
const { Item } = Form;
// 提交
const onSubmit = () => {
form.validateFields().then(validate => {
if (validate) {
setLoading(true);
let obj = form.getFieldsValue();
}
});
};
const columns = [
{
title: '字段名',
dataIndex: 'name',
key: 'name',
width: 150,
render: text => <a>{text}</a>,
},
{
title: '别名',
dataIndex: 'alias',
key: 'alias',
align: 'center',
},
{
title: '字段类型',
dataIndex: 'storeType',
key: 'storeType',
align: 'center',
},
{
title: '形态',
dataIndex: 'shape',
key: 'shape',
align: 'center',
},
{
title: '配置',
dataIndex: 'config',
key: 'config',
align: 'center',
},
{
title: '只读',
dataIndex: 'readOnly',
key: 'readOnly',
align: 'center',
},
{
title: '同步',
dataIndex: 'syncEvent',
key: 'syncEvent',
align: 'center',
},
{
title: '操作',
width: 250,
ellipsis: true,
align: 'center',
render: (text, record) => (
<Space>
<Button
type="primary"
size="small"
onClick={() => {
editor(record);
}}
>
编辑
</Button>
<div onClick={e => e.stopPropagation()}>
<Popconfirm
title="是否删除该字段?"
okText="确认"
cancelText="取消"
onConfirm={() => {
deleteChart(record);
}}
>
<Button size="small" danger>
删除
</Button>
</Popconfirm>
</div>
</Space>
),
},
];
const editor = record => {
setIsType('edit');
setIsVisible(true);
setItemData(record);
};
const Submit = prop => {
setIsVisible(false);
setFlag(flag + 1);
};
useEffect(() => {
if (props.match.params.id) {
setFormObj(props.match.params.id)
setTreeLoading(true);
reloadTableFields({
tableName: props.match.params.id,
}).then(res => {
setTreeLoading(false);
if (res.msg === 'Ok') {
setTableData(res.data.root);
console.log(formateArrDataA(res.data.root,'groupName'));
}
});
}
}, [flag]);
const formateArrDataA = (initialArr, name) => {
// 判定传参是否符合规则
if (!(initialArr instanceof Array)) {
return '请传入正确格式的数组'
}
if (!name) {
return '请传入对象属性'
}
//先获取一下这个数组中有多少个"name"
let nameArr = []
for (let i in initialArr) {
if (nameArr.indexOf(initialArr[i][`${name}`]) === -1) {
nameArr.push(initialArr[i][`${name}`])
}
}
//新建一个包含多个list的结果对象
let tempObj = {}
// 根据不同的"name"生成多个数组
for (let k in nameArr) {
for (let j in initialArr) {
if (initialArr[j][`${name}`] == nameArr[k]) {
// 每次外循环时新建一个对应"name"的数组, 内循环时当前数组不变
tempObj[nameArr[k]] = tempObj[nameArr[k]] || []
tempObj[nameArr[k]].push(initialArr[j])
}
}
}
for (let key in tempObj) {
let arr = []
tempObj[key].map(item => {
tempObj[key] = arr;
arr.push(item.fieldName)
})
}
return tempObj
}
// 删除表字段
const deleteChart = record => {
removeFields({ fieldIDs: record.ID }).then(res => {
if (res.msg === 'Ok' || res.msg === '') {
notification.success({
message: '提示',
duration: 3,
description: '删除成功',
});
setFlag(flag + 1);
} else {
notification.error({
message: '提示',
duration: 3,
description: res.msg,
});
}
});
};
// 返回上一级
const back = () => {
history.push('/platformCenter/bsmanger/tablemanger')
}
return (
<div style={{ width: '100vm', height: 'calc(100vh - 100px) ', background: '#ffffff' }}>
<Spin tip="loading..." spinning={treeLoading}>
<div className={styles.config}><div className={styles.title}>{formObj}(字段配置)</div> <Button type="primary" onClick={back}>返回</Button></div>
<Table
columns={columns}
dataSource={tableData}
// pagination={{ pageSize: 10 }}
scroll={{ x: 'max-content', y: '45rem' }}
size="small"
rowKey={(record, index) => `complete${record.tableID}${index}`}
pagination={{
showTotal: (total, range) =>
`第${range[0]}-${range[1]} 条/共 ${total} 条`,
pageSizeOptions: [10, 20, 50, 100],
defaultPageSize: 20,
showQuickJumper: true,
showSizeChanger: true,
}}
/>
</Spin>
<FieldEditor
isVisible={isVisible}
isType={isType}
itemData={itemData}
formObj1={formObj}
onCancel={() => setIsVisible(false)}
callBackSubmit={Submit}
/>
</div>
);
};
export default AddModal;
.field{
width:100%;
display: flex;
justify-content: flex-start;
flex-wrap: wrap;
max-height: 20rem;
overflow-y: scroll;
.ant-card{
width: 80%;
margin-left: 4rem;
}
.ant-card-head-title{
flex: none;
}
.ant-card-extra{
margin-left: 0.2rem;
}
.ant-card-body{
// padding: 0 ;
height: 15rem;
overflow-y: scroll;
}
}
.paneTitle{
font-weight: bold;
font-size: 18px;
margin: 0 0 0.5rem 4rem;
}
.listEvent{
display: flex;
}
.cardList{
.ant-card-body{
overflow-y:none !important;
}
}
.unit{
display: flex;
margin-left: 1.1rem;
align-items: center;
}
.listCard{
display: flex;
.cardItem{
width: 50%;
padding: 0.5rem;
}
.cardContent{
height: 25rem;
overflow-y: scroll;
width: 19.5rem;
}
.cardItemData{
padding: 1rem;
border: 1px solid #b5b8c8;
margin-bottom: 1rem;
}
}
.sortable-ghost {
border-bottom: 2px dashed #1890ff;
}
.doctorTable {
margin-bottom: 16px;
table {
width: 100%;
td {
padding: 6px;
border: 1px solid #e8e8e8;
}
thead {
tr {
font-weight: 600;
background: #FAFAFA;
}
}
tbody{
tr:hover{
background-color:#ededed ;
}
}
}
}
.config{
display: flex;
justify-content: space-between;
padding: 1rem 0 0.5rem 0.5rem;
width: calc(100% - 10px);
.title{
font-size: 18px;
color: rgba(0, 114, 255, 1);
}
}
......@@ -44,6 +44,7 @@ import DimensionsConfig from '@/pages/platformCenter/dimensionsConfig/dimensions
import TaskScheduling from '@/pages/artificial/taskScheduling/taskScheduling';
import PoliciesIssued from '@/pages/artificial/policiesIssued/policiesIssued';
import TableManager from '@/pages/platformCenter/bsmanager/tablemanager'
import FiledConfig from '@/pages/platformCenter/filedConfig/filedConfig'
import AuthControl from '@/pages/authcontrol'
// import ColConen from '@/components/Colophon/colContent';
......@@ -261,6 +262,12 @@ export default {
name: '表/字段',
component: TableManager,
},
{
path: '/platformCenter/bsmanger/filedConfig/:id',
name: '字段配置',
component: FiledConfig,
hideMenu: true
},
// {
// path: '/platformCenter/bsmanger/standbookmanager',
// name: '台账配置',
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment