Commit ad93985a authored by 何虹's avatar 何虹 💬

hs-input-select优化

parent 20d0918c
...@@ -130,7 +130,7 @@ export default { ...@@ -130,7 +130,7 @@ export default {
await this.remoteMethodsDebounce(query, this.configData) await this.remoteMethodsDebounce(query, this.configData)
}, },
dealWithDefaultData() { dealWithDefaultData() {
const { sourceData } = _.cloneDeep(this.allSourceData) const sourceData = _.cloneDeep(this.data || [])
const sourceData_ = _.cloneDeep(sourceData) const sourceData_ = _.cloneDeep(sourceData)
return Array.isArray(sourceData_) return Array.isArray(sourceData_)
? this.tansLate(sourceData_) ? this.tansLate(sourceData_)
......
...@@ -62,7 +62,7 @@ ...@@ -62,7 +62,7 @@
</hs-table> </hs-table>
<div <div
v-if='this.lookupConfig.multiple' v-if='this.configData.multiple'
slot="footer" slot="footer"
class="dialog-footer" class="dialog-footer"
> >
...@@ -88,7 +88,7 @@ export default { ...@@ -88,7 +88,7 @@ export default {
name: 'lookup-component', name: 'lookup-component',
computed: { computed: {
getDisabled: function() { getDisabled: function() {
const { disabled, disabledLevel } = this.lookupConfig const { disabled, disabledLevel } = this.configData
const type = typeof disabled const type = typeof disabled
if (disabledLevel === 1) { if (disabledLevel === 1) {
// 以自己的的配置为优先级最高 // 以自己的的配置为优先级最高
...@@ -105,13 +105,10 @@ export default { ...@@ -105,13 +105,10 @@ export default {
} }
} }
}, },
lookupConfig: function() {
return this.allSourceData.config || {}
},
hsTableData() { hsTableData() {
console.log('测试hsTableData') console.log('测试hsTableData')
const data = this.tableData const data = this.tableData
const { value } = this.lookupConfig const { value } = this.configData
const list = this.value ? this.value.split(',') : [] const list = this.value ? this.value.split(',') : []
list.forEach(x => { // 设置默认勾选 list.forEach(x => { // 设置默认勾选
const target = data.find(item => item[value] === x) const target = data.find(item => item[value] === x)
...@@ -150,7 +147,7 @@ export default { ...@@ -150,7 +147,7 @@ export default {
this.hsTableEl.position, this.hsTableEl.position,
'hsTableSimple' 'hsTableSimple'
) )
const { multiple } = this.lookupConfig const { multiple } = this.configData
config.selection = !!multiple config.selection = !!multiple
return config return config
}, },
...@@ -161,7 +158,7 @@ export default { ...@@ -161,7 +158,7 @@ export default {
} }
}, },
configData: function() { configData: function() {
return this.allSourceData.config || {} return this.config || {}
} }
}, },
watch: { watch: {
...@@ -225,7 +222,7 @@ export default { ...@@ -225,7 +222,7 @@ export default {
}, },
async showDialog() { async showDialog() {
// 弹出之前做逻辑判断 // 弹出之前做逻辑判断
const { value, multiple } = this.lookupConfig const { value, multiple } = this.configData
if (this.value && multiple) { if (this.value && multiple) {
// 多选 // 多选
const ids = this.value.split(',') const ids = this.value.split(',')
...@@ -260,7 +257,7 @@ export default { ...@@ -260,7 +257,7 @@ export default {
init_value() { init_value() {
if (!this.hsTableConfig) return if (!this.hsTableConfig) return
const sourceData = this.hsTableData const sourceData = this.hsTableData
const { multiple, value, displayfield } = this.lookupConfig const { multiple, value, displayfield } = this.configData
const displayfield_value = this.formData[displayfield] const displayfield_value = this.formData[displayfield]
if (displayfield_value) { if (displayfield_value) {
const list = displayfield_value.split(',') const list = displayfield_value.split(',')
...@@ -296,13 +293,12 @@ export default { ...@@ -296,13 +293,12 @@ export default {
} }
}, },
async queryByIds() { async queryByIds() {
this.allSourceData.sourceData = [] const { value } = this.configData
const { value } = this.lookupConfig
// 调用外面的查询方法 // 调用外面的查询方法
const obj = {} const obj = {}
obj[value] = this.value obj[value] = this.value
const data = await this.$listeners.queryLookup( const data = await this.$listeners.queryLookup(
this.allSourceData.config, this.configData,
obj, obj,
this.formData this.formData
) )
...@@ -317,10 +313,9 @@ export default { ...@@ -317,10 +313,9 @@ export default {
* 查询table数据 * 查询table数据
*/ */
async queryTable() { async queryTable() {
this.allSourceData.sourceData = []
this.setDefaultQueryParms() this.setDefaultQueryParms()
// 如果有分页信息则要分页 // 如果有分页信息则要分页
const { per_page } = this.lookupConfig const { per_page } = this.configData
if (per_page && this.firstQuery) { if (per_page && this.firstQuery) {
this.firstQuery = false this.firstQuery = false
this.searchForm.per_page = per_page this.searchForm.per_page = per_page
...@@ -328,7 +323,7 @@ export default { ...@@ -328,7 +323,7 @@ export default {
} }
// 调用外面的查询方法 // 调用外面的查询方法
const data = await this.$listeners.queryLookup( const data = await this.$listeners.queryLookup(
this.allSourceData.config, this.configData,
this.searchForm, this.searchForm,
this.formData this.formData
) )
...@@ -337,7 +332,7 @@ export default { ...@@ -337,7 +332,7 @@ export default {
this.paging = paging this.paging = paging
} }
// 做一个合并数据 // 做一个合并数据
const { multiple } = this.lookupConfig const { multiple } = this.configData
let returnData = [] let returnData = []
if (Array.isArray(data)) { if (Array.isArray(data)) {
returnData = data returnData = data
...@@ -354,7 +349,7 @@ export default { ...@@ -354,7 +349,7 @@ export default {
} }
}, },
unShiftData(queryData) { unShiftData(queryData) {
const { value } = this.lookupConfig const { value } = this.configData
const selectIds = this.selectedData.map(item => item[value]) const selectIds = this.selectedData.map(item => item[value])
const data_ = _.remove(queryData, function(item) { const data_ = _.remove(queryData, function(item) {
const item_value = item[value] const item_value = item[value]
...@@ -379,7 +374,7 @@ export default { ...@@ -379,7 +374,7 @@ export default {
*/ */
submit() { submit() {
const selectData = this.hsTableData.filter(x => x.isSelected) const selectData = this.hsTableData.filter(x => x.isSelected)
const prop = this.allSourceData.config.value const prop = this.configData.value
const list_ids = selectData.map(x => { const list_ids = selectData.map(x => {
return x[prop] return x[prop]
}) })
...@@ -398,7 +393,7 @@ export default { ...@@ -398,7 +393,7 @@ export default {
* 双击行时设置当前行为选中项 * 双击行时设置当前行为选中项
*/ */
tableRowDblclick(row) { tableRowDblclick(row) {
const prop = this.allSourceData.config.value const prop = this.configData.value
this.$emit('input', row[prop]) this.$emit('input', row[prop])
this.changeAction(row[prop]) this.changeAction(row[prop])
this.setWritebackfield([row]) this.setWritebackfield([row])
...@@ -407,7 +402,7 @@ export default { ...@@ -407,7 +402,7 @@ export default {
}, },
setLabelValue(data) { setLabelValue(data) {
const selectData = data const selectData = data
const label = this.allSourceData.config.displayfield const label = this.configData.displayfield
const label_list = selectData.map(x => x[label]) const label_list = selectData.map(x => x[label])
this.label_value = label_list.join(',') this.label_value = label_list.join(',')
this.label_value_old = this.label_value this.label_value_old = this.label_value
...@@ -418,7 +413,7 @@ export default { ...@@ -418,7 +413,7 @@ export default {
setWritebackfield(data) { setWritebackfield(data) {
this.isChange = true this.isChange = true
const selectData = data const selectData = data
const writebackfield = this.allSourceData.config.writebackfield const writebackfield = this.configData.writebackfield
if (writebackfield) { if (writebackfield) {
// 解析回写字段 // 解析回写字段
writebackfield.forEach(item => { writebackfield.forEach(item => {
...@@ -436,7 +431,7 @@ export default { ...@@ -436,7 +431,7 @@ export default {
* 清除回写字段 * 清除回写字段
*/ */
clearWritebackfield() { clearWritebackfield() {
const writebackfield = this.allSourceData.config.writebackfield const writebackfield = this.configData.writebackfield
writebackfield.forEach(item => { writebackfield.forEach(item => {
const [v1, v2] = item.split('=') const [v1, v2] = item.split('=')
if (v2) { if (v2) {
......
<template>
<div class="_hs_table">
<div class='titleToolbox'>
<div v-show="tableConfig.title">{{tableConfig.title}}</div>
<div
v-show="tableConfig.toolDirection==='row'&&tableConfig.isShowTools"
class="toolButtonGroupBox"
>
<tool-row
:toolList='toolList'
@clickLabel='clickToolLabel'
></tool-row>
</div>
</div>
<span
v-show="!tableConfig.toolDirection||tableConfig.toolDirection==='column'&&tableConfig.isShowTools"
class="iconTool"
>
<tool-column
:toolList='toolList'
@clickLabel='clickToolLabel'
></tool-column>
</span>
<ux-grid
:data-changes-scroll-top='false'
:big-data-checkbox="true"
ref="plTable"
:data="tableData"
:height="tableHeight"
use-virtual
showHeaderOverflow="title"
border
:show-summary='showSummary'
:summary-method="getSummaries"
@select-all='selectAll'
@select='selectCheckBox'
@sort-change='sortChange'
@row-dblclick='rowDblclick'
@row-click="rowClick"
@selection-change='selectionChange'
:pagination-show="!!paging"
:total="pagingConfig.total"
:page-size="pagingConfig.per_page"
:current-page="pagingConfig.page"
:page-sizes='pageSizes'
@handlePageSize='handlePageSize'
:row-height="rowHeight"
:row-style='setRowStyle'
>
<template v-for='(column,index) in tableColumns'>
<template v-if="!column.childs">
<ux-table-column
v-if='column.showType==="expandChild"'
:key="index"
type="expand"
width='50px'
title='展开'
>
<template v-slot:content="{ row }">
<rowTable :rowTable='row._childTable'></rowTable>
</template>
</ux-table-column>
<ux-table-column
v-else-if="column.showType==='index'"
:key="index"
type="index"
width="55"
/>
<ux-table-column
v-else-if="column.showType==='selection'"
:key="index"
type="checkbox"
width="55"
:selectable="selectable"
/>
<ux-table-column
v-else-if='column.showType==="handleColumn"'
:key="index"
fixed="right"
label="操作"
:width='tableConfig.handleWidth'
>
<template slot-scope="scope">
<handle-column
:data='tableHandleColumns'
:row='scope.row'
:showItem='showItem'
:disabledItem='disabledItem'
@itemClickHandle='itemClickHandle'
/>
</template>
</ux-table-column>
<ux-table-column
v-else
:key="index"
:resizable="column.resizable"
:show-overflow-tooltip="column.showOverflow"
:field="column.prop"
:title="column.label"
:fixed="column.fixed"
:min-width="column.width||80"
:sortable="column.isSort"
>
<template slot-scope="scope">
<i
v-if="column.type==='checkBox'"
:class="rowCellBoolean(scope.row[column.prop])"
></i>
<childItem
v-else
v-bind="$attrs"
v-on="$listeners"
:editable='editable'
:item='column'
:prop="column.prop"
:formParms='scope.row'
>
</childItem>
</template>
</ux-table-column>
</template>
<template v-else-if='column.childs'>
<ux-table-column
:label="column.label"
:key="index"
>
<template v-for="item in column.childs">
<ux-table-column
:field="item.prop"
:title="item.label"
:key="item.label"
:min-width="column.width||80"
>
<template slot-scope="scope">
<childItem
:item='item'
:formParms='scope.row'
:editable='editable'
v-bind="$attrs"
v-on="$listeners"
>
</childItem>
</template>
</ux-table-column>
</template>
</ux-table-column>
</template>
</template>
</ux-grid>
<tbaleColumsSet
v-model="dialogVisibleTbaleColums"
:tableDataColums='tableDataColums'
@submit="submitTableColums"
></tbaleColumsSet>
</div>
</template>
<script>
import childItem from './ItemComponentChild'
import tableTool from './tableColumsTrans'
import tableToolComponentRow from './tableToolComponentRow'
import tableToolComponentColumn from './tableToolComponentColumn'
import tableHandleComponent from './tableHandleComponent'
import { add } from 'mathjs'
import _ from 'lodash'
import tbaleColumsSet from '../../common/tbaleColumsSet'
// import utilsExcel from '../../funTools/excel/utils_excel'
import rowTable from './rowTable'
import commonMixins from '../../ucClass/commonMixins'
// import hsUtil from 'hs-util-js'
import uuT from './exportExcel'
export default {
mixins: [commonMixins],
components: {
childItem,
rowTable,
'tool-row': tableToolComponentRow,
'tool-column': tableToolComponentColumn,
'handle-column': tableHandleComponent,
tbaleColumsSet
},
props: {
getSourceData: {
type: Function
},
editable: {
default: false
},
// 数据
data: {
type: Array,
default() {
return []
}
},
paging: {},
// 高度
height: {
default: '400px'
},
// 最大高度
maxHeight: {},
// 导入信息
importInfo: {
type: Array,
default() {
return []
}
}
},
data() {
return {
rowHeight: 35, // 如果你这里给行高为50,那么你表格行会出现错乱,不要问为啥,因为你可以看看控制台看节点的高是多少,是55,而你这里给50就有问题!
columns: [],
sysTemTool: [
// 系统按钮
'$tableColumnSet',
'$exportCurrPageData',
'$exportAllPageData'
],
dialogVisibleTbaleColums: false,
tableDataColums: []
}
},
watch: {
tableData: {
handler: function(data) {
this.$nextTick(() => {
this.setIsSelectRowSelection(data)
})
},
deep: true,
immediate: true
}
},
computed: {
pagingConfig() {
if (!this.paging) return {}
const { page, per_page, total, total_page } = this.paging
this.paging.page = Number(page)
this.paging.per_page = Number(per_page)
this.paging.total = Number(total)
this.paging.total_page = Number(total_page)
return this.paging
},
pageSizes: function() {
const per_page = this.pagingConfig.per_page
const list = [10, 20, 50, 100, 200, 1000]
if (!list.includes(per_page)) {
list.unshift(per_page)
}
return list
},
// 第一行数据
firstRow() {
return (this.data.length && this.data[0]) || {}
},
// 表格真实显示数据
tableData() {
const tdata = this.data
if (!tdata) return []
// 处理原始数据,把_id排除掉
const list = tdata.filter(item => !this.hasProp(item, '_id'))
list.forEach(row => {
const _data_prop_list = Object.keys(row).filter(prop =>
prop.includes('_data_')
)
_data_prop_list.forEach(prop => {
if (typeof row[prop] === 'string' && row[prop]) {
row[prop] = JSON.parse(row[prop])
}
})
})
return list
},
// 表格高度
tableHeight() {
return this.height
},
// 表格配置
tableConfig() {
return this.config
},
// 表格列
tableColumns() {
return this.dealWithColumns()
},
// 工具栏内容:实体上的到导入配置和表格上的toolItems节点构成
toolList: function() {
return this.dealWithToolList()
},
// 表格操作列
tableHandleColumns() {
return this.dealWithHandleColumns()
},
showSummary: function() {
const tkeys = Object.keys(this.total || {}) // 返回的数据中会有这样的一个total
const sumKey = this.tableColumns.find(item => item.summarizing)
return !!tkeys.length || !!sumKey
}
},
mounted() {},
methods: {
tableDoLayout() {
this.$refs.plTable.doLayout()
},
// 选中isSelect的row,设置选中状态
setIsSelectRowSelection(data) {
data
.filter(row => row.isSelected)
.forEach(item => {
this.setToggleRowSelection(item, true)
})
},
handlePageSize({ size, page }) {
const bindEntity = this.getBindEntity()
this.$emit(
'paginationFun',
{
elInfo: this.elInfo, // 此处把组件信息返回出去 方便queryBi统一处理
pageSize: size,
page: page
},
bindEntity
)
},
hasProp(item, prop) {
return prop in item
},
// 处理操作栏
dealWithHandleColumns() {
return this.tableConfig.handleColumns || []
},
// 处理列配置
dealWithColumns() {
const { columnsConfig } = this.tableConfig
const columnsConfigTable = _.cloneDeep(columnsConfig || [])
const columnsConfig_ = []
const columnsConfig_hide = []
columnsConfigTable.forEach(item => {
const { isHide, isShow } = item
const typeofHide = typeof isHide
const typeofShow = typeof isShow
let result = true
if (typeofShow === 'boolean') {
result = isShow
} else if (typeofShow === 'function') {
result = isShow()
} else if (typeofHide === 'boolean') {
result = !isHide
} else if (typeofHide === 'function') {
result = !isHide()
} else if (typeofHide === 'undefined' && typeofShow === 'undefined') {
result = true
}
if (result) {
columnsConfig_.push(item)
} else {
columnsConfig_hide.push(item)
}
})
// 根据配置中是否有*,来判断是否有动态列
const hasDyncProp = columnsConfig_.find(
item => item.prop && item.prop.includes('*')
)
let list = []
if (hasDyncProp) {
// 获取数组第一列的所有的属性值
let allColumns = []
if (Object.keys(this.firstRow).length) {
allColumns = Object.keys(this.firstRow)
}
const columnsConfig_hideProps = columnsConfig_hide.map(x => x.prop)
// 要把isSelected 、iUpdateStatus字段删除掉
const hideProps = [
'isSelected',
'iUpdateStatus',
...columnsConfig_hideProps
]
// 把下划线开头的字段删除掉,避免显示处理
_.remove(allColumns, x => {
return hideProps.includes(x) || x.startsWith('_')
})
list = tableTool.getTableColums(columnsConfig_, allColumns)
} else {
list = tableTool.getTableColums(columnsConfig_, [])
}
this.tableConfig.showIndex && list.unshift({ showType: 'index' })
this.tableConfig.selection && list.unshift({ showType: 'selection' })
this.tableConfig.expandChild && list.unshift({ showType: 'expandChild' })
this.tableConfig.showHandle && list.push({ showType: 'handleColumn' })
return list
},
dealWithToolList() {
const newList = []
const newVal_ = _.cloneDeep(this.importInfo)
const toolItems = _.cloneDeep(this.tableConfig.toolItems || [])
newList.push(...newVal_, ...toolItems)
// 把显示的筛选出来,显示的才继续判断是否禁用
newList.forEach(item => {
item.isShow = this.showItem(item)
item.isShow && (item.isDisabled = this.disabledItem(item))
})
return newList.filter(item => item.isShow)
},
showItem(item, row) {
const { isHide, isShow } = item
const type_isHide = typeof isHide
const type_isShow = typeof isShow
const data = { row, item }
if (type_isShow === 'boolean') {
return isShow
} else if (type_isHide === 'boolean') {
return !isHide
} else if (type_isHide === 'function') {
try {
return !isHide(data)
} catch (error) {
console.log(error)
const funName = '$' + isHide
this.$message.error(`${funName} 有误`)
}
} else if (type_isShow === 'function') {
try {
return isShow(data)
} catch (error) {
console.log(error)
const funName = '$' + isShow
this.$message.error(`${funName} 有误`)
}
} else {
return true
}
},
disabledItem(item, row) {
const { disabled, disabledLogicOperation, disabledLevel, click } = item
if (this.sysTemTool.includes(click) && !disabled) return false
// disabledLogicOperation 表示是否禁用
const disabledLogicOperationValue =
typeof disabledLogicOperation === 'boolean'
? disabledLogicOperation
: false
const type = typeof disabled
const innerStatus = this.disabled && this.editable
const data = { row, item }
if (disabledLevel === 1) {
if (type === 'boolean' || type === 'undefined') {
return disabled
} else if (type === 'function') {
return disabled(data)
}
} else {
if (type === 'boolean' || type === 'undefined') {
return disabled || innerStatus || disabledLogicOperationValue
} else if (type === 'function') {
return disabled(data) || innerStatus || disabledLogicOperationValue
}
}
},
getBindEntity() {
const bindEntity = this.tableConfig.bindEntity
return bindEntity || 'dtl'
},
clickToolLabel(item) {
const { click } = item
const type = typeof click
const bindEntity = this.getBindEntity()
if (type === 'string' && click.startsWith('$')) {
const item_ = Object.assign({}, item)
item_.click = item_.click.substr(1)
switch (item_.click) {
case 'exportCurrPageData':
this.exportExcel(1)
break
case 'exportAllPageData':
this.exportExcel(2)
break
case 'tableColumnSet':
this.tableColumnSet()
break
default:
this.$emit(
'toolClick',
item_,
bindEntity,
this.tableData,
this.tableConfig
)
break
}
} else if (type === 'function') {
click(item, bindEntity)
}
},
/**
* 排序方法
*/
sortChange({ column, prop, order }) {
const sortData = {
order: this.dealWithOrderValue(order),
prop
}
debugger
this.$emit('sortChange', sortData, this.getBindEntity())
},
/**
* 处理排序值
*/
dealWithOrderValue(order) {
if (order === 'descending' || order === 'desc') return 0
if (order === 'ascending' || order === 'asc') return 1
if (!order) return ''
},
rowDblclick(row, column, event) {
const disaledDblClick = this.tableConfig.disaledDblClick
if (!disaledDblClick) {
const bindEntity = this.getBindEntity()
this.$emit('tableRowDblclick', row, bindEntity)
}
},
rowClick(row, column, event) {
const bindEntity = this.getBindEntity()
this.$emit(
'rowClick',
{
row: row,
column: column,
event: event
},
bindEntity
)
},
selectionChange(data) {
this.$emit('selectionChange', data)
},
emitSetCurrentRow(row) {
const bindEntity = this.getBindEntity()
if (!row) {
this.$emit('setCurrentRow', null, bindEntity)
} else {
row.isSelected = true
const bindEntity = this.getBindEntity()
this.$emit('setCurrentRow', row, bindEntity)
}
},
getSummaries1({ columns, data }) {
// 平均值算法(不需要自己去掉)
function cacl(arr, callback) {
let ret
for (let i = 0; i < arr.length; i++) {
ret = callback(arr[i], ret)
}
return ret
}
// 平均值算法(不需要自己去掉)
Array.prototype.sum = function() {
return cacl(this, function(item, sum) {
if (typeof sum === 'undefined') {
return item
} else {
return (sum += item)
}
})
}
// 平均值算法(不需要自己去掉)
Array.prototype.avg = function() {
if (this.length == 0) {
return 0
}
return this.sum(this) / this.length
}
const means = [] // 合计
const fenceSums = [] // 平均值
columns.forEach((column, columnIndex) => {
if (columnIndex === 0) {
means.push('合计')
fenceSums.push('平均值')
} else {
const values = data.map(item => Number(item[column.property]))
// 合计
if (!values.every(value => isNaN(value))) {
means[columnIndex] = values.reduce((prev, curr) => {
const value = Number(curr)
if (!isNaN(value)) {
return prev + curr
} else {
return prev
}
}, 0)
// means[columnIndex] += ' 元'
// 改变了ele的合计方式,扩展了合计场景
// 你以为就只有上面这样玩吗?错啦,你还可以自定义样式哦
// means[columnIndex] = '<span style="color: red">' + means[columnIndex] + '</span>'
means[columnIndex] =
'<span style="color: red">' + means[columnIndex] + '</span><br/>'
} else {
means[columnIndex] = ''
}
// 平均值
const precisions = []
let notNumber = true
values.forEach(value => {
if (!isNaN(value)) {
notNumber = false
const decimal = ('' + value).split('.')[1]
precisions.push(decimal ? decimal.length : 0)
}
})
if (!notNumber) {
fenceSums[columnIndex] = values.avg()
} else {
fenceSums[columnIndex] = ''
}
}
})
// 返回一个二维数组的表尾合计(不要平均值,你就不要在数组中添加)
return [means]
},
getSummaries(param) {
const { columns } = param
const sums = []
const sumKey = this.tableColumns.reduce((prve, curr) => {
if (curr.summarizing) {
prve.push(curr.prop)
}
return prve
}, [])
const sumObj = {}
sumKey.forEach(key => {
sumObj[key] = 0
this.tableData.forEach(item => {
if (item[key]) {
// 利用mathjs 来计算精度问题
// sumObj[key] = NP.plus(sumObj[key], Number(item[key]))
sumObj[key] = add(sumObj[key], Number(item[key]))
// sumObj[key] += Number(item[key])
}
})
})
const total_ = Object.assign(_.cloneDeep(this.total || {}))
const tkeys = Object.keys(total_)
columns.forEach((column, index) => {
const { property } = column
if (index === 0) {
sums[index] = '合计'
} else if (tkeys.length) {
if (tkeys.includes(property)) {
sums[index] = total_[property]
} else {
sums[index] = ''
}
} else if (sumKey.length) {
if (sumKey.includes(property)) {
sums[index] = sumObj[property]
} else {
sums[index] = ''
}
}
})
return [sums]
},
selectAll(selection) {
this.tableData.forEach(item => {
item.isSelected = !!selection.length
})
if (!selection.length) {
// 清空时 去掉当前行
this.emitSetCurrentRow(null, false)
}
},
setToggleRowSelection(row, flag) {
if (!row) return
this.$refs.plTable &&
this.$refs.plTable.toggleRowSelection([
// 设置当前行选中
{
row,
selected: !!flag
}
])
row.isSelected = !!flag
},
selectCheckBox(selection, row) {
row.isSelected = !row.isSelected
this.$refs.plTable.setCurrentRow(row)
this.rowClick(row)
},
selectable(row, index) {
return true
},
/* 操作列按钮点击
* item 按钮信息
* index 当前行所在行数
* row 当前行
*/
async itemClickHandle(item, row, index) {
// this.setToggleRowSelection(row, true)
const { click, confirm } = item
if (confirm) {
// 点击后弹出提示语
const confirmObj = {}
if (typeof confirm === 'string') {
confirmObj.confirmText = confirm
confirmObj.confirmButtonText = '确定'
confirmObj.cancelButtonText = '取消'
} else {
const { confirmButtonText, cancelButtonText, confirmText } = confirm
confirmObj.confirmText = confirmText
confirmObj.confirmButtonText = confirmButtonText || '确定'
confirmObj.cancelButtonText = cancelButtonText || '取消'
}
const r = await this.$confirm(confirmObj.confirmText, '提示', {
confirmButtonText: confirmObj.confirmButtonText,
cancelButtonText: confirmObj.cancelButtonText,
type: 'warning'
})
if (r !== 'confirm') {
return
}
}
const type = typeof click
const bindEntity = this.getBindEntity()
if (type === 'string' && click.startsWith('$')) {
const item_ = Object.assign({}, item) // 拷贝一份item
item_.click = item_.click.substr(1)
this.$emit('handleClick', row, item_, bindEntity)
} else if (type === 'function') {
click(row, item, bindEntity)
}
},
tableColumnSet() {
const config = _.cloneDeep(this.tableConfig)
if (config && config.columnsConfig && config.columnsConfig.length) {
this.tableDataColums = [...config.columnsConfig]
} else {
this.tableDataColums = [{}]
}
this.tableDataColums.forEach((item, index) => {
if (item.childs) {
this.tableDataColums.splice(index, 1, ...item.childs)
}
})
this.dialogVisibleTbaleColums = true
},
getPageInfo(info = this.elInfo) {
const data = {
controlName: info.position
}
return this.$listeners.webChartConfigQuery(data)
},
async submitTableColums(data, flage) {
const res = await this.getPageInfo()
let paramsData = {}
const resData = res.data
if (!resData || (Array.isArray(resData) && !resData.length)) {
paramsData.json_config = JSON.stringify(this.config || {})
paramsData.json_data = JSON.stringify(this.data || [])
paramsData.is_mock = 1
paramsData.query_sql = ''
} else if (Array.isArray(resData) && resData.length) {
paramsData = resData[0]
}
const { query_sql, json_config, json_data, is_mock } = paramsData
const json_config_ = JSON.parse(json_config)
json_config_.columnsConfig = data
const dataw = {
controlName: this.elInfo.position,
config: json_config_,
data: JSON.parse(json_data),
querySql: query_sql,
mockData: is_mock ? 1 : 0
}
this.$listeners.webChartConfigSave(dataw).then(res => {
if (flage !== 'columnStyleSet') {
this.dialogVisibleTbaleColums = false
}
this.tableConfig.columnsConfig = data
})
},
async exportExcel(flage) {
const data = this.tableData
const columnsProp_ = []
this.tableColumns.forEach(item => {
if (item.childs) {
columnsProp_.push(...item.childs)
} else {
columnsProp_.push(item)
}
})
const tHeader = []
// 筛选出具有实际意义的列(包含prop)
columnsProp_
.filter(item => item.prop)
.forEach(item => {
const str = item.label
? `${item.label}=${item.prop}`
: `${item.prop}=${item.prop}`
tHeader.push(str)
})
const exportExcelName = this.tableConfig.exportExcelName || '表'
if (flage === 2) {
const bindEntity = this.getBindEntity()
const result = await this.getSourceData(bindEntity)
if (Array.isArray(result) && result.length) {
let exportExcelData = []
if (result[0].json_data) {
const json_data =
typeof result[0].json_data === 'string'
? JSON.parse(result[0].json_data)
: result[0].json_data
exportExcelData = Array.isArray(json_data)
? json_data
: json_data.table
} else {
exportExcelData = result
}
uuT.exportToExcel(tHeader, exportExcelData, exportExcelName)
} else {
this.$message.warning('暂无数据~')
}
} else {
uuT.exportToExcel(tHeader, data, exportExcelName)
}
},
rowCellBoolean(value) {
if (Number(value)) {
return 'el-icon-check'
} else {
return 'el-icon-close'
}
},
setRowStyle({ row }) {
const { usable, bUsable, bDisabled, bill_status } = row
const valuelist = [false, 0, '0']
if (
Number(bill_status) === 5 ||
valuelist.includes(usable) ||
valuelist.includes(bUsable) ||
valuelist.includes(bDisabled)
) {
return {
'text-decoration': 'line-through',
color: '#afafaf'
}
}
}
}
}
</script>
<style scoped>
.iconTool {
position: absolute;
right: 0;
z-index: 100;
}
._hs_table >>> .plTableBox .myPagination {
padding-top: 0;
}
</style>
<style>
/* ._hs_table .el-table::before,
._hs_table .el-table::after {
height: 0 !important;
}
._hs_table body .el-table th.gutter {
display: table-cell !important;
} */
/*滑块轨道*/
._hs_table .el-table__body-wrapper::-webkit-scrollbar {
width: 8px;
height: 8px;
}
._hs_table .el-table__body-wrapper::-webkit-scrollbar-thumb {
background-color: #ddd;
border-radius: 3px;
}
/*轨道*/
._hs_table .el-table__body-wrapper::-webkit-scrollbar-track {
box-shadow: none;
-webkit-box-shadow: none;
border-radius: 0;
background: transparent;
}
._hs_table .el-table::-webkit-scrollbar-track {
/*滚动条里面轨道*/
box-shadow: none;
-webkit-box-shadow: none;
border-radius: 0;
background: transparent;
}
._hs_table .el-table::-webkit-scrollbar-thumb {
/*滚动条里面小方块*/
border-radius: 0;
box-shadow: none;
-webkit-box-shadow: none;
opacity: 0.7;
}
._hs_table ::-webkit-scrollbar {
width: 0px;
background-color: transparent;
}
.elLink {
margin: 0 3px;
font-size: 12px;
}
.toolButtonGroupBox {
display: flex;
justify-content: flex-end;
}
.titleToolbox {
display: flex;
justify-content: space-between;
}
.eldropdownitem {
width: 100px;
padding: 10px;
text-align: center;
}
.el-dropdown-link {
cursor: pointer;
color: #409eff;
margin-left: 10px;
}
.el-table__body tbody td {
padding: 0 !important;
}
.el-table td,
.el-table th {
padding: 0 !important;
}
.el-table .cell {
padding-right: 0;
}
td {
height: 35px !important;
}
</style>
<template>
<div class="_hs_table">
<div class='titleToolbox'>
<div v-show="tableConfig.title">{{tableConfig.title}}</div>
<div
v-show="tableConfig.toolDirection==='row'&&tableConfig.isShowTools"
class="toolButtonGroupBox"
>
<tool-row
:toolList='toolList'
@clickLabel='clickToolLabel'
></tool-row>
</div>
</div>
<span
v-show="!tableConfig.toolDirection||tableConfig.toolDirection==='column'&&tableConfig.isShowTools"
class="iconTool"
>
<tool-column
:toolList='toolList'
@clickLabel='clickToolLabel'
></tool-column>
</span>
<template v-if='!tableConfig.expandChild'>
<u-table
:data-changes-scroll-top='false'
:big-data-checkbox="true"
ref="plTable"
:data="tableData"
:height="tableHeight"
use-virtual
showHeaderOverflow="title"
border
:show-summary='showSummary'
:summary-method="getSummaries"
@select-all='selectAll'
@select='selectCheckBox'
@sort-change='sortChange'
@row-dblclick='rowDblclick'
@row-click="rowClick"
@selection-change='selectionChange'
:pagination-show="!!paging"
:total="pagingConfig.total"
:page-size="pagingConfig.per_page"
:current-page="pagingConfig.page"
:page-sizes='pageSizes'
@handlePageSize='handlePageSize'
:row-height="rowHeight"
:row-style='setRowStyle'
>
<template v-for='(column,index) in tableColumns'>
<template v-if="!column.childs">
<u-table-column
v-if='tableConfig.expandChild'
:key="index"
type="expand"
>
<template slot-scope="props">
<rowTable :rowTable='props.row._childTable'></rowTable>
</template>
</u-table-column>
<u-table-column
v-else-if="column.showType==='index'"
:key="index"
type="index"
width="55"
/>
<u-table-column
v-else-if="column.showType==='selection'"
:key="index"
type="selection"
width="55"
:selectable="selectable"
/>
<u-table-column
v-else-if='column.showType==="handleColumn"'
:key="index"
fixed="right"
label="操作"
:width='tableConfig.handleWidth'
>
<template slot-scope="scope">
<handle-column
:data='tableHandleColumns'
:row='scope.row'
:showItem='showItem'
:disabledItem='disabledItem'
@itemClickHandle='itemClickHandle'
/>
</template>
</u-table-column>
<u-table-column
v-else
:key="index"
:resizable="column.resizable"
:show-overflow-tooltip="column.showOverflow"
:prop="column.prop"
:label="column.label"
:fixed="column.fixed"
:min-width="column.width||80"
:sortable="column.isSort?'custom':false"
>
<template slot-scope="scope">
<i
v-if="column.type==='checkBox'"
:class="rowCellBoolean(scope.row[column.prop])"
></i>
<childItem
v-else
:fromWhere='fromWhere'
v-bind="$attrs"
v-on="$listeners"
:item='column'
:prop="column.prop"
:formParms='scope.row'
>
</childItem>
</template>
</u-table-column>
</template>
<template v-else-if='column.childs'>
<u-table-column
:label="column.label"
:key="index"
>
<template v-for="item in column.childs">
<u-table-column
:prop="item.prop"
:label="item.label"
:key="item.label"
:min-width="column.width||80"
>
<template slot-scope="scope">
<childItem
:item='item'
:formParms='scope.row'
v-bind="$attrs"
v-on="$listeners"
:fromWhere='fromWhere'
>
</childItem>
</template>
</u-table-column>
</template>
</u-table-column>
</template>
</template>
</u-table>
</template>
<template v-else>
<ux-grid
:data-changes-scroll-top='false'
:big-data-checkbox="true"
ref="plTable"
:data="tableData"
:height="tableHeight"
use-virtual
showHeaderOverflow="title"
border
:show-summary='showSummary'
:summary-method="getSummaries"
@select-all='selectAll'
@select='selectCheckBox'
@sort-change='sortChange'
@row-dblclick='rowDblclick'
@row-click="rowClick"
@selection-change='selectionChange'
:pagination-show="!!paging"
:total="pagingConfig.total"
:page-size="pagingConfig.per_page"
:current-page="pagingConfig.page"
:page-sizes='pageSizes'
@handlePageSize='handlePageSize'
:row-height="rowHeight"
:row-style='setRowStyle'
>
<template v-for='(column,index) in tableColumns'>
<template v-if="!column.childs">
<ux-table-column
v-if='column.showType==="expandChild"'
:key="index"
type="expand"
width='50px'
title='展开'
>
<template v-slot:content="{ row }">
<rowTable :rowTable='row._childTable'></rowTable>
</template>
</ux-table-column>
<ux-table-column
v-else-if="column.showType==='index'"
:key="index"
type="index"
width="55"
/>
<ux-table-column
v-else-if="column.showType==='selection'"
:key="index"
type="checkbox"
width="55"
:selectable="selectable"
/>
<ux-table-column
v-else-if='column.showType==="handleColumn"'
:key="index"
fixed="right"
label="操作"
:width='tableConfig.handleWidth'
>
<template slot-scope="scope">
<handle-column
:data='tableHandleColumns'
:row='scope.row'
:showItem='showItem'
:disabledItem='disabledItem'
@itemClickHandle='itemClickHandle'
/>
</template>
</ux-table-column>
<ux-table-column
v-else
:key="index"
:resizable="column.resizable"
:show-overflow-tooltip="column.showOverflow"
:field="column.prop"
:title="column.label"
:fixed="column.fixed"
:min-width="column.width||80"
:sortable="column.isSort"
>
<template slot-scope="scope">
<i
v-if="column.type==='checkBox'"
:class="rowCellBoolean(scope.row[column.prop])"
></i>
<childItem
v-else
v-bind="$attrs"
v-on="$listeners"
:editable='editable'
:item='column'
:prop="column.prop"
:formParms='scope.row'
>
</childItem>
</template>
</ux-table-column>
</template>
<template v-else-if='column.childs'>
<ux-table-column
:label="column.label"
:key="index"
>
<template v-for="item in column.childs">
<ux-table-column
:field="item.prop"
:title="item.label"
:key="item.label"
:min-width="column.width||80"
>
<template slot-scope="scope">
<childItem
:item='item'
:formParms='scope.row'
:editable='editable'
v-bind="$attrs"
v-on="$listeners"
>
</childItem>
</template>
</ux-table-column>
</template>
</ux-table-column>
</template>
</template>
</ux-grid>
</template>
<tbaleColumsSet
v-model="dialogVisibleTbaleColums"
:tableDataColums='tableDataColums'
@submit="submitTableColums"
></tbaleColumsSet>
</div>
</template>
<script>
import childItem from './ItemComponentChild'
import tableTool from './tableColumsTrans'
import tableToolComponentRow from './tableToolComponentRow'
import tableToolComponentColumn from './tableToolComponentColumn'
import tableHandleComponent from './tableHandleComponent'
import { add } from 'mathjs'
import _ from 'lodash'
import tbaleColumsSet from '../../common/tbaleColumsSet'
import utilsExcel from '../../funTools/excel/utils_excel'
import rowTable from './rowTable'
import commonMixins from '../../ucClass/commonMixins'
export default {
mixins: [commonMixins],
components: {
childItem,
rowTable,
'tool-row': tableToolComponentRow,
'tool-column': tableToolComponentColumn,
'handle-column': tableHandleComponent,
tbaleColumsSet
},
props: {
getSourceData: {
type: Function
},
fromWhere: {
default: 'list'
},
// 数据
data: {
type: Array,
default() {
return []
}
},
paging: {},
// 高度
height: {
default: '400px'
},
// 最大高度
maxHeight: {},
// 导入信息
importInfo: {
type: Array,
default() {
return []
}
}
},
data() {
return {
rowHeight: 35, // 如果你这里给行高为50,那么你表格行会出现错乱,不要问为啥,因为你可以看看控制台看节点的高是多少,是55,而你这里给50就有问题!
columns: [],
sysTemTool: [
// 系统按钮
'$tableColumnSet',
'$exportCurrPageData',
'$exportAllPageData'
],
dialogVisibleTbaleColums: false,
tableDataColums: []
}
},
watch: {
tableData: {
handler: function(data) {
this.$nextTick(() => {
this.setIsSelectRowSelection(data)
})
},
deep: true,
immediate: true
}
},
computed: {
pagingConfig() {
if (!this.paging) return {}
const { page, per_page, total, total_page } = this.paging
this.paging.page = Number(page)
this.paging.per_page = Number(per_page)
this.paging.total = Number(total)
this.paging.total_page = Number(total_page)
return this.paging
},
pageSizes: function() {
const per_page = this.pagingConfig.per_page
const list = [10, 20, 50, 100, 200, 1000]
if (!list.includes(per_page)) {
list.unshift(per_page)
}
return list
},
// 第一行数据
firstRow() {
return (this.data.length && this.data[0]) || {}
},
// 表格真实显示数据
tableData() {
const tdata = this.data
if (!tdata) return []
// 处理原始数据,把_id排除掉
const list = tdata.filter(item => !this.hasProp(item, '_id'))
list.forEach(row => {
const _data_prop_list = Object.keys(row).filter(prop =>
prop.includes('_data_')
)
_data_prop_list.forEach(prop => {
if (typeof row[prop] === 'string' && row[prop]) {
row[prop] = JSON.parse(row[prop])
}
})
})
return list
},
// 表格高度
tableHeight() {
return this.height
},
// 表格配置
tableConfig() {
return this.config
},
// 表格列
tableColumns() {
return this.dealWithColumns()
},
// 工具栏内容:实体上的到导入配置和表格上的toolItems节点构成
toolList: function() {
return this.dealWithToolList()
},
// 表格操作列
tableHandleColumns() {
return this.dealWithHandleColumns()
},
showSummary: function() {
const tkeys = Object.keys(this.total || {}) // 返回的数据中会有这样的一个total
const sumKey = this.tableColumns.find(item => item.summarizing)
return !!tkeys.length || !!sumKey
}
},
mounted() {},
methods: {
tableDoLayout() {
this.$refs.plTable.doLayout()
},
// 选中isSelect的row,设置选中状态
setIsSelectRowSelection(data) {
data
.filter(row => row.isSelected)
.forEach(item => {
this.setToggleRowSelection(item, true)
})
},
handlePageSize({ size, page }) {
const bindEntity = this.getBindEntity()
this.$emit(
'paginationFun',
{
elInfo: this.elInfo, // 此处把组件信息返回出去 方便queryBi统一处理
pageSize: size,
page: page
},
bindEntity
)
},
hasProp(item, prop) {
return prop in item
},
// 处理操作栏
dealWithHandleColumns() {
return this.tableConfig.handleColumns || []
},
// 处理列配置
dealWithColumns() {
const { columnsConfig } = this.tableConfig
const columnsConfigTable = _.cloneDeep(columnsConfig || [])
const columnsConfig_ = []
const columnsConfig_hide = []
columnsConfigTable.forEach(item => {
const { isHide, isShow } = item
const typeofHide = typeof isHide
const typeofShow = typeof isShow
let result = true
if (typeofShow === 'boolean') {
result = isShow
} else if (typeofShow === 'function') {
result = isShow()
} else if (typeofHide === 'boolean') {
result = !isHide
} else if (typeofHide === 'function') {
result = !isHide()
} else if (typeofHide === 'undefined' && typeofShow === 'undefined') {
result = true
}
if (result) {
columnsConfig_.push(item)
} else {
columnsConfig_hide.push(item)
}
})
// 根据配置中是否有*,来判断是否有动态列
const hasDyncProp = columnsConfig_.find(
item => item.prop && item.prop.includes('*')
)
let list = []
if (hasDyncProp) {
// 获取数组第一列的所有的属性值
let allColumns = []
if (Object.keys(this.firstRow).length) {
allColumns = Object.keys(this.firstRow)
}
const columnsConfig_hideProps = columnsConfig_hide.map(x => x.prop)
// 要把isSelected 、iUpdateStatus字段删除掉
const hideProps = [
'isSelected',
'iUpdateStatus',
...columnsConfig_hideProps
]
// 把下划线开头的字段删除掉,避免显示处理
_.remove(allColumns, x => {
return hideProps.includes(x) || x.startsWith('_')
})
list = tableTool.getTableColums(columnsConfig_, allColumns)
} else {
list = tableTool.getTableColums(columnsConfig_, [])
}
this.tableConfig.showIndex && list.unshift({ showType: 'index' })
this.tableConfig.selection && list.unshift({ showType: 'selection' })
this.tableConfig.expandChild && list.unshift({ showType: 'expandChild' })
this.tableConfig.showHandle && list.push({ showType: 'handleColumn' })
return list
},
dealWithToolList() {
const newList = []
const newVal_ = _.cloneDeep(this.importInfo)
const toolItems = _.cloneDeep(this.tableConfig.toolItems || [])
newList.push(...newVal_, ...toolItems)
// 把显示的筛选出来,显示的才继续判断是否禁用
newList.forEach(item => {
item.isShow = this.showItem(item)
item.isShow && (item.isDisabled = this.disabledItem(item))
})
return newList.filter(item => item.isShow)
},
showItem(item, row) {
const { isHide, isShow } = item
const type_isHide = typeof isHide
const type_isShow = typeof isShow
const data = { row, item }
if (type_isShow === 'boolean') {
return isShow
} else if (type_isHide === 'boolean') {
return !isHide
} else if (type_isHide === 'function') {
try {
return !isHide(data)
} catch (error) {
console.log(error)
const funName = '$' + isHide
this.$message.error(`${funName} 有误`)
}
} else if (type_isShow === 'function') {
try {
return isShow(data)
} catch (error) {
console.log(error)
const funName = '$' + isShow
this.$message.error(`${funName} 有误`)
}
} else {
return true
}
},
disabledItem(item, row) {
const { disabled, disabledLogicOperation, disabledLevel, click } = item
if (this.sysTemTool.includes(click) && !disabled) return false
// disabledLogicOperation 表示是否禁用
const disabledLogicOperationValue =
typeof disabledLogicOperation === 'boolean'
? disabledLogicOperation
: false
const type = typeof disabled
const innerStatus = this.disabled && this.fromWhere === 'hdrDtl'
const data = { row, item }
if (disabledLevel === 1) {
if (type === 'boolean' || type === 'undefined') {
return disabled
} else if (type === 'function') {
return disabled(data)
}
} else {
if (type === 'boolean' || type === 'undefined') {
return disabled || innerStatus || disabledLogicOperationValue
} else if (type === 'function') {
return disabled(data) || innerStatus || disabledLogicOperationValue
}
}
},
getBindEntity() {
const bindEntity = this.tableConfig.bindEntity
if (bindEntity) return bindEntity
if (this.fromWhere === 'hdrDtl') return 'dtl'
},
clickToolLabel(item) {
const { click } = item
const type = typeof click
const bindEntity = this.getBindEntity()
if (type === 'string' && click.startsWith('$')) {
const item_ = Object.assign({}, item)
item_.click = item_.click.substr(1)
switch (item_.click) {
case 'exportCurrPageData':
this.exportExcel(1)
break
case 'exportAllPageData':
this.exportExcel(2)
break
case 'tableColumnSet':
this.tableColumnSet()
break
default:
this.$emit(
'toolClick',
item_,
bindEntity,
this.tableData,
this.tableConfig
)
break
}
} else if (type === 'function') {
click(item, bindEntity)
}
},
/**
* 排序方法
*/
sortChange({ column, prop, order }) {
const sortData = {
order: this.dealWithOrderValue(order),
prop
}
this.$emit('sortChange', sortData, this.getBindEntity())
},
/**
* 处理排序值
*/
dealWithOrderValue(order) {
if (order === 'descending') return 0
if (order === 'ascending') return 1
if (!order) return ''
},
rowDblclick(row, column, event) {
const disaledDblClick = this.tableConfig.disaledDblClick
if (!disaledDblClick) {
const bindEntity = this.getBindEntity()
this.$emit('tableRowDblclick', row, bindEntity)
}
},
rowClick(row, column, event) {
const bindEntity = this.getBindEntity()
this.$emit(
'rowClick',
{
row: row,
column: column,
event: event
},
bindEntity
)
},
selectionChange(data) {
this.$emit('selectionChange', data)
},
emitSetCurrentRow(row) {
const bindEntity = this.getBindEntity()
if (!row) {
this.$emit('setCurrentRow', null, bindEntity)
} else {
row.isSelected = true
const bindEntity = this.getBindEntity()
this.$emit('setCurrentRow', row, bindEntity)
}
},
getSummaries1({ columns, data }) {
// 平均值算法(不需要自己去掉)
function cacl(arr, callback) {
let ret
for (let i = 0; i < arr.length; i++) {
ret = callback(arr[i], ret)
}
return ret
}
// 平均值算法(不需要自己去掉)
Array.prototype.sum = function() {
return cacl(this, function(item, sum) {
if (typeof sum === 'undefined') {
return item
} else {
return (sum += item)
}
})
}
// 平均值算法(不需要自己去掉)
Array.prototype.avg = function() {
if (this.length == 0) {
return 0
}
return this.sum(this) / this.length
}
const means = [] // 合计
const fenceSums = [] // 平均值
columns.forEach((column, columnIndex) => {
if (columnIndex === 0) {
means.push('合计')
fenceSums.push('平均值')
} else {
const values = data.map(item => Number(item[column.property]))
// 合计
if (!values.every(value => isNaN(value))) {
means[columnIndex] = values.reduce((prev, curr) => {
const value = Number(curr)
if (!isNaN(value)) {
return prev + curr
} else {
return prev
}
}, 0)
// means[columnIndex] += ' 元'
// 改变了ele的合计方式,扩展了合计场景
// 你以为就只有上面这样玩吗?错啦,你还可以自定义样式哦
// means[columnIndex] = '<span style="color: red">' + means[columnIndex] + '</span>'
means[columnIndex] =
'<span style="color: red">' + means[columnIndex] + '</span><br/>'
} else {
means[columnIndex] = ''
}
// 平均值
const precisions = []
let notNumber = true
values.forEach(value => {
if (!isNaN(value)) {
notNumber = false
const decimal = ('' + value).split('.')[1]
precisions.push(decimal ? decimal.length : 0)
}
})
if (!notNumber) {
fenceSums[columnIndex] = values.avg()
} else {
fenceSums[columnIndex] = ''
}
}
})
// 返回一个二维数组的表尾合计(不要平均值,你就不要在数组中添加)
return [means]
},
getSummaries(param) {
const { columns } = param
const sums = []
const sumKey = this.tableColumns.reduce((prve, curr) => {
if (curr.summarizing) {
prve.push(curr.prop)
}
return prve
}, [])
const sumObj = {}
sumKey.forEach(key => {
sumObj[key] = 0
this.tableData.forEach(item => {
if (item[key]) {
// 利用mathjs 来计算精度问题
// sumObj[key] = NP.plus(sumObj[key], Number(item[key]))
sumObj[key] = add(sumObj[key], Number(item[key]))
// sumObj[key] += Number(item[key])
}
})
})
const total_ = Object.assign(_.cloneDeep(this.total || {}))
const tkeys = Object.keys(total_)
columns.forEach((column, index) => {
const { property } = column
if (index === 0) {
sums[index] = '合计'
} else if (tkeys.length) {
if (tkeys.includes(property)) {
sums[index] = total_[property]
} else {
sums[index] = ''
}
} else if (sumKey.length) {
if (sumKey.includes(property)) {
sums[index] = sumObj[property]
} else {
sums[index] = ''
}
}
})
return [sums]
},
selectAll(selection) {
this.tableData.forEach(item => {
item.isSelected = !!selection.length
})
if (!selection.length) {
// 清空时 去掉当前行
this.emitSetCurrentRow(null, false)
}
},
setToggleRowSelection(row, flag) {
if (!row) return
this.$refs.plTable &&
this.$refs.plTable.toggleRowSelection([
// 设置当前行选中
{
row,
selected: !!flag
}
])
row.isSelected = !!flag
},
selectCheckBox(selection, row) {
row.isSelected = !row.isSelected
this.$refs.plTable.setCurrentRow(row)
this.rowClick(row)
},
selectable(row, index) {
return true
},
/* 操作列按钮点击
* item 按钮信息
* index 当前行所在行数
* row 当前行
*/
async itemClickHandle(item, row, index) {
// this.setToggleRowSelection(row, true)
const { click, confirm } = item
if (confirm) {
// 点击后弹出提示语
const confirmObj = {}
if (typeof confirm === 'string') {
confirmObj.confirmText = confirm
confirmObj.confirmButtonText = '确定'
confirmObj.cancelButtonText = '取消'
} else {
const { confirmButtonText, cancelButtonText, confirmText } = confirm
confirmObj.confirmText = confirmText
confirmObj.confirmButtonText = confirmButtonText || '确定'
confirmObj.cancelButtonText = cancelButtonText || '取消'
}
const r = await this.$confirm(confirmObj.confirmText, '提示', {
confirmButtonText: confirmObj.confirmButtonText,
cancelButtonText: confirmObj.cancelButtonText,
type: 'warning'
})
if (r !== 'confirm') {
return
}
}
const type = typeof click
const bindEntity = this.getBindEntity()
if (type === 'string' && click.startsWith('$')) {
const item_ = Object.assign({}, item) // 拷贝一份item
item_.click = item_.click.substr(1)
this.$emit('handleClick', row, item_, bindEntity)
} else if (type === 'function') {
click(row, item, bindEntity)
}
},
tableColumnSet() {
const config = _.cloneDeep(this.tableConfig)
if (config && config.columnsConfig && config.columnsConfig.length) {
this.tableDataColums = [...config.columnsConfig]
} else {
this.tableDataColums = [{}]
}
this.tableDataColums.forEach((item, index) => {
if (item.childs) {
this.tableDataColums.splice(index, 1, ...item.childs)
}
})
this.dialogVisibleTbaleColums = true
},
getPageInfo(info = this.elInfo) {
const data = {
controlName: info.position
}
return this.$listeners.webChartConfigQuery(data)
},
async submitTableColums(data, flage) {
const res = await this.getPageInfo()
let paramsData = {}
const resData = res.data
if (!resData || (Array.isArray(resData) && !resData.length)) {
paramsData.json_config = JSON.stringify(this.config || {})
paramsData.json_data = JSON.stringify(this.data || [])
paramsData.is_mock = 1
paramsData.query_sql = ''
} else if (Array.isArray(resData) && resData.length) {
paramsData = resData[0]
}
const { query_sql, json_config, json_data, is_mock } = paramsData
const json_config_ = JSON.parse(json_config)
json_config_.columnsConfig = data
const dataw = {
controlName: this.elInfo.position,
config: json_config_,
data: JSON.parse(json_data),
querySql: query_sql,
mockData: is_mock ? 1 : 0
}
this.$listeners.webChartConfigSave(dataw).then(res => {
if (flage !== 'columnStyleSet') {
this.dialogVisibleTbaleColums = false
}
this.tableConfig.columnsConfig = data
})
},
async exportExcel(flage) {
const data = this.tableData
const columnsProp_ = []
this.tableColumns.forEach(item => {
if (item.childs) {
columnsProp_.push(...item.childs)
} else {
columnsProp_.push(item)
}
})
const tHeader = []
// 筛选出具有实际意义的列(包含prop)
columnsProp_
.filter(item => item.prop)
.forEach(item => {
const str = item.label
? `${item.label}=${item.prop}`
: `${item.prop}=${item.prop}`
tHeader.push(str)
})
const exportExcelName = this.tableConfig.exportExcelName || '表'
if (flage === 2) {
const bindEntity = this.getBindEntity()
const result = await this.getSourceData(bindEntity)
if (Array.isArray(result) && result.length) {
let exportExcelData = []
if (result[0].json_data) {
const json_data =
typeof result[0].json_data === 'string'
? JSON.parse(result[0].json_data)
: result[0].json_data
exportExcelData = Array.isArray(json_data)
? json_data
: json_data.table
} else {
exportExcelData = result
}
utilsExcel.exportToExcel(tHeader, exportExcelData, exportExcelName)
} else {
this.$message.warning('暂无数据~')
}
} else {
utilsExcel.exportToExcel(tHeader, data, exportExcelName)
}
},
rowCellBoolean(value) {
if (Number(value)) {
return 'el-icon-check'
} else {
return 'el-icon-close'
}
},
setRowStyle({ row }) {
const { usable, bUsable, bDisabled, bill_status } = row
const valuelist = [false, 0, '0']
if (
Number(bill_status) === 5 ||
valuelist.includes(usable) ||
valuelist.includes(bUsable) ||
valuelist.includes(bDisabled)
) {
return {
'text-decoration': 'line-through',
color: '#afafaf'
}
}
}
}
}
</script>
<style scoped>
.iconTool {
position: absolute;
right: 0;
z-index: 100;
}
._hs_table >>> .plTableBox .myPagination {
padding-top: 0;
}
</style>
<style>
/* ._hs_table .el-table::before,
._hs_table .el-table::after {
height: 0 !important;
}
._hs_table body .el-table th.gutter {
display: table-cell !important;
} */
/*滑块轨道*/
._hs_table .el-table__body-wrapper::-webkit-scrollbar {
width: 8px;
height: 8px;
}
._hs_table .el-table__body-wrapper::-webkit-scrollbar-thumb {
background-color: #ddd;
border-radius: 3px;
}
/*轨道*/
._hs_table .el-table__body-wrapper::-webkit-scrollbar-track {
box-shadow: none;
-webkit-box-shadow: none;
border-radius: 0;
background: transparent;
}
._hs_table .el-table::-webkit-scrollbar-track {
/*滚动条里面轨道*/
box-shadow: none;
-webkit-box-shadow: none;
border-radius: 0;
background: transparent;
}
._hs_table .el-table::-webkit-scrollbar-thumb {
/*滚动条里面小方块*/
border-radius: 0;
box-shadow: none;
-webkit-box-shadow: none;
opacity: 0.7;
}
._hs_table ::-webkit-scrollbar {
width: 0px;
background-color: transparent;
}
.elLink {
margin: 0 3px;
font-size: 12px;
}
.toolButtonGroupBox {
display: flex;
justify-content: flex-end;
}
.titleToolbox {
display: flex;
justify-content: space-between;
}
.eldropdownitem {
width: 100px;
padding: 10px;
text-align: center;
}
.el-dropdown-link {
cursor: pointer;
color: #409eff;
margin-left: 10px;
}
.el-table__body tbody td {
padding: 0 !important;
}
.el-table td,
.el-table th {
padding: 0 !important;
}
.el-table .cell {
padding-right: 0;
}
td {
height: 35px !important;
}
</style>
...@@ -21,134 +21,263 @@ ...@@ -21,134 +21,263 @@
@clickLabel='clickToolLabel' @clickLabel='clickToolLabel'
></tool-column> ></tool-column>
</span> </span>
<ux-grid <template v-if='!tableConfig.expandChild'>
:data-changes-scroll-top='false' <u-table
:big-data-checkbox="true" :data-changes-scroll-top='false'
ref="plTable" :big-data-checkbox="true"
:data="tableData" ref="plTable"
:height="tableHeight" :data="tableData"
use-virtual :height="tableHeight"
showHeaderOverflow="title" use-virtual
border showHeaderOverflow="title"
:show-summary='showSummary' border
:summary-method="getSummaries" :show-summary='showSummary'
@select-all='selectAll' :summary-method="getSummaries"
@select='selectCheckBox' @select-all='selectAll'
@sort-change='sortChange' @select='selectCheckBox'
@row-dblclick='rowDblclick' @sort-change='sortChange'
@row-click="rowClick" @row-dblclick='rowDblclick'
@selection-change='selectionChange' @row-click="rowClick"
:pagination-show="!!paging" @selection-change='selectionChange'
:total="pagingConfig.total" :pagination-show="!!paging"
:page-size="pagingConfig.per_page" :total="pagingConfig.total"
:current-page="pagingConfig.page" :page-size="pagingConfig.per_page"
:page-sizes='pageSizes' :current-page="pagingConfig.page"
@handlePageSize='handlePageSize' :page-sizes='pageSizes'
:row-height="rowHeight" @handlePageSize='handlePageSize'
:row-style='setRowStyle' :row-height="rowHeight"
> :row-style='setRowStyle'
>
<template v-for='(column,index) in tableColumns'> <template v-for='(column,index) in tableColumns'>
<template v-if="!column.childs"> <template v-if="!column.childs">
<ux-table-column <u-table-column
v-if='column.showType==="expandChild"' v-if='tableConfig.expandChild'
:key="index" :key="index"
type="expand" type="expand"
width='50px' >
title='展开' <template slot-scope="props">
> <rowTable :rowTable='props.row._childTable'></rowTable>
<template v-slot:content="{ row }"> </template>
<rowTable :rowTable='row._childTable'></rowTable> </u-table-column>
</template> <u-table-column
</ux-table-column> v-else-if="column.showType==='index'"
<ux-table-column :key="index"
v-else-if="column.showType==='index'" type="index"
:key="index" width="55"
type="index" />
width="55" <u-table-column
/> v-else-if="column.showType==='selection'"
<ux-table-column :key="index"
v-else-if="column.showType==='selection'" type="selection"
:key="index" width="55"
type="checkbox" :selectable="selectable"
width="55" />
:selectable="selectable" <u-table-column
/> v-else-if='column.showType==="handleColumn"'
<ux-table-column :key="index"
v-else-if='column.showType==="handleColumn"' fixed="right"
:key="index" label="操作"
fixed="right" :width='tableConfig.handleWidth'
label="操作" >
:width='tableConfig.handleWidth' <template slot-scope="scope">
> <handle-column
<template slot-scope="scope"> :data='tableHandleColumns'
<handle-column :row='scope.row'
:data='tableHandleColumns' :showItem='showItem'
:row='scope.row' :disabledItem='disabledItem'
:showItem='showItem' @itemClickHandle='itemClickHandle'
:disabledItem='disabledItem' />
@itemClickHandle='itemClickHandle' </template>
/> </u-table-column>
</template> <u-table-column
</ux-table-column> v-else
<ux-table-column :key="index"
v-else :resizable="column.resizable"
:key="index" :show-overflow-tooltip="column.showOverflow"
:resizable="column.resizable" :prop="column.prop"
:show-overflow-tooltip="column.showOverflow" :label="column.label"
:field="column.prop" :fixed="column.fixed"
:title="column.label" :min-width="column.width||80"
:fixed="column.fixed" :sortable="column.isSort?'custom':false"
:min-width="column.width||80" >
:sortable="column.isSort" <template slot-scope="scope">
> <i
<template slot-scope="scope"> v-if="column.type==='checkBox'"
<i :class="rowCellBoolean(scope.row[column.prop])"
v-if="column.type==='checkBox'" ></i>
:class="rowCellBoolean(scope.row[column.prop])" <childItem
></i> v-else
<childItem :editable='editable'
v-else v-bind="$attrs"
v-bind="$attrs" v-on="$listeners"
v-on="$listeners" :item='column'
:editable='editable' :prop="column.prop"
:item='column' :formParms='scope.row'
:prop="column.prop" >
:formParms='scope.row' </childItem>
> </template>
</childItem> </u-table-column>
</template> </template>
</ux-table-column> <template v-else-if='column.childs'>
<u-table-column
:label="column.label"
:key="index"
>
<template v-for="item in column.childs">
<u-table-column
:prop="item.prop"
:label="item.label"
:key="item.label"
:min-width="column.width||80"
>
<template slot-scope="scope">
<childItem
:item='item'
:formParms='scope.row'
v-bind="$attrs"
v-on="$listeners"
:editable='editable'
>
</childItem>
</template>
</u-table-column>
</template>
</u-table-column>
</template>
</template> </template>
<template v-else-if='column.childs'> </u-table>
<ux-table-column </template>
:label="column.label" <template v-else>
:key="index" <ux-grid
> :data-changes-scroll-top='false'
<template v-for="item in column.childs"> :big-data-checkbox="true"
<ux-table-column ref="plTable"
:field="item.prop" :data="tableData"
:title="item.label" :height="tableHeight"
:key="item.label" use-virtual
:min-width="column.width||80" showHeaderOverflow="title"
> border
<template slot-scope="scope"> :show-summary='showSummary'
<childItem :summary-method="getSummaries"
:item='item' @select-all='selectAll'
:formParms='scope.row' @select='selectCheckBox'
:editable='editable' @sort-change='sortChange'
v-bind="$attrs" @row-dblclick='rowDblclick'
v-on="$listeners" @row-click="rowClick"
> @selection-change='selectionChange'
</childItem> :pagination-show="!!paging"
</template> :total="pagingConfig.total"
</ux-table-column> :page-size="pagingConfig.per_page"
</template> :current-page="pagingConfig.page"
</ux-table-column> :page-sizes='pageSizes'
@handlePageSize='handlePageSize'
:row-height="rowHeight"
:row-style='setRowStyle'
>
<template v-for='(column,index) in tableColumns'>
<template v-if="!column.childs">
<ux-table-column
v-if='column.showType==="expandChild"'
:key="index"
type="expand"
width='50px'
title='展开'
>
<template v-slot:content="{ row }">
<rowTable :rowTable='row._childTable'></rowTable>
</template>
</ux-table-column>
<ux-table-column
v-else-if="column.showType==='index'"
:key="index"
type="index"
width="55"
/>
<ux-table-column
v-else-if="column.showType==='selection'"
:key="index"
type="checkbox"
width="55"
:selectable="selectable"
/>
<ux-table-column
v-else-if='column.showType==="handleColumn"'
:key="index"
fixed="right"
label="操作"
:width='tableConfig.handleWidth'
>
<template slot-scope="scope">
<handle-column
:data='tableHandleColumns'
:row='scope.row'
:showItem='showItem'
:disabledItem='disabledItem'
@itemClickHandle='itemClickHandle'
/>
</template>
</ux-table-column>
<ux-table-column
v-else
:key="index"
:resizable="column.resizable"
:show-overflow-tooltip="column.showOverflow"
:field="column.prop"
:title="column.label"
:fixed="column.fixed"
:min-width="column.width||80"
:sortable="column.isSort"
>
<template slot-scope="scope">
<i
v-if="column.type==='checkBox'"
:class="rowCellBoolean(scope.row[column.prop])"
></i>
<childItem
v-else
v-bind="$attrs"
v-on="$listeners"
:editable='editable'
:item='column'
:prop="column.prop"
:formParms='scope.row'
>
</childItem>
</template>
</ux-table-column>
</template>
<template v-else-if='column.childs'>
<ux-table-column
:label="column.label"
:key="index"
>
<template v-for="item in column.childs">
<ux-table-column
:field="item.prop"
:title="item.label"
:key="item.label"
:min-width="column.width||80"
>
<template slot-scope="scope">
<childItem
:item='item'
:formParms='scope.row'
:editable='editable'
v-bind="$attrs"
v-on="$listeners"
>
</childItem>
</template>
</ux-table-column>
</template>
</ux-table-column>
</template>
</template> </template>
</template>
</ux-grid> </ux-grid>
</template>
<tbaleColumsSet <tbaleColumsSet
v-model="dialogVisibleTbaleColums" v-model="dialogVisibleTbaleColums"
:tableDataColums='tableDataColums' :tableDataColums='tableDataColums'
......
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