From f35972ec8c84555d365b36240d217b8bb555d642 Mon Sep 17 00:00:00 2001 From: zhangwenshuai Date: Wed, 26 Feb 2020 23:10:35 +0800 Subject: [PATCH] update --- package.json | 3 +- src/apollo-table/component/Row.less | 43 ++++ src/apollo-table/component/Row.tsx | 26 +++ src/apollo-table/component/Table.tsx | 67 +++--- src/apollo-table/component/base/config.tsx | 14 +- .../component/base/edit/editInterface.tsx | 12 +- .../base/extra/dataEntry/textSelect/index.tsx | 190 +++++++++------- .../extra/dataEntry/textSelect/styles.less | 10 +- .../component/base/extra/upload/config.tsx | 32 --- .../component/base/extra/upload/detail.less | 202 ----------------- .../component/base/extra/upload/detail.tsx | 176 --------------- .../component/base/extra/upload/index.tsx | 204 ------------------ .../component/base/extra/upload/preview.tsx | 48 ----- .../component/base/extra/upload/styles.less | 86 -------- .../base/extra/upload/utils/utils.tsx | 27 --- src/apollo-table/component/index.less | 5 +- src/apollo-table/component/interface.tsx | 3 +- src/index.html | 2 + webpack.config.js | 2 +- 19 files changed, 252 insertions(+), 900 deletions(-) create mode 100644 src/apollo-table/component/Row.less create mode 100644 src/apollo-table/component/Row.tsx delete mode 100644 src/apollo-table/component/base/extra/upload/config.tsx delete mode 100644 src/apollo-table/component/base/extra/upload/detail.less delete mode 100644 src/apollo-table/component/base/extra/upload/detail.tsx delete mode 100644 src/apollo-table/component/base/extra/upload/index.tsx delete mode 100644 src/apollo-table/component/base/extra/upload/preview.tsx delete mode 100644 src/apollo-table/component/base/extra/upload/styles.less delete mode 100644 src/apollo-table/component/base/extra/upload/utils/utils.tsx diff --git a/package.json b/package.json index 0e79b8e..b3dc3e0 100644 --- a/package.json +++ b/package.json @@ -14,7 +14,7 @@ "build": "umi-lib build", "lint:ts": "tslint \"src/**/*.ts\" \"src/**/*.tsx\"", "precommit": "lint-staged:ts", - "start": "webpack" + "start": "cross-env BUILD_ENV=development PROXY_ENV=development ENV=development webpack-dev-server" }, "peerDependencies": { "react": "16.x" @@ -52,6 +52,7 @@ "license": "MIT", "dependencies": { "antd": "^3.25.2", + "dom-helpers": "^5.1.3", "father": "^2.29.1", "file-saver": "^2.0.2", "react-dom": "^16.12.0", diff --git a/src/apollo-table/component/Row.less b/src/apollo-table/component/Row.less new file mode 100644 index 0000000..99b7b1e --- /dev/null +++ b/src/apollo-table/component/Row.less @@ -0,0 +1,43 @@ +@import '../../common'; + +.colContainer { + display: flex; + align-items: center; + justify-content: space-between; + height: 100%; + width: 100%; + + .colBrief { + display: flex; + align-items: center; + flex: 1; + width: 100%; + + .colIcon { + width: @textFontGen; + color: @textPrimaryColor; + } + + .colTitle { + flex: 1; + overflow: hidden; + text-overflow: ellipsis; + white-space: nowrap; + text-align: left; + margin-left: 5px; + color: @textPrimaryColor; + } + } + + + .colOpera { + width: 20px; + text-align: center; + cursor: pointer; + + .colOperaIcon { + width: 7px; + height: 5px; + } + } +} diff --git a/src/apollo-table/component/Row.tsx b/src/apollo-table/component/Row.tsx new file mode 100644 index 0000000..3633c64 --- /dev/null +++ b/src/apollo-table/component/Row.tsx @@ -0,0 +1,26 @@ +import React, { PureComponent } from 'react'; +import { config } from './config'; +import s from './Row.less'; +import { ColumnProps } from './interface'; +import IconFont from './base/extra/iconFont'; + +export default class TableRow extends PureComponent { + render() { + let { type, title, width = 200, columnAttrObj = {} } = this.props; + if (!config[String(type)]) { + type = '1'; + } + let icon = config[String(type)] && config[String(type)].icon; + if (String(type) === '13' && !columnAttrObj.isMultiple) { + icon = 'iconziduan-lianxiangdanxuan'; + } + return ( +
+
+ {icon && (typeof icon === 'string' ? : icon)} + {title} +
+
+ ); + } +} diff --git a/src/apollo-table/component/Table.tsx b/src/apollo-table/component/Table.tsx index 95b6b05..dbe5b77 100644 --- a/src/apollo-table/component/Table.tsx +++ b/src/apollo-table/component/Table.tsx @@ -10,7 +10,7 @@ import Column from './Column'; import Cell from './Cell'; import extendIcon from '../assets/extend.png'; import IconFont from './base/extra/iconFont'; -import scrollbarSize from '../utils/scrollbarSize'; +import scrollbarSize from 'dom-helpers/scrollbarSize'; export default class AirTable extends Component { private indexCount: any; @@ -32,7 +32,8 @@ export default class AirTable extends Component { if (JSON.stringify(prevProps.checked) !== JSON.stringify(nextProps.checked)) { nextState.checked = nextProps.checked; } - nextState.height = document.body.clientHeight - 193; + nextState.tableHeight = document.body.clientHeight; + nextState.tableWidth = document.body.clientWidth; return nextState; } constructor(props: TableProps) { @@ -44,7 +45,8 @@ export default class AirTable extends Component { checked, tableId, prevProps: props, - height: document.body.clientHeight - 193, + tableWidth: 0, + tableHeight: 0, }; this.config = { overscanColumnCount: 5, @@ -62,7 +64,8 @@ export default class AirTable extends Component { //重置窗口高度 resize = () => { this.setState({ - height: document.body.clientHeight - 193, + tableHeight: document.body.clientHeight, + tableWidth: document.body.clientWidth, }); }; //获取左侧固定列数量 @@ -411,20 +414,27 @@ export default class AirTable extends Component { }; render() { - const { columns, dataSource, checked } = this.state; + const { columns, dataSource, checked, tableHeight, tableWidth } = this.state; const { changeChecked, operateConfig = {}, hasGroup } = this.props; const { groupConfig } = operateConfig; const { overscanColumnCount, overscanRowCount, columnWidth, rowHeight } = this.config; - let { height } = this.state; - if (dataSource.length * rowHeight < height) { - height = dataSource.length * rowHeight; + let totalHeight = tableHeight; + let colWidth = columnWidth; + const columnCount = columns.length; + const rowCount = dataSource.length; + if (rowCount > 0 && rowCount * rowHeight < tableHeight) { + // 表格行数少于一屏高度时,高度增加横向滚动条高度 + totalHeight = rowCount * rowHeight + scrollbarSize(); + } + if (columnCount > 0 && columnCount * columnWidth < tableWidth) { + // 表格宽度不足一屏时,按屏幕宽度平分每列宽度 + colWidth = Math.floor(tableWidth / columnCount); } //有隐藏列时,修正数据与列头不匹配问题 const data = this.memoizeData(columns, dataSource); //左侧固定列数量 const leftCount = this.memoizeLeftCount(columns); - const rowCount = dataSource.length; - const columnCount = columns.length; + return ( <> @@ -434,8 +444,8 @@ export default class AirTable extends Component {
{ @@ -453,9 +463,9 @@ export default class AirTable extends Component { { className={styles.LeftSideGrid} overscanRowCount={overscanRowCount} cellRenderer={this.renderBodyCell.bind(this, data)} - columnWidth={columnWidth} + columnWidth={colWidth} columnCount={leftCount} - width={columnWidth * leftCount} + width={colWidth * leftCount} rowHeight={rowHeight} rowCount={rowCount} - height={height - scrollbarSize()} + height={totalHeight - scrollbarSize()} scrollTop={scrollTop} checked={checked} dataSource={dataSource} @@ -501,8 +511,11 @@ export default class AirTable extends Component { {({ width }: any) => { // 如果列太少不满一屏时,列头宽度按列计算 - const headerWidth: number = - columnWidth * columnCount < width ? columnWidth * columnCount : width; + let headerWidth = width; + if (rowCount * rowHeight > tableHeight) { + // 表格行数大于一屏的高度时出现竖向滚动条,此时宽度减出滚动条宽度 + headerWidth -= scrollbarSize(); + } return (
{ @@ -511,19 +524,16 @@ export default class AirTable extends Component { style={{ backgroundColor: `rgba(246, 246, 246, 1)`, height: rowHeight, - width: - columnWidth * columnCount < width - ? columnWidth * columnCount - : headerWidth - scrollbarSize(), + width: headerWidth, }} > { //右侧内容
@@ -546,13 +556,14 @@ export default class AirTable extends Component { overscanColumnCount={overscanColumnCount} overscanRowCount={overscanRowCount} dataSource={dataSource} - columnWidth={columnWidth} + columnWidth={colWidth} columnCount={columnCount} width={width} rowHeight={rowHeight} rowCount={rowCount} - height={height} + height={totalHeight} onScroll={(...arg: Array) => { + console.log('arg', arg); onScroll(...arg); this.onScrollRow(arg[0]); }} diff --git a/src/apollo-table/component/base/config.tsx b/src/apollo-table/component/base/config.tsx index 9bc97b7..46d58fe 100644 --- a/src/apollo-table/component/base/config.tsx +++ b/src/apollo-table/component/base/config.tsx @@ -29,13 +29,13 @@ export const config: any = { }, detail: require('./detail/textarea').default, }, - '4': { - name: '附件上传', - component: require('./edit/upload').default, - getFormatter: GetFormatter['UPLOAD'], - setFormatter: SetFormatter['UPLOAD'], - detail: require('./detail/upload').default, - }, + // '4': { + // name: '附件上传', + // component: require('./edit/upload').default, + // getFormatter: GetFormatter['UPLOAD'], + // setFormatter: SetFormatter['UPLOAD'], + // detail: require('./detail/upload').default, + // }, '5': { name: '复选', component: require('./edit/checkbox').default, // 暂未添加 diff --git a/src/apollo-table/component/base/edit/editInterface.tsx b/src/apollo-table/component/base/edit/editInterface.tsx index 9036638..fe63905 100644 --- a/src/apollo-table/component/base/edit/editInterface.tsx +++ b/src/apollo-table/component/base/edit/editInterface.tsx @@ -1,3 +1,5 @@ +import { DatePickerProps } from 'antd/es/date-picker/interface'; + export interface CommonProps { value: any[] | undefined; placeholder?: string; @@ -32,8 +34,7 @@ export interface SelectProps extends CommonProps { maxCount?: number; tableId?: number; options?: any[]; - allowClear?:boolean; - + allowClear?: boolean; } export interface RateProps { value: number; @@ -60,9 +61,4 @@ export interface NumberState { value: number | undefined; cellData?: any[]; } -export interface DateProps extends CommonProps { - allowClear?: boolean; - disabled?: boolean; - format?: string | string[]; - showTime?: Object | boolean; -} +export interface DateProps extends DatePickerProps {} diff --git a/src/apollo-table/component/base/extra/dataEntry/textSelect/index.tsx b/src/apollo-table/component/base/extra/dataEntry/textSelect/index.tsx index 672fba3..658bf0e 100644 --- a/src/apollo-table/component/base/extra/dataEntry/textSelect/index.tsx +++ b/src/apollo-table/component/base/extra/dataEntry/textSelect/index.tsx @@ -1,5 +1,5 @@ import React from 'react'; -import { Dropdown, Menu, Empty, Spin, Icon, Input } from 'antd'; +import { Menu, Empty, Spin, Icon, Input, Dropdown } from 'antd'; import { findDOMNode } from 'react-dom'; import lodash from 'lodash'; import styles from './styles.less'; @@ -7,9 +7,37 @@ import styles from './styles.less'; /* * 此空间用于数据选择及输入控制,若不选择只传入输入框数据 */ - -class TextSelect extends React.Component { +interface Props { + initDataType?: undefined | 'onfocus'; // 初始化请求方式 + request?: Function; + selfCom?: any; + dataSource?: []; + onChange: Function; + value?: any; + autoFocus?: boolean; + mode?: 'multiple' | 'tags' | undefined; + fieldNames?: { + value: any; + label: string; + }; + placeholder?:string; + width?:number; + disabled?:boolean; +} +interface State { + searchStr: string, + list: any[], + loading: boolean, + selected: any[], + tempSelected: any[], + tempVisible: boolean, +} +class TextSelect extends React.Component { + container: any; input: any; + width: number; + inputWidth = 320; + constructor(props) { super(props); this.state = { @@ -20,15 +48,15 @@ class TextSelect extends React.Component { tempSelected: undefined, tempVisible: false, }; - this._fetch = lodash.debounce(this._fetch, 400); + this.container = React.createRef(); + this.input = React.createRef(); + this.fetch = lodash.debounce(this.fetch, 400); } - inputWidth: number = 320; - static getDerivedStateFromProps(nextProps, prevState) { if (JSON.stringify(nextProps.value) !== JSON.stringify(prevState.tempSelected)) { - let searchStr = - nextProps.value && nextProps.value[0] ? nextProps.value[0].label || nextProps.value[0].text : ''; + const [first] = nextProps.value || []; + const searchStr = first ? first.label || first.text : ''; return { tempSelected: nextProps.value || [], selected: nextProps.value, @@ -43,81 +71,109 @@ class TextSelect extends React.Component { } getInputWidth = () => { - if (this.input && findDOMNode(this.input)) { - this.width = findDOMNode(this.input).offsetWidth; + if (this.input.current) { + const dom = findDOMNode(this.input.current); + if (dom) { + // @ts-ignore + this.width = dom.offsetWidth; + } } }; - _fetch = async (val) => { - const request = this.props.request; + + fetch = async (val) => { + const { request } = this.props; if (!request) return; await this.setState({ loading: true, list: [] }); const result = await request(val); if (result && result.success) { const data = result.data || {}; let list = Array.isArray(data.list) ? data.list : []; - list = this.formateData(list); + list = this.formatData(list); this.setState({ list }); } await this.setState({ loading: false }); }; - formateData = (data) => { + + formatData = (data) => { const { fieldNames = { label: 'name', value: 'id' } } = this.props || {}; - return data.map((item) => ({ - ...item, - _label: item[fieldNames.label], - _value: item[fieldNames.value], - })); + const { label, value } = fieldNames; + return data.map((item) => { + return { + ...item, + _label: item[label], + _value: item[value], + }; + }); }; + onResetValue = (searchStr) => { - return { value: '', label: searchStr }; + return [{ value: '', label: searchStr }]; }; + onSearch = (e) => { const searchStr = e.currentTarget.value; const selected = this.onResetValue(searchStr); this.setState({ searchStr, selected }, () => { - this._fetch(searchStr); + this.fetch(searchStr); this.onChange(selected); }); }; + onFocus = () => { - this._fetch(this.state.searchStr); + const { searchStr } = this.state; + this.fetch(searchStr); }; + onClickMenu = ({ item, key }) => { const { props } = item || {}; const { title } = props || {}; - const selected = { label: title, value: key }; + const selected = [{ label: title, value: key }]; this.setState({ selected, searchStr: title }); this.onVisibleChange(false); this.onChange(selected); }; + onChange = (obj) => { - this.props.onChange && this.props.onChange(obj); + const { onChange } = this.props; + if (typeof onChange === 'function') { + onChange(obj); + } }; + onClear = () => { const { tempVisible } = this.state; const searchStr = ''; const selected = this.onResetValue(searchStr); this.setState({ searchStr, selected }, () => { - tempVisible && this._fetch(searchStr); + if (tempVisible) { + this.fetch(searchStr); + } this.onChange(selected); }); }; + onVisibleChange = (tempVisible) => { this.setState({ tempVisible }); }; + renderList = () => { const { list, loading, selected } = this.state; + const { width } = this.props; return ( - {list.map((item) => ( - - {item._label} - - ))} + {list.map((item) => { + return ( + // eslint-disable-next-line no-underscore-dangle + + {/* eslint-disable-next-line no-underscore-dangle */} + {item._label} + + ); + })} {loading ? ( @@ -133,54 +189,36 @@ class TextSelect extends React.Component { ); }; - renderSuffix = () => { - if (this.props.suffix) return this.props.suffix; - const { searchStr } = this.state; - const { allowClear = true } = this.props; - return ( - <> - - {' '} - - - {searchStr.length > 0 && allowClear ? ( - - {' '} - - - ) : null} - - ); + + getContainer = () => { + return this.container.current; }; render() { - const { placeholder } = this.props; + const { placeholder, disabled } = this.props; + const { searchStr } = this.state; return ( - - (this.input = dom)} - className={styles.input} - value={this.state.searchStr} - placeholder={placeholder} - onChange={this.onSearch} - onFocus={this.onFocus} - suffix={this.renderSuffix()} - /> - + + + + + ); } } diff --git a/src/apollo-table/component/base/extra/dataEntry/textSelect/styles.less b/src/apollo-table/component/base/extra/dataEntry/textSelect/styles.less index 0e53a1b..007c3a1 100644 --- a/src/apollo-table/component/base/extra/dataEntry/textSelect/styles.less +++ b/src/apollo-table/component/base/extra/dataEntry/textSelect/styles.less @@ -1,3 +1,11 @@ +.container { + position: relative; +} +.overlayClassName { + max-height: 300px; + overflow: auto; + margin-top: 20px; +} .searchIcon{ position: absolute; top: 50%; @@ -23,4 +31,4 @@ display: flex; justify-content: center; align-items: center; -} \ No newline at end of file +} diff --git a/src/apollo-table/component/base/extra/upload/config.tsx b/src/apollo-table/component/base/extra/upload/config.tsx deleted file mode 100644 index 5d1c5df..0000000 --- a/src/apollo-table/component/base/extra/upload/config.tsx +++ /dev/null @@ -1,32 +0,0 @@ -export const CDN_PATH = 'https://static.mttop.cn/admin'; -export const CDN_HOST = 'https://static.mttop.cn'; -export const fileConfig = { - image: {}, - ppt: { - thumbUrl: `${CDN_PATH}/pptIcon.png`, - }, - pptx: { - thumbUrl: `${CDN_PATH}/pptIcon.png`, - }, - zip: { - thumbUrl: `${CDN_PATH}/zipIcon.png`, - }, - xlsx: { - thumbUrl: `${CDN_PATH}/xlsIcon.png`, - }, - xls: { - thumbUrl: `${CDN_PATH}/xlsIcon.png`, - }, - doc: { - thumbUrl: `${CDN_PATH}/docIcon.png`, - }, - docx: { - thumbUrl: `${CDN_PATH}/docIcon.png`, - }, - pdf: { - thumbUrl: `${CDN_PATH}/pdfIcon.png`, - }, - other: { - thumbUrl: `${CDN_PATH}/otherIcon.png`, - }, -}; diff --git a/src/apollo-table/component/base/extra/upload/detail.less b/src/apollo-table/component/base/extra/upload/detail.less deleted file mode 100644 index c9d8e17..0000000 --- a/src/apollo-table/component/base/extra/upload/detail.less +++ /dev/null @@ -1,202 +0,0 @@ -@import "../../../../../common"; - -.fileList { - display: flex; - flex-flow: row; - flex-wrap: wrap; -} - -.fileListCenter { - justify-content: center; -} - -.wrap { - position: relative; - cursor: pointer; -} - -.wrap:hover .fileBoxHove { - display: flex; -} - -.fileBox { - padding: 10px; - width: 100px; - display: flex; - flex-flow: column; - justify-items: center; - align-items: center; - border-radius: 4px; - overflow: hidden; -} - -.fileBoxHove { - position: absolute; - top: 0; - left: 0; - display: none; - justify-content: center; - align-items: center; - width: 100%; - height: 100%; - background: rgba(0, 0, 0, 0.5); - border-radius: 4px; - - .icon { - color: #fff; - padding: 5px; - } -} - -.fileName { - margin-top: 5px; - width: 80px; - font-size: 12px; - font-weight: 400; - color: rgba(90, 104, 118, 1); - overflow: hidden; - text-overflow: ellipsis; - white-space: nowrap; - text-align: center; -} - -.fileStyle { - height: 56px; -} - -.dialog { - width: 900px !important; - min-height: 500px; -} - -.textUploadList { - box-sizing: border-box; - margin: 0; - padding: 0; - color: rgba(0, 0, 0, 0.65); - font-size: 14px; - font-variant: tabular-nums; - line-height: 1.5; - list-style: none; - -webkit-font-feature-settings: 'tnum'; - font-feature-settings: 'tnum'; - zoom: 1; - - .textUploadListItem { - position: relative; - height: 22px; - margin-top: 8px; - font-size: 14px; - - .textUploadListItemInfo { - height: 100%; - padding: 0 12px 0 4px; - - .textUploadListItemBox { - display: flex; - align-items: center; - - .textUploadListItemInfoName { - display: inline-block; - margin-right: 10px; - overflow: hidden; - white-space: nowrap; - text-overflow: ellipsis; - color: #5a6876; - - &:hover { - color: #5c99ff; - } - } - } - } - } -} - -.downIcon { - display: inline-block; - position: absolute; - right: 0; - top: 50%; - transform: translate(0, -50%); - cursor: pointer; -} - -.pictureTextUploadList { - box-sizing: border-box; - margin: 0; - padding: 0; - color: rgba(0, 0, 0, 0.65); - font-size: 14px; - font-variant: tabular-nums; - line-height: 1.5; - list-style: none; - -webkit-font-feature-settings: 'tnum'; - font-feature-settings: 'tnum'; - zoom: 1; - overflow: hidden; - width: 100%; - - .textUploadListItem { - position: relative; - display: flex; - justify-items: center; - height: 41px; - margin-top: 16px; - font-size: 14px; - width: 100%; - - .textUploadListItemInfo { - width: 100%; - height: 100%; - padding: 0 12px 0 4px; - - .textUploadListItemBox { - display: flex; - align-items: center; - height: 100%; - - .fileImgStyle { - width: 32px; - margin-right: 10px; - cursor: pointer; - } - - .textUploadListItemInfoName { - display: inline-block; - margin-right: 10px; - overflow: hidden; - white-space: nowrap; - text-overflow: ellipsis; - color: @textGeneralColor; - - &:hover { - color: @primaryColor; - } - } - &:hover{ - .downIcon{ - opacity: 1; - } - } - - .downIcon { - display: inline-block; - position: absolute; - right: 0; - top: 50%; - transform: translate(0, -50%); - cursor: pointer; - color: @textSupplyColor; - opacity: 0; - transition: opacity 0.2s linear; - } - } - } - } -} - - -// .textUploadListItemInfo:hover { -// background: #e6f7ff; -// } diff --git a/src/apollo-table/component/base/extra/upload/detail.tsx b/src/apollo-table/component/base/extra/upload/detail.tsx deleted file mode 100644 index a2b8768..0000000 --- a/src/apollo-table/component/base/extra/upload/detail.tsx +++ /dev/null @@ -1,176 +0,0 @@ -import React from 'react'; -import { Icon, message, Tooltip } from 'antd'; -import { saveAs } from 'file-saver'; -import styles from './detail.less'; -import { checkoutFileType, handleName } from './utils/utils'; -import Preview from './preview'; -import { renderTxt } from '@/utils/hoverPopover'; -import { CDN_HOST } from './config'; - -/* - * listType = 'text' 以文本展示 - * listType = 'picture' 以圖文展示 - */ - -/* eslint-disable */ -export default class uploadDetail extends React.Component { - model: any; - onPreview = (item: any) => { - if (this.model && this.model.onPreview) { - const url = `${item.domain ? 'https://' + item.domain : CDN_HOST}/${item.value}`; - this.model.onPreview(url); - } - }; - onDownLoad = (item: any) => { - // debugger - if (!item.value) { - message('下载异常'); - return; - } - const url = `${item.domain ? 'https://' + item.domain : CDN_HOST}/${item.value}`; - // const typeArr = url.match(/\.[a-zA-Z]+$/); - // const type = typeArr && typeArr[0] ? typeArr[0].replace('.', '') : ''; - saveAs(url, item.name); - // let a = document.createElement('a'); - // a.href = url; - // a.target = '_blank'; - // a.download = item.name; - // a.click(); - // a = null; - }; - handleCancel = () => { - this.setState({ showDialog: false }); - }; - checkoutDetailType = () => { - const listType = this.props.listType; - switch (listType) { - case 'picture': // 单纯图片 - return this.renderUpload(); - case 'text': // 淡村文本 - return this.rendertextUpload(); - case 'picture-text': // 图文混排 - return this.renderPictureText(); - default: - return this.renderUpload(); - } - }; - renderPictureText = (item = this.props.data || []) => { - if (!Array.isArray(item)) return item; - return ( -
    - {item.map((ls, num) => ( -
  • -
    - - (this.img = img)} - className={styles.fileImgStyle} - onClick={this.onPreview.bind(this, ls)} - src={ - checkoutFileType(`${ls.domain ? 'https://' + ls.domain : CDN_HOST}/${ls.value}`) - .thumbUrl - } - /> - - - {ls.name} - - - - - -
    -
  • - ))} -
- ); - }; - rendertextUpload = (item = this.props.data || []) => { - if (!Array.isArray(item)) return item; - return ( -
    - {item.map((ls, index) => ( -
  • -
    - - - - - - {ls.name} - - - -
    -
  • - ))} -
- ); - }; - renderUpload = (item = this.props.data || []) => { - if (!Array.isArray(item)) return item; - return item.map((ls, index) => { - return ( -
-
- (this.img = img)} - className={styles.fileStyle} - src={ - checkoutFileType(`${ls.domain ? 'https://' + ls.domain : CDN_HOST}/${ls.value}`) - .thumbUrl - } - /> - {ls.name} -
- -
- - - - - - -
-
- ); - }); - }; - - render() { - const { stylePosition } = this.props; - return ( - <> - (this.model = dom)} /> -
- {this.checkoutDetailType()} -
- - ); - } -} diff --git a/src/apollo-table/component/base/extra/upload/index.tsx b/src/apollo-table/component/base/extra/upload/index.tsx deleted file mode 100644 index c865fb2..0000000 --- a/src/apollo-table/component/base/extra/upload/index.tsx +++ /dev/null @@ -1,204 +0,0 @@ -import React from 'react'; -import { Button, Icon, message, Upload } from 'antd'; -import moment from 'moment'; -import Detail from './detail'; -import { checkoutFileType } from './utils/utils'; -import { getToken } from '../../../../services/globalSearchApi'; -import Preview from './preview'; -import { getRandom } from '../../../../utils/utils'; -import './styles.less'; -import { CDN_HOST } from './config'; - -message.config({ - maxCount: 1, -}); -const formatFileList = ({ list = [], fileList, domain, setFormat }: any) => { - return list.map((item, key) => { - //增加自定义回显数据格式 - let value = setFormat ? setFormat(item) : item; - //处理上传成功但没保存到后台的数据(onSaveFileList把数据同步到父组件导致子组件重新渲染处理数据不一致) - let file = fileList - .filter((f) => f.status === 'done') - .find((f) => { - const url = `${domain ? 'https://' + domain : CDN_HOST}/${f.response.key}`; - return url === value.value; - }); - if (file) { - return file; - } - //处理保存到后台的数据 - return { - ...value, - uid: value.value, - url: value.value, - ...checkoutFileType(value.value), - }; - }); -}; - -const UploadCom: any = class UploadCom extends React.Component { - model: any; - - static getDerivedStateFromProps(nextProps, prevState) { - const { prevProps } = prevState; - let nextState = { - ...prevState, - prevProps: nextProps, - }; - if (JSON.stringify(prevProps.value) !== JSON.stringify(nextProps.value)) { - nextState.fileList = formatFileList({ - list: nextProps.value, - fileList: prevState.fileList, - domain: prevState.domain, - setFormat: nextProps.setFormat, - }); - } - return nextState; - } - constructor(props) { - super(props); - const { value, setFormat } = props; - const fileList = formatFileList({ list: value, fileList: [], domain: null, setFormat: setFormat }); - this.state = { - prevProps: props, - fileList, - token: null, - domain: null, - }; - } - - //获取七牛上传token - getToken = async () => { - let response = await getToken(); - if (response && response.success && response.data) { - this.setState({ - token: response.data.token, - domain: response.data.domain, - }); - } - }; - //自定义七牛文件唯一key - getKey = (file: any) => { - if (!file) return; - let suffix = file.name.match(/\.\w+$/)[0]; - let rand6: string = getRandom(); - let time = moment().format('YYYYMMDDHHmmss'); - return time + rand6 + suffix; - }; - //七牛上传额外数据,token和key - getData = (file: any) => { - const { token } = this.state; - return { - token, - key: this.getKey(file), - }; - }; - - static checkoutFileType = checkoutFileType; - - onSaveFileList = (fileList = []) => { - if (this.props.onChange) { - const newList = fileList - .filter((item: any) => item.value) - .map((item: any) => ({ - name: item.name, - value: item.value, - size: item.size, - })); - this.props.onChange(newList); - } - }; - beforeUpload = async () => { - await this.getToken(); - return true; - }; - onChange = ({ file, fileList, event }: any) => { - const { domain } = this.state; - let newList = fileList; - // const filterFilter = fileList.filter((item) => item.status && item.status !== 'done'); - // if (filterFilter.length > 5) { - // message.warn('文件不能超过5个'); - // return; - // } - if (file.status === 'done' && file.response) { - const data = file.response || {}; - const url = `${domain ? 'https://' + domain : CDN_HOST}/${data.key}`; - //上传成功后处理为服务端数据结构 - const itemObj = { - uid: file.uid, - name: file.name, - value: url, - size: file.size, - url, - domain, - }; - newList = fileList.map((item: any) => { - return item.uid === file.uid ? { ...item, ...itemObj } : item; - }); - this.onSaveFileList(newList); - } - //ant upload组件实时更新上传状态必须实时setState最新文件列表 - this.setState({ fileList: newList }); - }; - previewFile = (file: any) => { - return new Promise((res, rej) => { - const obj = checkoutFileType(file.name); - const typeArr = file.name.match(/\.[a-zA-Z]+$/); - const type = typeArr && typeArr[0] ? typeArr[0].replace('.', '') : ''; - if (!['png', 'gif', 'bmp', 'jpg', 'jpeg'].includes(type)) { - res(obj.thumbUrl); - } - }); - }; - onPreview = (file: any) => { - if (this.model && this.model.onPreview) { - this.model.onPreview(file.url, file.value); - } - }; - onRemove = (file: any) => { - const fileList = this.state.fileList || []; - const newFileList = fileList.filter((item) => item.uid !== file.uid); - this.onSaveFileList(newFileList); - this.setState({ fileList: newFileList }); - }; - - render() { - const { btnText, renderButton, listType } = this.props; - const { fileList } = this.state; - const classObj = { - picture: 'upload-list-picture', - text: 'upload-list-text', - }; - return ( -
- - {renderButton ? ( - renderButton - ) : ( - - )} - - (this.model = dom)} /> -
- ); - } -}; - -UploadCom.Preview = Preview; -UploadCom.Detail = Detail; -export default UploadCom; diff --git a/src/apollo-table/component/base/extra/upload/preview.tsx b/src/apollo-table/component/base/extra/upload/preview.tsx deleted file mode 100644 index 41dcb38..0000000 --- a/src/apollo-table/component/base/extra/upload/preview.tsx +++ /dev/null @@ -1,48 +0,0 @@ -import React from 'react'; -import styles from './detail.less'; -import { checkoutFileType, previewFile } from './utils/utils'; -import { message, Modal } from 'antd'; - -/* eslint-disable */ -export default class uploadDetail extends React.Component { - state = { - showDialog: false, - type: 'image', - url: '', - }; - onPreview = (url: string, name: string) => { - const typeArr = (name || url).match(/\.[a-zA-Z]+$/); - let type = typeArr && typeArr[0] ? typeArr[0].replace('.', '') : ''; - type = type.toLowerCase(); - if (['png', 'gif', 'bmp', 'jpg', 'jpeg'].includes(type)) { - this.setState({ showDialog: true, type: 'image', url }); - } else if (['doc', 'docx', 'document', 'xls', 'xlsx', 'ppt', 'pptx'].includes(type)) { - this.setState({ showDialog: true, type: 'office', url }); - } else if (type === 'pdf') { - this.setState({ showDialog: true, type: 'pdf', url }); - } else { - message.warn('暂不支持预览'); - } - }; - handleCancel = () => { - this.setState({ showDialog: false }); - }; - render() { - const { showDialog, type, url } = this.state; - return ( -
- - {type === 'image' ? example : null} - {type === 'office' ? ( -