From 33dbc6a161554f3a897f9e9273feb4f2c1b47381 Mon Sep 17 00:00:00 2001
From: chenlu <1320612696@qq.com>
Date: 星期一, 15 十二月 2025 17:04:27 +0800
Subject: [PATCH] Merge branch 'master' of http://10.153.19.25:10105/r/ERP_override
---
north-glass-erp/northglass-erp/src/components/BasicTable.vue | 376 +++++++++++++++++++++++++++++++++++++++++++++--------
1 files changed, 317 insertions(+), 59 deletions(-)
diff --git a/north-glass-erp/northglass-erp/src/components/BasicTable.vue b/north-glass-erp/northglass-erp/src/components/BasicTable.vue
index b77ee15..9bd61fa 100644
--- a/north-glass-erp/northglass-erp/src/components/BasicTable.vue
+++ b/north-glass-erp/northglass-erp/src/components/BasicTable.vue
@@ -1,19 +1,34 @@
<script setup>
import {Search} from "@element-plus/icons-vue"
-import {reactive, ref} from "vue"
+import {defineEmits, onMounted, reactive, ref, watch} from "vue"
+import {changeFilterEvent} from "@/hook"
+import request from "@/utils/request"
+import exportExcel from "@/hook/exportExcel"
+import {addListener,exportData} from "@/hook/mouseMove"
+import deepClone from "@/utils/deepClone";
+import {ElMessage} from "element-plus";
+import * as XLSX from "xlsx";
+import {useI18n} from "vue-i18n";
+import useOrderInfoStore from "@/stores/sd/order/orderInfo";
+
+const { t } = useI18n()
const xGrid = ref()
+let filterData = ref({})
+const orderInfo = useOrderInfoStore()
const gridOptions = reactive({
+ loading:true,
border: "full",//琛ㄦ牸鍔犺竟妗�
keepSource: true,//淇濇寔婧愭暟鎹�
align: 'center',//鏂囧瓧灞呬腑
stripe:true,//鏂戦┈绾�
- rowConfig: {isCurrent: true, isHover: true,height: 50},//榧犳爣绉诲姩鎴栭�夋嫨楂樹寒
+ rowConfig: {isCurrent: true, isHover: true,height: 30},//榧犳爣绉诲姩鎴栭�夋嫨楂樹寒
id: 'OrderReport',
showFooter: true,//鏄剧ず鑴�
printConfig: {},
importConfig: {},
exportConfig: {},
- scrollY:{ enabled: true },//寮�鍚櫄鎷熸粴鍔�
+ scrollY:{ enabled: true,gt:0 },//寮�鍚櫄鎷熸粴鍔�
+ scrollX:{ enabled: true,gt:5 },//寮�鍚櫄鎷熸粴鍔�
showOverflow:true,
columnConfig: {
resizable: true,
@@ -30,50 +45,25 @@
mode: 'row',
showStatus: true
},//琛ㄥご鍙傛暟
+ menuConfig: {
+ body: {
+ options: [
+ [
+
+ { code: 'exportExcelChecked', name: t('components.exportSelected'), prefixIcon: 'vxe-icon-download', visible: true }
+ ]
+ ]
+ }
+ },
columns:[
- {type:'expand',fixed:"left",slots: { content:'content' },width: 50},
- {type: 'seq',fixed:"left", title: '鑷簭', width: 80 },
- {field: '1',width:120, title: '璁㈠崟绫诲瀷',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: '2',width:120, title: '瀹㈡埛鍚嶇О',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: '3',width:120, title: '椤圭洰鍚嶇О',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: '4',width:120, title: '閿�鍞崟鍙�',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: '5',width:120, title: '鎵规',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: '6',width:120, title: '浜у搧缂栧彿',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: '7',width:120, title: '浜у搧缂栫爜',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: '8',width:120, title: '浜у搧鍚嶇О',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: '9',width:120, title: '璁㈠崟搴忓彿',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '妤煎彿',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '瀹�',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '楂�',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '鏁伴噺',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '鍗婂緞',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '瀹為檯闈㈢Н',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '缁撶畻鎬婚潰绉�',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '褰㈢姸',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '纾ㄨ竟绫诲瀷',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '涓诲姞宸ヨ姹�',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '鍔犲伐瑕佹眰',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '澶囨敞',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '鍟嗘爣閫夐」',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '鍖呰鏂瑰紡',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '宸ヨ壓娴佺▼',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '鍛ㄩ暱',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '鍗曚环',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '閲戦',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '閾濇潯鏂瑰紡',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '璁㈠崟绫诲瀷',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '涓氬姟鍛�',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '閫佽揣鍦板潃',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '鍒跺崟鍛�',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '寤虹珛鏃堕棿',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '鎬诲帤搴�',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '浜у搧澶х被',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '浜у搧灏忕被',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true},
- {field: 'prodID',width:120, title: '瀹㈡埛鎵规',filters:[{ data: '' }],slots: { filter: 'num1_filter' }, sortable: true}
],//琛ㄥご鎸夐挳
toolbarConfig: {
buttons: [],
+ slots: {
+ tools: 'toolbar_buttons',
+ buttons:'buttons'
+ },
// import: false,
// export: true,
// print: true,
@@ -86,41 +76,296 @@
return[
columns.map((column, columnIndex) => {
if (columnIndex === 0) {
- return '鍚堣:'
+ return t('basicData.total')
}
- // if (props.tableProp.footList.includes(column.field)) {
- // return sumNum(data, column.field)
- // }
+ if (props.childrenData.footList.includes(column.field)) {
+ return sumNum(data, column.field)
+ }
return ''
})
]
}
})
+const gridEvents = {
+ menuClick ({ menu, row, column }) {
+ const $grid = xGrid.value
+ if ($grid) {
+ switch (menu.code) {
+ case 'exportExcelChecked': {
+ let result = exportData()
+ if(result){
+ // 灏嗘暟鎹浆鎹负 worksheet 瀵硅薄
+ const worksheet = XLSX.utils.aoa_to_sheet(result);
+ const workbook = XLSX.utils.book_new();
+ XLSX.utils.book_append_sheet(workbook, worksheet, 'Sheet1');
+ XLSX.writeFile(workbook, `${props.childrenData.exportName}.xlsx`);
+ }
+ break
+ }
+ }
+ }
+ }
+}
+
+
+const props = defineProps({
+ childrenData:{
+ Object,
+ default: ''
+ }
+})
+const basicProp = ref({
+ pageSize : 10000,//椤甸潰鏄剧ず鏁伴噺
+ pageNum:1,//褰撳墠椤�
+ selectDate:['',''],//鏌ヨ鐨勬棩鏈�
+ pageTotal : 0,//鎬婚〉鏁�
+ dataTotal : 0,//鏁版嵁鎬绘潯鏁�
+})
+const sumNum = (list, field) => {
+ let count = 0
+ list.forEach(item => {
+ count += Number(item[field])
+ })
+ return count.toFixed(2)
+}
+
+//鍚堝苟鏄剧ず鍏朵粬鍒�
+const handleDynamicColumns = (data,title) => {
+ // 1. 鏀堕泦鎵�鏈夎鐨刼therColumns瀛楁锛堝幓閲嶏級
+ const allOtherFields = new Set();
+ data.forEach(row => {
+ if (!row || !row.otherColumns) return;
+
+ let parsedOtherColumns;
+ try {
+ // 鏍稿績锛氬皢瀛楃涓茶В鏋愪负JSON
+ parsedOtherColumns = JSON.parse(row.otherColumns);
+ } catch (e) {
+ console.error('瑙f瀽otherColumns澶辫触锛�', e, '鍘熷鏁版嵁锛�', row.otherColumns);
+ return;
+ }
+
+ // 2. 浠庤В鏋愬悗鐨凧SON涓敹闆嗗瓧娈碉紙鏀寔鏁扮粍鎴栧璞℃牸寮忥級
+ if (Array.isArray(parsedOtherColumns)) {
+ // 鏁扮粍鏍煎紡锛歔{ key: 'field1', label: '瀛楁1', value: '鍊�1' }, ...]
+ parsedOtherColumns.forEach(item => {
+ if (item.key) allOtherFields.add(item.key);
+ });
+ } else if (typeof parsedOtherColumns === 'object' && parsedOtherColumns !== null) {
+ // 瀵硅薄鏍煎紡锛歿 field1: { label: '瀛楁1', value: '鍊�1' }, ... }
+ Object.keys(parsedOtherColumns).forEach(key => {
+ allOtherFields.add(key);
+ });
+ }
+ });
+
+ // 2. 鐢熸垚鍔ㄦ�佸瓙鍒楋紙浣滀负processList鐨刢hildren锛�
+ const otherColumns = Array.from(allOtherFields).map(field => {
+ // 灏濊瘯鑾峰彇瀛楁瀵瑰簲鐨刲abel锛堜紭鍏堝彇绗竴涓嚭鐜扮殑label锛�
+ let label=field;
+ title.forEach(item=>{
+ if(field==item.column){
+ label=item.alias
+ }
+ })
+ return {
+ title: label,
+ field: `otherColumnsJson.${field}`,
+ width: 120,
+ align: 'center',
+ // 澶勭悊瀛楁鍊兼樉绀猴紙鍏煎鏁扮粍/瀵硅薄绫诲瀷鐨刼therColumns锛�
+ formatter: ({ row }) => {
+ return row.otherColumnsJson?.[field] || '';
+
+ }
+ };
+ });
+
+ // 3. 瀹氫箟鐖剁骇鍒梡rocessList锛屽寘鍚姩鎬佸瓙鍒�
+ const processList = {
+ title: t('basicData.otherColumns'),
+ field: 'process',
+ children: otherColumns // 灏嗗姩鎬佸垪浣滀负瀛愬垪
+ };
+
+ // 4. 鍏堢Щ闄ゅ凡瀛樺湪鐨刾rocess鍒楋紙閬垮厤閲嶅锛夛紝鍐嶆坊鍔犳柊鍒�
+ gridOptions.columns = gridOptions.columns.filter(col => col.field !== 'process');
+ gridOptions.columns.push(processList);
+}
+
+
+
+
+watch(props, (newVal) => {
+ xGrid.value.loadData(props.childrenData.data)
+ gridOptions.loading = false
+})
+onMounted(() => {
+ gridOptions.columns = props.childrenData.columns
+ getReportData()
+ addListener(xGrid.value,gridOptions)
+})
+function filterChanged(column){
+ //gridOptions.loading=true
+ //绛涢�夋潯浠跺彂鐢熷彉鍖栨潯浠跺彂鐢熷彉鍖�
+ let value = column.datas[0]!=undefined?column.datas[0]:''
+ value = value.trim()
+ //鍒ゆ柇鏄惁瀛樺湪澶栭敭
+ if (column.property.indexOf('.')>-1){
+ const columnArr = column.property.split('.')
+ filterData.value[columnArr[0]] = {
+ [columnArr[1]]:value
+ }
+ }else{
+ filterData.value[column.property] = value
+ }
+
+ gridOptions.loading = true
+ getReportData()
+
+}
+
+const handlePageChange = ({ currentPage, pageSize }) => {
+ basicProp.value.pageNum = currentPage
+ basicProp.value.pageTotal = pageSize
+ gridOptions.loading = true
+ getReportData()
+}
+const dateChanged = () => {
+ gridOptions.loading = true
+ getReportData()
+}
+
+const getReportData = () => {
+ if(props.childrenData.model!=null){
+ request.post(`${props.childrenData.url}/${basicProp.value.pageNum}/${basicProp.value.pageSize}/${orderInfo.reportFormDate}/${props.childrenData.model}/${props.childrenData.scope}`,filterData.value).then(res => {
+ if(res.code === '200'){
+ props.childrenData.data = res.data.data
+ basicProp.value.pageTotal = res.data.total.pageTotal
+ basicProp.value.dataTotal = res.data.total.total
+ orderInfo.reportFormDate = res.data.selectDate
+
+ //璁㈠崟鏄庣粏鎶ヨ〃
+ if (props.childrenData.url === '/order/getOrderReport') {
+ const dataList = res.data.data || [];
+ handleDynamicColumns(dataList,res.data.title)
+ }
+ }
+ })
+ return
+ }
+ request.post(`${props.childrenData.url}/${basicProp.value.pageNum}/${basicProp.value.pageSize}/${orderInfo.reportFormDate}`,filterData.value).then(res => {
+ if(res.code === '200'){
+ props.childrenData.data = res.data.data
+ basicProp.value.pageTotal = res.data.total.pageTotal
+ basicProp.value.dataTotal = res.data.total.total
+ orderInfo.reportFormDate = res.data.selectDate
+
+
+ }
+ })
+}
+
+const exportEvent = () => {
+ const $table = xGrid.value
+ if ($table) {
+ $table.exportData({
+ filename: 'order_export',
+ sheetName: 'Sheet1',
+ type: 'xlsx'
+ })
+ }
+}
+
+
</script>
<template>
- <div class="main-div">
+ <div style="width: 100%;height: 100%">
+ <div class="head">
<el-date-picker
- v-model="value1"
+ v-model="orderInfo.reportFormDate"
type="daterange"
- start-placeholder="寮�濮嬫椂闂�"
- end-placeholder="缁撴潫鏃堕棿"
+ :start-placeholder="$t('basicData.startDate')"
+ :end-placeholder="$t('basicData.endDate')"
+ format="YYYY-MM-DD"
+ value-format="YYYY-MM-DD"
/>
- <el-button style="margin-top: -5px" id="searchButton" type="primary" :icon="Search">鏌ヨ</el-button>
- <div class="order-detail">
+ <el-button
+ @click="dateChanged"
+ id="searchButton"
+ type="primary"
+ style="margin-top: -5px"
+ :icon="Search">{{$t('basicData.search')}}</el-button>
+ </div>
+ <div class="main-table">
<vxe-grid
- max-height="97%"
+ @filter-change="filterChanged"
+ height="100%"
class="mytable-scrollbar"
ref="xGrid"
v-bind="gridOptions"
- ></vxe-grid>
+ v-on="gridEvents"
+ >
+ <!-- 涓嬫媺鏄剧ず鎵�鏈変俊鎭彃妲�-->
+ <template #content="{ row }">
+ <ul class="expand-wrapper">
+ <li v-for="(item,index) in gridOptions.columns" v-show="item.field!==undefined && index>9">
+ <span style="font-weight: bold">{{item.title+': '}}</span>
+ <span>{{ row[item.field] }}</span>
+ </li>
+ </ul>
+ </template>
+ <!-- 涓嬫媺绛涢�夋彃妲�-->
+ <template #num1_filter="{ column, $panel }">
+ <div>
+ <div v-for="(option, index) in column.filters" :key="index">
+ <input type="text"
+ v-model="option.data"
+ @keyup.enter.native="$panel.confirmFilter()"
+ @input="changeFilterEvent($event, option, $panel)"/>
+ </div>
+ </div>
+ </template>
+
+ <template #toolbar_buttons>
+ <vxe-button icon="vxe-icon-download" circle
+ style="margin-right: 0.5rem"
+ @click="exportEvent" />
+
+ <vxe-button icon="vxe-icon-cloud-download" style="margin-right: 0.5rem"
+ circle
+ @click="exportExcel(props.childrenData.exportUrl,
+ props.childrenData.exportName,
+ orderInfo.reportFormDate)" />
+
+ </template>
+ <template #buttons>
+ <slot name="buttons"></slot>
+ </template>
+
+
+ <template #pager>
+ <!--浣跨敤 pager 鎻掓Ы-->
+ <!-- 'PrevJump','NextJump', -->
+ <vxe-pager
+ @page-change="handlePageChange"
+ :layouts="[ 'PrevPage', 'Jump','PageCount', 'NextPage', 'Total']"
+ v-model:current-page="basicProp.pageNum"
+ v-model:page-size="basicProp.pageSize"
+ v-model:pager-count="basicProp.pageTotal"
+ :total="basicProp.dataTotal"
+ >
+ </vxe-pager>
+ </template>
+ </vxe-grid>
</div>
</div>
</template>
-<style scoped>
+<style scoped >
.main-div {
width: 100%;
height: 100%;
@@ -134,12 +379,25 @@
border: none !important;
background-color: transparent;
}
-.order-primary{
+.head{
width: 100%;
+ height: 35px;
}
-.order-detail{
- width: 100%;
- height: 90%;
+.main-table{
+ width: 100%;
+ height: calc(100% - 35px);
+}
+
+.vxe-grid {
+ /* 绂佺敤娴忚鍣ㄩ粯璁ら�変腑 */
+ -webkit-user-select: none;
+ -moz-user-select: none;
+ -ms-user-select: none;
+ user-select: none;
+}
+:deep(#product .el-dialog__body){
+ height: 90%;
+ width: 100%;
}
</style>
\ No newline at end of file
--
Gitblit v1.8.0