添加水温分析菜单
This commit is contained in:
parent
be3936d1bd
commit
1b4f036c6e
@ -13,6 +13,10 @@
|
||||
"@ant-design/icons-vue": "^7.0.1",
|
||||
"@element-plus/icons-vue": "^2.0.10",
|
||||
"@types/js-cookie": "^3.0.2",
|
||||
"@univerjs-pro/exchange-client": "0.15.0",
|
||||
"@univerjs/core": "0.14.0",
|
||||
"@univerjs/preset-sheets-core": "^0.14.0",
|
||||
"@univerjs/presets": "^0.14.0",
|
||||
"@vueuse/core": "^9.1.1",
|
||||
"@wangeditor/editor": "^5.0.0",
|
||||
"@wangeditor/editor-for-vue": "^5.1.10",
|
||||
@ -27,6 +31,7 @@
|
||||
"element-plus": "^2.2.27",
|
||||
"esri-leaflet": "^3.0.19",
|
||||
"exceljs": "^4.4.0",
|
||||
"file-saver": "^2.0.5",
|
||||
"js-base64": "^3.7.5",
|
||||
"js-cookie": "^3.0.1",
|
||||
"jsencrypt": "^3.3.2",
|
||||
@ -40,6 +45,8 @@
|
||||
"path-to-regexp": "^6.2.0",
|
||||
"pdfjs-dist": "^6.0.227",
|
||||
"pinia": "^2.0.12",
|
||||
"react": "18",
|
||||
"react-dom": "18",
|
||||
"screenfull": "^6.0.0",
|
||||
"sortablejs": "^1.14.0",
|
||||
"video.js": "^8.23.7",
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@ -159,6 +159,31 @@ export function getSurfaceTempMonthList(data) {
|
||||
data
|
||||
});
|
||||
}
|
||||
// 表层水温 - 数据分析 - 断面
|
||||
export function getSurfaceTempAnalysisList(data) {
|
||||
return request({
|
||||
url: '/wt/msstbprpt/eng/GetKendoList',
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
}
|
||||
// 表层水温 - 数据分析 - excel
|
||||
export function getSurfaceTempAnalysisExcel(data) {
|
||||
return request({
|
||||
url: '/wt/wtrvAmend/dayAmend/GetKendoListCust',
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
}
|
||||
// 表层水温 - 数据分析 - 保存
|
||||
export function saveSurfaceTempAnalysisExcel(data) {
|
||||
return request({
|
||||
url: '/wt/wtrvAmend/dayAmend/saveAmendData',
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
}
|
||||
|
||||
// 过鱼设施名称 - 断面
|
||||
export function getFishReleaseMonitorSectionList(data) {
|
||||
return request({
|
||||
|
||||
@ -17,6 +17,14 @@ export function getSelectForDropdown(data: any) {
|
||||
data
|
||||
});
|
||||
}
|
||||
// 所在河段下拉列表
|
||||
export function getRvcdDropdown(params: any) {
|
||||
return request({
|
||||
url: '/env/rvcd/selectForDropdown',
|
||||
method: 'get',
|
||||
params: params
|
||||
});
|
||||
}
|
||||
//电站下拉列表
|
||||
export function getEngInfoDropdown(data: any) {
|
||||
return request({
|
||||
@ -25,6 +33,22 @@ export function getEngInfoDropdown(data: any) {
|
||||
data
|
||||
});
|
||||
}
|
||||
// 根据id获取电站信息
|
||||
export function getEngInfoById(params: any) {
|
||||
return request({
|
||||
url: '/env/engInfo/getById',
|
||||
method: 'get',
|
||||
params
|
||||
});
|
||||
}
|
||||
// 所在位置下拉列表
|
||||
export function getAddvcdDropdown(data: any) {
|
||||
return request({
|
||||
url: '/env/addvcd/selectForDropdown',
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
}
|
||||
// 重新验证并更新行数据
|
||||
export function revalidateAndUpdateRow(data: any) {
|
||||
return request({
|
||||
|
||||
@ -2,7 +2,7 @@ import request from '@/utils/request';
|
||||
// 顶部tabs
|
||||
export function baseMsstbprpt(data: any) {
|
||||
return request({
|
||||
url: '/api/dec-lygk-base-server/base/msstbprpt/GetKendoList',
|
||||
url: '/vd/msstbprpt/GetKendoList',
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
@ -10,7 +10,7 @@ export function baseMsstbprpt(data: any) {
|
||||
// 实时视频
|
||||
export function envVdTreeGetKendoListCust(data: any) {
|
||||
return request({
|
||||
url: '/api/wmp-env-server/env/vd/tree/GetKendoListCust',
|
||||
url: '/vd/tree/GetKendoListCust',
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
@ -18,7 +18,7 @@ export function envVdTreeGetKendoListCust(data: any) {
|
||||
// 录像
|
||||
export function envVdRunDataGetKendoList(data: any) {
|
||||
return request({
|
||||
url: '/api/wmp-env-server/env/vd/runData/GetKendoListCust',
|
||||
url: '/vd/runData/GetKendoListCust',
|
||||
method: 'post',
|
||||
data
|
||||
});
|
||||
|
||||
@ -38,7 +38,7 @@
|
||||
|
||||
<script setup lang="ts">
|
||||
import { ref, computed, onMounted, watch, nextTick, h, useSlots } from 'vue';
|
||||
import { message } from 'ant-design-vue';
|
||||
import { message, Tooltip } from 'ant-design-vue';
|
||||
import { calcTableScrollY } from '@/utils/index';
|
||||
import { exportTable as exportTableUtil } from '@/utils/exportExcel';
|
||||
|
||||
@ -222,7 +222,7 @@ const getList = async (filter?: Record<string, any>) => {
|
||||
let finalTotal = 0;
|
||||
|
||||
if (props.transformData) {
|
||||
const result:any = props.transformData(res);
|
||||
const result: any = props.transformData(res);
|
||||
finalRecords = result.records || result.data || [];
|
||||
finalTotal = result.total || 0;
|
||||
} else {
|
||||
@ -575,7 +575,7 @@ const enhancedColumns = computed(() => {
|
||||
return props.columns.map(col => {
|
||||
const enhancedCol: any = { ...col };
|
||||
|
||||
// 处理 sort 或 sorter: true,统一转为 sorter 并绑定 sortOrder
|
||||
// 处理 sort 或 sorter: true
|
||||
const isSortable = enhancedCol.sort === true || enhancedCol.sorter === true;
|
||||
if (isSortable) {
|
||||
enhancedCol.sorter = true;
|
||||
@ -592,7 +592,6 @@ const enhancedColumns = computed(() => {
|
||||
customCell: createMergeCellHandler(col)
|
||||
};
|
||||
|
||||
// 如果有 slots.customRender,移除 slots
|
||||
if (enhancedCol.slots?.customRender) {
|
||||
const { slots, ...restCol } = enhancedCol;
|
||||
return {
|
||||
@ -605,26 +604,61 @@ const enhancedColumns = computed(() => {
|
||||
return enhancedCol;
|
||||
}
|
||||
|
||||
// 如果有 slots.customRender,移除 slots(由 bodyCell 处理),保留 dataIndex 用于匹配
|
||||
// 如果有 slots.customRender,移除 slots
|
||||
if (enhancedCol.slots?.customRender) {
|
||||
const { slots, ...restCol } = enhancedCol;
|
||||
return {
|
||||
...restCol,
|
||||
// 保留 slotName 供 bodyCell 模板匹配使用
|
||||
_slotName: slots.customRender,
|
||||
...(props.enableEllipsis ? { ellipsis: true } : {})
|
||||
};
|
||||
}
|
||||
|
||||
// 如果已有 customRender 函数,直接返回
|
||||
if (enhancedCol.customRender) {
|
||||
// ✅ 修改:为需要 ellipsis 的列添加 customRender,使用 Tooltip
|
||||
if (props.enableEllipsis && !enhancedCol.customRender) {
|
||||
return {
|
||||
...enhancedCol,
|
||||
...(props.enableEllipsis && !enhancedCol.ellipsis ? { ellipsis: true } : {})
|
||||
ellipsis: true,
|
||||
customRender: ({ text }: { text: any }) => {
|
||||
// 如果 text 是空值,直接返回占位符
|
||||
if (text === null || text === undefined || text === '') {
|
||||
return props.emptyPlaceholder;
|
||||
}
|
||||
// 使用 h 函数创建 Tooltip
|
||||
return h(
|
||||
'div',
|
||||
{
|
||||
style: {
|
||||
overflow: 'hidden',
|
||||
textOverflow: 'ellipsis',
|
||||
whiteSpace: 'nowrap'
|
||||
}
|
||||
},
|
||||
h(
|
||||
Tooltip,
|
||||
{
|
||||
title: String(text)
|
||||
},
|
||||
{
|
||||
default: () => String(text)
|
||||
}
|
||||
)
|
||||
);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
// 普通列,添加 ellipsis
|
||||
// 如果已有 customRender 函数,但需要添加 ellipsis
|
||||
if (enhancedCol.customRender) {
|
||||
return {
|
||||
...enhancedCol,
|
||||
...(props.enableEllipsis && !enhancedCol.ellipsis
|
||||
? { ellipsis: true }
|
||||
: {})
|
||||
};
|
||||
}
|
||||
|
||||
// 普通列
|
||||
if (!props.enableEllipsis) return enhancedCol;
|
||||
|
||||
return {
|
||||
@ -633,7 +667,6 @@ const enhancedColumns = computed(() => {
|
||||
};
|
||||
});
|
||||
});
|
||||
|
||||
onMounted(() => {
|
||||
nextTick(() => {
|
||||
tableScrollY.value = calcTableScrollY(tableContainerRef.value);
|
||||
@ -681,7 +714,7 @@ watch(
|
||||
// 行点击高亮样式(仅当 enableRowHighlight 为 true 时生效)
|
||||
::v-deep(.ant-table-tbody > tr.row-clicked > td) {
|
||||
background-color: v-bind(
|
||||
'props.enableRowHighlight ? "#e6f7ff" : "transparent"'
|
||||
'props.enableRowHighlight ? "#e6f7ff" : "#ffffff"'
|
||||
) !important;
|
||||
}
|
||||
|
||||
|
||||
@ -101,12 +101,14 @@ interface Props {
|
||||
hycdList: any[];
|
||||
topHynmLoading: boolean;
|
||||
hycdLoading: boolean;
|
||||
dvtpList: any[];
|
||||
}
|
||||
const props = withDefaults(defineProps<Props>(), {
|
||||
topHynmList: () => [],
|
||||
hycdList: () => [],
|
||||
topHynmLoading: false,
|
||||
hycdLoading: false
|
||||
hycdLoading: false,
|
||||
dvtpList: () => []
|
||||
});
|
||||
|
||||
const basicSearchRef = ref<any>();
|
||||
@ -120,11 +122,7 @@ const jcdt = ref({
|
||||
min: null,
|
||||
max: null
|
||||
});
|
||||
const dvtpList = ref<any[]>([
|
||||
{ label: '堤坝式', value: '0' },
|
||||
{ label: '引水式', value: '1' },
|
||||
{ label: '混合式', value: '2' }
|
||||
]);
|
||||
|
||||
const dvtp = ref([]);
|
||||
const initSearchData = {
|
||||
rvcd: 'all',
|
||||
@ -134,7 +132,12 @@ const initSearchData = {
|
||||
baseId: null,
|
||||
hbrvcd: null,
|
||||
bldsttCcode: null,
|
||||
dtin: 'all'
|
||||
dtin: 'all',
|
||||
jcdt: {
|
||||
min: null,
|
||||
max: null
|
||||
},
|
||||
dvtp: []
|
||||
};
|
||||
const isHide = ref<boolean>(false);
|
||||
const searchData = ref<any>({ ...initSearchData });
|
||||
@ -260,11 +263,13 @@ const disabledEndDate = (current: Dayjs) => {
|
||||
|
||||
const onSearchFinish = (values: any) => {
|
||||
values.ttpwr = ttpwr.value;
|
||||
if (jcdt.value.min)
|
||||
if (jcdt.value?.min) {
|
||||
values.jcdt.min = dayjs(jcdt.value.min).format('YYYY-MM-DD') + ' 00:00:00';
|
||||
if (jcdt.value.max)
|
||||
}
|
||||
if (jcdt.value?.max) {
|
||||
values.jcdt.max = dayjs(jcdt.value.max).format('YYYY-MM-DD') + ' 00:00:00';
|
||||
values.dvtp = dvtp.value;
|
||||
}
|
||||
if (dvtp.value.length > 0) values.dvtp = dvtp.value;
|
||||
emit('search-finish', { ...values });
|
||||
};
|
||||
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
<template>
|
||||
<!-- 第一步:输入数据来源 -->
|
||||
<!-- 第一步:输入修改依据 -->
|
||||
<a-modal
|
||||
v-model:open="dataSourceVisible"
|
||||
title="删除电站"
|
||||
@ -8,12 +8,11 @@
|
||||
@ok="handleDataSourceConfirm"
|
||||
>
|
||||
<div>
|
||||
<p style="color: red; margin-bottom: 8px;">
|
||||
请输入数据来源以继续删除操作
|
||||
</p>
|
||||
<a-input
|
||||
<p style="color: red; margin-bottom: 8px">请输入修改依据以继续删除操作</p>
|
||||
<a-textarea
|
||||
v-model:value="dataSource"
|
||||
placeholder="请输入数据来源"
|
||||
placeholder="请输入修改依据"
|
||||
:rows="4"
|
||||
/>
|
||||
</div>
|
||||
</a-modal>
|
||||
@ -28,11 +27,9 @@
|
||||
@ok="handleFinalDelete"
|
||||
>
|
||||
<div>
|
||||
<p style="color: red; font-weight: bold;">
|
||||
请慎重操作!此操作不可恢复!
|
||||
</p>
|
||||
<p style="color: red; font-weight: bold">请慎重操作!</p>
|
||||
<p>电站名称:{{ deleteRecord?.stnm }}</p>
|
||||
<p>数据来源:{{ dataSource }}</p>
|
||||
<p>修改依据:{{ dataSource || '无' }}</p>
|
||||
<p>确定要删除该电站吗?</p>
|
||||
</div>
|
||||
</a-modal>
|
||||
@ -59,12 +56,8 @@ const open = (record: any, callback: Function) => {
|
||||
onSuccess.value = callback;
|
||||
};
|
||||
|
||||
// 数据来源确认
|
||||
// 修改依据确认
|
||||
const handleDataSourceConfirm = () => {
|
||||
if (!dataSource.value || dataSource.value.trim() === '') {
|
||||
message.error('请输入数据来源');
|
||||
return;
|
||||
}
|
||||
dataSourceVisible.value = false;
|
||||
confirmVisible.value = true;
|
||||
};
|
||||
@ -72,8 +65,13 @@ const handleDataSourceConfirm = () => {
|
||||
// 最终删除
|
||||
const handleFinalDelete = async () => {
|
||||
try {
|
||||
const res = await deletePowerInfo({ stcd: deleteRecord.value.stcd });
|
||||
if (res?.code === 200 || res?.success) {
|
||||
const params = {
|
||||
ids: [deleteRecord.value.stcd],
|
||||
source: dataSource.value
|
||||
};
|
||||
const res = await deletePowerInfo(params);
|
||||
console.log(res);
|
||||
if (res?.code == 0) {
|
||||
message.success('删除成功');
|
||||
confirmVisible.value = false;
|
||||
onSuccess.value();
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@ -6,6 +6,7 @@
|
||||
:hycdList="hycdList"
|
||||
:topHynmLoading="topHynmLoading"
|
||||
:hycdLoading="hycdLoading"
|
||||
:dvtpList="dvtpList"
|
||||
@export-btn="exportBtn"
|
||||
@custom-filter-btn="customFilterBtn"
|
||||
@search-finish="onSearchFinish"
|
||||
@ -16,9 +17,13 @@
|
||||
<!-- 表格组件 -->
|
||||
<BasicTable
|
||||
ref="tableRef"
|
||||
:enableEllipsis="true"
|
||||
:scrollX="tableScrollX"
|
||||
:scrollY="tableScrollY"
|
||||
:columns="columns"
|
||||
:searchParams="{
|
||||
sort: sort
|
||||
}"
|
||||
:list-url="getPowerTableList"
|
||||
>
|
||||
<template #action="{ record }">
|
||||
@ -51,6 +56,7 @@
|
||||
<!-- 编辑电站 Modal -->
|
||||
<EditPowerModal
|
||||
v-model:open="editVisible"
|
||||
:dvtp-list="dvtpList"
|
||||
:record="editRecord"
|
||||
:top-hynm-list="topHynmList"
|
||||
:hycd-list="hycdList"
|
||||
@ -75,12 +81,32 @@ import {
|
||||
updatePowerInfo,
|
||||
deletePowerInfo
|
||||
} from '@/api/DataQueryMenuModule';
|
||||
import { getEngInfoById } from '@/api/select';
|
||||
import { calcTableScrollY } from '@/utils/index';
|
||||
import { useModelStore } from '@/store/modules/model';
|
||||
import { BasicColumns } from '@/components/MapModal/column.config';
|
||||
|
||||
const modelStore = useModelStore();
|
||||
|
||||
const sort = ref<any>([
|
||||
{
|
||||
field: 'baseStepSort',
|
||||
dir: 'asc'
|
||||
},
|
||||
{
|
||||
field: 'rvcdStepSort',
|
||||
dir: 'asc'
|
||||
},
|
||||
{
|
||||
field: 'rstcdStepSort',
|
||||
dir: 'asc'
|
||||
},
|
||||
{
|
||||
field: 'ttpwr',
|
||||
dir: 'asc'
|
||||
}
|
||||
]);
|
||||
|
||||
const tableRef = ref();
|
||||
const searchRef = ref();
|
||||
const tableScrollY = ref<string | number>(0);
|
||||
@ -101,6 +127,11 @@ const hycdLoading = ref(false);
|
||||
|
||||
const isEdit = ref(true);
|
||||
|
||||
const dvtpList = ref<any[]>([
|
||||
{ label: '堤坝式', value: '0' },
|
||||
{ label: '引水式', value: '1' },
|
||||
{ label: '混合式', value: '2' }
|
||||
]);
|
||||
const columns = ref<any[]>([
|
||||
{
|
||||
key: 'stnm',
|
||||
@ -165,7 +196,7 @@ const columns = ref<any[]>([
|
||||
title: '第一台机组投产时间',
|
||||
dataIndex: 'piodt',
|
||||
visible: true,
|
||||
width: 150,
|
||||
width: 160,
|
||||
sort: true,
|
||||
ellipsis: true,
|
||||
customRender: ({ text }) => {
|
||||
@ -221,8 +252,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'nrupar',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'dstcrvr',
|
||||
@ -230,26 +260,23 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'dstcrvr',
|
||||
visible: true,
|
||||
width: 150,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avyrp',
|
||||
title: '多年平均降雨量(mm)',
|
||||
dataIndex: 'avyrp',
|
||||
visible: true,
|
||||
width: 160,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 170,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avw',
|
||||
title: '多年平均年径流量(亿m³)',
|
||||
dataIndex: 'avw',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 190,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avq',
|
||||
@ -257,8 +284,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'avq',
|
||||
visible: true,
|
||||
width: 160,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avq01',
|
||||
@ -266,8 +292,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'avq01',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avq02',
|
||||
@ -275,8 +300,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'avq02',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avq03',
|
||||
@ -284,8 +308,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'avq03',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avq04',
|
||||
@ -293,8 +316,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'avq04',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avq05',
|
||||
@ -302,8 +324,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'avq05',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avq06',
|
||||
@ -311,8 +332,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'avq06',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avq07',
|
||||
@ -320,8 +340,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'avq07',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avq08',
|
||||
@ -329,8 +348,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'avq08',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avq09',
|
||||
@ -338,35 +356,31 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'avq09',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avq10',
|
||||
title: '10月多年平均流量(m³/s)',
|
||||
dataIndex: 'avq10',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 190,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avq11',
|
||||
title: '11月多年平均流量(m³/s)',
|
||||
dataIndex: 'avq11',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 190,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avq12',
|
||||
title: '12月多年平均流量(m³/s)',
|
||||
dataIndex: 'avq12',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 190,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'obmxq',
|
||||
@ -374,8 +388,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'obmxq',
|
||||
visible: true,
|
||||
width: 170,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'obmnq',
|
||||
@ -383,26 +396,23 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'obmnq',
|
||||
visible: true,
|
||||
width: 170,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'hmxq',
|
||||
title: '调查历史最大流量(m³/s)',
|
||||
dataIndex: 'hmxq',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 190,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'dsnfqfrq',
|
||||
title: '设计入库洪水流量(m³/s)',
|
||||
dataIndex: 'dsnfqfrq',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 190,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'dsrcin',
|
||||
@ -410,17 +420,15 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'dsrcin',
|
||||
visible: true,
|
||||
width: 160,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'ckfqfqr',
|
||||
title: '校核入库洪水流量(m³/s)',
|
||||
dataIndex: 'ckfqfqr',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 190,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'chrcin',
|
||||
@ -428,61 +436,54 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'chrcin',
|
||||
visible: true,
|
||||
width: 160,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'obmxw3',
|
||||
title: '实测最大洪量(三天)(亿m³)',
|
||||
dataIndex: 'obmxw3',
|
||||
visible: true,
|
||||
width: 200,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 220,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'dsw3',
|
||||
title: '设计洪量(三天)(亿m³)',
|
||||
dataIndex: 'dsw3',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 190,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'ckw3',
|
||||
title: '校核洪量(三天)(亿m³)',
|
||||
dataIndex: 'ckw3',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 190,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'avsd',
|
||||
title: '多年平均输沙量(万t)',
|
||||
dataIndex: 'avsd',
|
||||
visible: true,
|
||||
width: 170,
|
||||
ellipsis: true
|
||||
width: 180
|
||||
},
|
||||
{
|
||||
key: 'avs',
|
||||
title: '多年平均含沙量(kg/m³)',
|
||||
dataIndex: 'avs',
|
||||
visible: true,
|
||||
width: 170,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 180,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'obmxs',
|
||||
title: '实测最大含沙量(kg/m³)',
|
||||
dataIndex: 'obmxs',
|
||||
visible: true,
|
||||
width: 170,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 180,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'ckflz',
|
||||
@ -490,8 +491,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'ckflz',
|
||||
visible: true,
|
||||
width: 140,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'dsflz',
|
||||
@ -499,8 +499,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'dsflz',
|
||||
visible: true,
|
||||
width: 140,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'normz',
|
||||
@ -508,8 +507,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'normz',
|
||||
visible: true,
|
||||
width: 140,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'uzfc',
|
||||
@ -517,8 +515,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'uzfc',
|
||||
visible: true,
|
||||
width: 140,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'fsltdz',
|
||||
@ -526,8 +523,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'fsltdz',
|
||||
visible: true,
|
||||
width: 150,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'ydownz',
|
||||
@ -535,8 +531,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'ydownz',
|
||||
visible: true,
|
||||
width: 140,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'ddz',
|
||||
@ -544,17 +539,15 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'ddz',
|
||||
visible: true,
|
||||
width: 120,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'nrzar',
|
||||
title: '正常蓄水位水库面积(km²)',
|
||||
dataIndex: 'nrzar',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 200,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'bcklen',
|
||||
@ -562,8 +555,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'bcklen',
|
||||
visible: true,
|
||||
width: 130,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'ttcp',
|
||||
@ -571,17 +563,15 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'ttcp',
|
||||
visible: true,
|
||||
width: 130,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'nmzcp',
|
||||
title: '正常蓄水位以下库容(亿m³)',
|
||||
dataIndex: 'nmzcp',
|
||||
visible: true,
|
||||
width: 190,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 200,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'fldcpStr',
|
||||
@ -589,8 +579,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'fldcpStr',
|
||||
visible: true,
|
||||
width: 140,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'actcp',
|
||||
@ -598,8 +587,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'actcp',
|
||||
visible: true,
|
||||
width: 140,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'ddcp',
|
||||
@ -607,8 +595,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'ddcp',
|
||||
visible: true,
|
||||
width: 130,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'cpsc',
|
||||
@ -616,8 +603,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'cpsc',
|
||||
visible: true,
|
||||
width: 120,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'rgcpName',
|
||||
@ -634,17 +620,15 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'dsflzmxq',
|
||||
visible: true,
|
||||
width: 250,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'dsflzxyz',
|
||||
title: '设计洪水位时最大下泄流量相应下游水位(m)',
|
||||
dataIndex: 'dsflzxyz',
|
||||
visible: true,
|
||||
width: 300,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 320,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'ckflzmxq',
|
||||
@ -652,17 +636,15 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'ckflzmxq',
|
||||
visible: true,
|
||||
width: 250,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'ckflzxyz',
|
||||
title: '校核洪水位时最大下泄流量相应下游水位(m)',
|
||||
dataIndex: 'ckflzxyz',
|
||||
visible: true,
|
||||
width: 300,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 320,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'ksqadjq',
|
||||
@ -670,8 +652,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'ksqadjq',
|
||||
visible: true,
|
||||
width: 170,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'ksqxyz',
|
||||
@ -679,17 +660,15 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'ksqxyz',
|
||||
visible: true,
|
||||
width: 250,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'gemaxrq',
|
||||
title: '发电最大引用流量(m³/s)',
|
||||
dataIndex: 'gemaxrq',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
width: 190,
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'mxgeqxyz',
|
||||
@ -697,8 +676,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'mxgeqxyz',
|
||||
visible: true,
|
||||
width: 260,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'ttpwr',
|
||||
@ -742,8 +720,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'yrge',
|
||||
visible: true,
|
||||
width: 200,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'ushr',
|
||||
@ -751,15 +728,14 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'ushr',
|
||||
visible: true,
|
||||
width: 150,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'k',
|
||||
title: '机组综合出力系数',
|
||||
dataIndex: 'k',
|
||||
visible: true,
|
||||
width: 140,
|
||||
width: 150,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
},
|
||||
@ -778,8 +754,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'dmcrel',
|
||||
visible: true,
|
||||
width: 130,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'mxdmhg',
|
||||
@ -787,8 +762,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'mxdmhg',
|
||||
visible: true,
|
||||
width: 120,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'dmlen',
|
||||
@ -796,8 +770,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'dmlen',
|
||||
visible: true,
|
||||
width: 130,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'sgyge',
|
||||
@ -805,8 +778,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'sgyge',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'unyge',
|
||||
@ -814,8 +786,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'unyge',
|
||||
visible: true,
|
||||
width: 180,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'gap',
|
||||
@ -823,8 +794,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'gap',
|
||||
visible: true,
|
||||
width: 120,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'dvtpName',
|
||||
@ -832,8 +802,7 @@ const columns = ref<any[]>([
|
||||
dataIndex: 'dvtpName',
|
||||
visible: true,
|
||||
width: 120,
|
||||
sort: true,
|
||||
ellipsis: true
|
||||
sort: true
|
||||
},
|
||||
{
|
||||
key: 'dtinName',
|
||||
@ -926,8 +895,8 @@ const buildSearchParams = (values: any) => {
|
||||
|
||||
values.rstcd
|
||||
? {
|
||||
field: 'rstcd',
|
||||
operator: 'contains',
|
||||
field: 'stcd',
|
||||
operator: 'eq',
|
||||
dataType: 'string',
|
||||
value: values.rstcd
|
||||
}
|
||||
@ -1059,7 +1028,10 @@ const handleDetail = (record: any) => {
|
||||
};
|
||||
// 编辑
|
||||
const handleEdit = (record: any) => {
|
||||
editRecord.value = { ...record };
|
||||
getEngInfoById({ stcd: record.stcd }).then(res => {
|
||||
console.log(res);
|
||||
editRecord.value = { ...res.data };
|
||||
});
|
||||
editVisible.value = true;
|
||||
};
|
||||
|
||||
|
||||
@ -203,7 +203,7 @@ const initCrossSectionList = params => {
|
||||
|
||||
const onValuesChange = (changedValues: any, allValues: any) => {
|
||||
// 当流域或断面变化时,清空过鱼设施选中并重新请求列表
|
||||
if (changedValues.rvcd || changedValues.rstcd !== undefined) {
|
||||
if ('rvcd' in changedValues || 'rstcd' in changedValues) {
|
||||
allValues.stcd = null;
|
||||
if (basicSearchRef.value?.formData) {
|
||||
basicSearchRef.value.formData.stcd = null;
|
||||
|
||||
@ -226,7 +226,7 @@ const initCrossSectionList = params => {
|
||||
|
||||
const onValuesChange = (changedValues: any, allValues: any) => {
|
||||
// 当流域变化时,清空断面选中
|
||||
if (changedValues.rvcd || changedValues.rstcd !== undefined) {
|
||||
if ('rvcd' in changedValues || 'rstcd' in changedValues) {
|
||||
allValues.stcd = null;
|
||||
if (basicSearchRef.value?.formData) {
|
||||
basicSearchRef.value.formData.stcd = null;
|
||||
|
||||
@ -226,7 +226,7 @@ const initCrossSectionList = params => {
|
||||
|
||||
const onValuesChange = (changedValues: any, allValues: any) => {
|
||||
// 当流域变化时,清空断面选中
|
||||
if (changedValues.rvcd || changedValues.rstcd !== undefined) {
|
||||
if ('rvcd' in changedValues || 'rstcd' in changedValues) {
|
||||
allValues.stcd = null;
|
||||
if (basicSearchRef.value?.formData) {
|
||||
basicSearchRef.value.formData.stcd = null;
|
||||
|
||||
@ -232,7 +232,7 @@ const initCrossSectionList = params => {
|
||||
|
||||
const onValuesChange = (changedValues: any, allValues: any) => {
|
||||
// 当流域变化时,清空断面选中
|
||||
if (changedValues.rvcd || changedValues.rstcd !== undefined) {
|
||||
if ('rvcd' in changedValues || 'rstcd' in changedValues) {
|
||||
allValues.stcd = null;
|
||||
if (basicSearchRef.value?.formData) {
|
||||
basicSearchRef.value.formData.stcd = null;
|
||||
|
||||
@ -248,7 +248,7 @@ const initCrossSectionList = params => {
|
||||
|
||||
const onValuesChange = (changedValues: any, allValues: any) => {
|
||||
// 当流域变化时,清空断面选中
|
||||
if (changedValues.rvcd || changedValues.rstcd !== undefined) {
|
||||
if ('rvcd' in changedValues || 'rstcd' in changedValues) {
|
||||
allValues.stcd = null;
|
||||
if (basicSearchRef.value?.formData) {
|
||||
basicSearchRef.value.formData.stcd = null;
|
||||
|
||||
@ -1,5 +1,6 @@
|
||||
<template>
|
||||
<div class="conventionalHydropower-page">
|
||||
<!-- 1. 排序 -->
|
||||
<a-tabs v-model:activeKey="activeTab" class="conventionalHydropower-tabs">
|
||||
<a-tab-pane tab="电站信息" key="BasicData">
|
||||
<BasicData />
|
||||
|
||||
225
frontend/src/views/shuJuFenXi/components/export.js
Normal file
225
frontend/src/views/shuJuFenXi/components/export.js
Normal file
@ -0,0 +1,225 @@
|
||||
import Excel from 'exceljs';
|
||||
import FileSaver from 'file-saver';
|
||||
|
||||
const exportExcel = function (univerData, fileName = 'data') {
|
||||
// 参数为Univer工作簿数据对象
|
||||
const workbook = new Excel.Workbook();
|
||||
|
||||
// 遍历工作簿中的所有工作表
|
||||
const sheetOrder = univerData.sheetOrder || [];
|
||||
sheetOrder.forEach(sheetId => {
|
||||
const sheet = univerData.sheets[sheetId];
|
||||
if (!sheet || !sheet.cellData) return;
|
||||
|
||||
const worksheet = workbook.addWorksheet(sheet.name || 'Sheet1');
|
||||
|
||||
// 处理单元格数据
|
||||
setCellsData(sheet.cellData, worksheet, univerData.styles || {});
|
||||
|
||||
// 设置合并单元格
|
||||
if (sheet.mergeData) {
|
||||
setMerge(sheet.mergeData, worksheet);
|
||||
}
|
||||
|
||||
// 设置行高
|
||||
if (sheet.rowData) {
|
||||
setRowHeight(sheet.rowData, worksheet);
|
||||
}
|
||||
|
||||
// 设置列宽
|
||||
if (sheet.columnData) {
|
||||
setColumnWidth(sheet.columnData, worksheet);
|
||||
}
|
||||
|
||||
// 设置冻结行列
|
||||
if (sheet.freeze) {
|
||||
setFreeze(sheet.freeze, worksheet);
|
||||
}
|
||||
});
|
||||
|
||||
// 写入 buffer
|
||||
const buffer = workbook.xlsx.writeBuffer().then(data => {
|
||||
const blob = new Blob([data], {
|
||||
type: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet;charset=utf-8'
|
||||
});
|
||||
console.log('导出成功!');
|
||||
FileSaver.saveAs(blob, `${fileName}.xlsx`);
|
||||
});
|
||||
|
||||
return buffer;
|
||||
};
|
||||
|
||||
// 设置单元格数据
|
||||
var setCellsData = function (cellData, worksheet, styles = {}) {
|
||||
for (let row in cellData) {
|
||||
const rowData = cellData[row];
|
||||
for (let col in rowData) {
|
||||
const cell = rowData[col];
|
||||
if (!cell) continue;
|
||||
|
||||
const excelRow = parseInt(row) + 1;
|
||||
const excelCol = parseInt(col) + 1;
|
||||
const targetCell = worksheet.getCell(excelRow, excelCol);
|
||||
|
||||
// 设置值
|
||||
if (cell.f) {
|
||||
// 如果是公式
|
||||
targetCell.value = { formula: cell.f, result: cell.v };
|
||||
} else if (cell.v !== undefined) {
|
||||
// 如果是普通值
|
||||
targetCell.value = cell.v;
|
||||
}
|
||||
|
||||
// 如果有样式ID,应用样式
|
||||
if (cell.s && styles[cell.s]) {
|
||||
const cellStyle = styles[cell.s];
|
||||
applyCellStyle(targetCell, cellStyle);
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// 应用单元格样式
|
||||
var applyCellStyle = function (targetCell, cellStyle) {
|
||||
// 应用字体样式
|
||||
if (cellStyle.ff) {
|
||||
targetCell.font = targetCell.font || {};
|
||||
targetCell.font.name = cellStyle.ff;
|
||||
}
|
||||
|
||||
if (cellStyle.fs) {
|
||||
targetCell.font = targetCell.font || {};
|
||||
targetCell.font.size = cellStyle.fs;
|
||||
}
|
||||
|
||||
if (cellStyle.bl === 1) {
|
||||
targetCell.font = targetCell.font || {};
|
||||
targetCell.font.bold = true;
|
||||
}
|
||||
|
||||
if (cellStyle.it === 1) {
|
||||
targetCell.font = targetCell.font || {};
|
||||
targetCell.font.italic = true;
|
||||
}
|
||||
|
||||
// 应用背景色
|
||||
if (cellStyle.bg && cellStyle.bg.rgb) {
|
||||
targetCell.fill = {
|
||||
type: 'pattern',
|
||||
pattern: 'solid',
|
||||
fgColor: { argb: cellStyle.bg.rgb.replace('#', '') }
|
||||
};
|
||||
}
|
||||
|
||||
// 应用字体颜色
|
||||
if (cellStyle.cl && cellStyle.cl.rgb) {
|
||||
targetCell.font = targetCell.font || {};
|
||||
targetCell.font.color = { argb: cellStyle.cl.rgb.replace('#', '') };
|
||||
}
|
||||
|
||||
// 应用水平对齐
|
||||
if (cellStyle.ht !== undefined) {
|
||||
targetCell.alignment = targetCell.alignment || {};
|
||||
if (cellStyle.ht === 1) targetCell.alignment.horizontal = 'left';
|
||||
else if (cellStyle.ht === 2) targetCell.alignment.horizontal = 'center';
|
||||
else if (cellStyle.ht === 3) targetCell.alignment.horizontal = 'right';
|
||||
}
|
||||
|
||||
// 应用垂直对齐
|
||||
if (cellStyle.vt !== undefined) {
|
||||
targetCell.alignment = targetCell.alignment || {};
|
||||
if (cellStyle.vt === 1) targetCell.alignment.vertical = 'top';
|
||||
else if (cellStyle.vt === 2) targetCell.alignment.vertical = 'middle';
|
||||
else if (cellStyle.vt === 3) targetCell.alignment.vertical = 'bottom';
|
||||
}
|
||||
|
||||
// 应用文本换行
|
||||
if (cellStyle.tb !== undefined) {
|
||||
targetCell.alignment = targetCell.alignment || {};
|
||||
targetCell.alignment.wrapText = cellStyle.tb === 1;
|
||||
}
|
||||
|
||||
// 应用文本旋转
|
||||
if (cellStyle.tr !== undefined) {
|
||||
targetCell.alignment = targetCell.alignment || {};
|
||||
targetCell.alignment.textRotation = cellStyle.tr;
|
||||
}
|
||||
|
||||
// 应用边框(如果有的话)
|
||||
if (cellStyle.bd) {
|
||||
// 这里可以处理边框样式
|
||||
// 具体实现根据实际边框数据结构
|
||||
}
|
||||
};
|
||||
|
||||
// 设置合并单元格
|
||||
var setMerge = function (mergeData = [], worksheet) {
|
||||
mergeData.forEach(function (merge) {
|
||||
worksheet.mergeCells(
|
||||
merge.startRow + 1, // Excel行号从1开始
|
||||
merge.startColumn + 1, // Excel列号从1开始
|
||||
merge.endRow + 1,
|
||||
merge.endColumn + 1
|
||||
);
|
||||
});
|
||||
};
|
||||
|
||||
// 设置行高
|
||||
var setRowHeight = function (rowData = {}, worksheet) {
|
||||
for (let rowIndex in rowData) {
|
||||
const rowInfo = rowData[rowIndex];
|
||||
if (rowInfo.h) {
|
||||
const excelRowNum = parseInt(rowIndex) + 1;
|
||||
// 转换像素到Excel行高单位 (1像素 ≈ 0.75 Excel行高单位)
|
||||
const excelHeight = rowInfo.h * 0.75;
|
||||
worksheet.getRow(excelRowNum).height = excelHeight;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// 设置列宽
|
||||
var setColumnWidth = function (columnData = {}, worksheet) {
|
||||
for (let colIndex in columnData) {
|
||||
const colInfo = columnData[colIndex];
|
||||
if (colInfo.w) {
|
||||
const excelColNum = parseInt(colIndex) + 1;
|
||||
// 转换像素到Excel列宽单位 (1像素 ≈ 0.14 Excel列宽单位,粗略估算)
|
||||
const excelWidth = colInfo.w * 0.14;
|
||||
worksheet.getColumn(excelColNum).width = excelWidth;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// 设置冻结行列
|
||||
var setFreeze = function (freeze, worksheet) {
|
||||
if (freeze.startRow > 0 || freeze.startColumn > 0) {
|
||||
// Excel中冻结窗格通过视图设置
|
||||
worksheet.views = [
|
||||
{
|
||||
state: 'frozen',
|
||||
xSplit: freeze.xSplit || freeze.startColumn,
|
||||
ySplit: freeze.ySplit || freeze.startRow,
|
||||
topLeftCell: `${getExcelColumnName(freeze.startColumn + 1)}${freeze.startRow + 1}`
|
||||
}
|
||||
];
|
||||
}
|
||||
};
|
||||
|
||||
// 将数字转换为Excel列名 (A, B, ..., Z, AA, AB, ...)
|
||||
function getExcelColumnName(colNumber) {
|
||||
let columnName = '';
|
||||
let num = colNumber;
|
||||
|
||||
while (num > 0) {
|
||||
num--;
|
||||
const remainder = num % 26;
|
||||
columnName = String.fromCharCode(65 + remainder) + columnName;
|
||||
num = Math.floor(num / 26);
|
||||
}
|
||||
|
||||
return columnName || 'A';
|
||||
}
|
||||
|
||||
export {
|
||||
exportExcel
|
||||
};
|
||||
1011
frontend/src/views/shuJuFenXi/components/utils.ts
Normal file
1011
frontend/src/views/shuJuFenXi/components/utils.ts
Normal file
File diff suppressed because it is too large
Load Diff
@ -1,5 +1,381 @@
|
||||
<template>
|
||||
<div>
|
||||
<h2>水温数据分析</h2>
|
||||
<div class="shuiWenShuJuFenXi-page">
|
||||
<BasicSearch
|
||||
ref="basicSearchRef"
|
||||
:searchList="searchList"
|
||||
:initial-values="initSearchData"
|
||||
:zhujianfujian="'fu'"
|
||||
@reset="handleReset"
|
||||
@finish="onSearchFinish"
|
||||
@values-change="onValuesChange"
|
||||
>
|
||||
<template #actions>
|
||||
<a-button :loading="exportLoading" @click="exportBtn">导出</a-button>
|
||||
<a-button @click="saveBtn">保存</a-button>
|
||||
</template>
|
||||
</BasicSearch>
|
||||
|
||||
<a-spin :spinning="loading">
|
||||
<div
|
||||
ref="containerRef"
|
||||
id="x-spreadsheet-demo"
|
||||
style="width: 100%; height: calc(100vh - 220px)"
|
||||
></div>
|
||||
</a-spin>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script setup lang="ts">
|
||||
import { ref, computed, onMounted, onUnmounted } from 'vue';
|
||||
import { message } from 'ant-design-vue';
|
||||
import {
|
||||
getSurfaceTempAnalysisList,
|
||||
getSurfaceTempAnalysisExcel,
|
||||
saveSurfaceTempAnalysisExcel
|
||||
} from '@/api/DataQueryMenuModule';
|
||||
import BasicSearch from '@/components/BasicSearch/index.vue';
|
||||
import '@univerjs/preset-sheets-core/lib/index.css';
|
||||
import { exportExcel } from './components/export';
|
||||
import { createExcelInstance, renderDataToExcel } from './components/utils';
|
||||
import dayjs from 'dayjs';
|
||||
|
||||
const basicSearchRef = ref();
|
||||
const stcdData = ref([]);
|
||||
const stcdLoading = ref(false);
|
||||
|
||||
const originalData = ref([]);
|
||||
const initSearchData = {
|
||||
rvcd: 'all',
|
||||
rstcd: null,
|
||||
stcd: '008660306300000079',
|
||||
dt: dayjs().startOf('year').format('YYYY-MM-DD HH:mm:ss')
|
||||
};
|
||||
const searchFinishInfo = ref({});
|
||||
// 加载状态
|
||||
const loading = ref(false);
|
||||
const exportLoading = ref(false);
|
||||
const saveLoading = ref(false);
|
||||
// 容器ref
|
||||
const containerRef = ref();
|
||||
const univerInstanceRef = ref();
|
||||
|
||||
const searchList: any = computed(() => [
|
||||
{
|
||||
type: 'waterStation',
|
||||
name: 'rvcd',
|
||||
label: '流域',
|
||||
placeholder: '请输入流域',
|
||||
fieldProps: {
|
||||
allowClear: true
|
||||
},
|
||||
options: []
|
||||
},
|
||||
{
|
||||
type: 'Select',
|
||||
name: 'stcd',
|
||||
label: '断面',
|
||||
width: 160,
|
||||
fieldProps: {
|
||||
allowClear: false
|
||||
},
|
||||
loading: stcdLoading.value,
|
||||
options: stcdData.value
|
||||
},
|
||||
{
|
||||
type: 'DataPicker',
|
||||
name: 'dt',
|
||||
label: '时间',
|
||||
width: 100,
|
||||
picker: 'year',
|
||||
fieldProps: {
|
||||
format: 'YYYY',
|
||||
valueFormat: 'YYYY-MM-DD HH:mm:ss',
|
||||
allowClear: false
|
||||
}
|
||||
}
|
||||
]);
|
||||
// 导出按钮点击事件
|
||||
const exportBtn = () => {
|
||||
exportLoading.value = true;
|
||||
const { univer, univerAPI } = univerInstanceRef.value;
|
||||
const fWorkbook = univerAPI.getActiveWorkbook();
|
||||
const fWorksheet = fWorkbook.getActiveSheet();
|
||||
const snapshot = fWorkbook.save();
|
||||
const titleRange = fWorksheet.getRange('A1');
|
||||
exportExcel(snapshot, titleRange.getValue() || ' 水温站xxxx年监测数据');
|
||||
setTimeout(() => {
|
||||
message.success('导出成功');
|
||||
exportLoading.value = false;
|
||||
}, 500);
|
||||
};
|
||||
// 保存按钮点击事件
|
||||
const saveBtn = async () => {
|
||||
saveLoading.value = true;
|
||||
if (univerInstanceRef.value) {
|
||||
const { univerAPI } = univerInstanceRef.value;
|
||||
const workbook = univerAPI.getActiveWorkbook();
|
||||
const activeSheet = workbook.getActiveSheet();
|
||||
|
||||
// 获取当前工作表数据
|
||||
const maxRow = activeSheet.getMaxRows();
|
||||
const maxCol = activeSheet.getMaxColumns();
|
||||
|
||||
// 获取所有单元格的值
|
||||
const currentData = [];
|
||||
for (let row = 0; row < maxRow; row++) {
|
||||
const rowData = [];
|
||||
for (let col = 0; col < maxCol; col++) {
|
||||
const cellValue = activeSheet.getRange(row, col).getValue();
|
||||
rowData.push(cellValue);
|
||||
}
|
||||
currentData.push(rowData);
|
||||
}
|
||||
|
||||
// 创建结果数组
|
||||
const resultData = [];
|
||||
|
||||
// 假设年份是根据原始数据中的年份确定的,从原始数据中获取年份
|
||||
let year = '2025'; // 默认年份
|
||||
if (originalData.value && originalData.value.length > 0) {
|
||||
year = originalData.value[0].dt.split('-')[0]; // 从原始数据的第一个元素中提取年份
|
||||
}
|
||||
|
||||
// 遍历月份行 (根据utils.tsx中的initializeExcelWorksheet函数逻辑)
|
||||
for (let month = 1; month <= 12; month++) {
|
||||
const monthRow = (month - 1) * 2 + 3; // 月份名称行(日数据行)
|
||||
const dataRow = monthRow + 1; // 数据行(平均值行)
|
||||
|
||||
if (dataRow >= maxRow) break; // 防止越界
|
||||
|
||||
// 获取月份名称行的值(日数据行)
|
||||
const monthValue = currentData[monthRow - 1][0]; // 月份值在A列(索引0),monthRow是1基索引,所以减1
|
||||
|
||||
// 检查月份值,可能为字符串如"1月"或数字
|
||||
let monthNum = null;
|
||||
if (typeof monthValue === 'string' && monthValue.endsWith('月')) {
|
||||
monthNum = parseInt(monthValue.replace('月', ''));
|
||||
} else if (typeof monthValue === 'number') {
|
||||
monthNum = monthValue;
|
||||
}
|
||||
|
||||
if (monthNum !== null && monthNum >= 1 && monthNum <= 12) {
|
||||
const monthStr = monthNum.toString().padStart(2, '0'); // 格式化月份为两位数
|
||||
|
||||
// 遍历日期列 (从C列开始,即索引2,根据utils.tsx中的逻辑)
|
||||
for (let day = 1; day <= 31; day++) {
|
||||
const dayCol = day + 1; // 日期列索引,day=1对应C列(索引2)
|
||||
if (dayCol >= maxCol) break; // 防止越界
|
||||
|
||||
// 从日数据行(monthRow)获取wt值,而不是从平均值行(dataRow)
|
||||
const wtValue = currentData[monthRow - 1][dayCol]; // 获取wt值,monthRow是1基索引,所以减1
|
||||
|
||||
// 如果wt不为空,则添加到结果数组
|
||||
if (wtValue !== undefined && wtValue !== null && wtValue !== '') {
|
||||
// 使用原始数据的格式创建对象,但wt使用Excel中的新值
|
||||
const newDataItem = {
|
||||
dt: `${year}-${monthStr}-${day.toString().padStart(2, '0')}`, // 生成日期字符串
|
||||
wt: wtValue, // 使用Excel中的新wt值
|
||||
stcd: originalData.value[0]?.stcd || '' // 使用原始数据的第一个元素的字段
|
||||
};
|
||||
|
||||
resultData.push(newDataItem);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 按日期排序
|
||||
resultData.sort(
|
||||
(a, b) => new Date(a.dt).getTime() - new Date(b.dt).getTime()
|
||||
);
|
||||
|
||||
if (resultData.length > 0) {
|
||||
let res = await saveSurfaceTempAnalysisExcel(resultData);
|
||||
if (res.code == 0) {
|
||||
message.success('保存成功');
|
||||
} else {
|
||||
message.error(res.data.msg);
|
||||
}
|
||||
saveLoading.value = false;
|
||||
} else {
|
||||
message.warning(`保存失败,数据为空`);
|
||||
saveLoading.value = false;
|
||||
}
|
||||
}
|
||||
};
|
||||
// 重置按钮点击事件
|
||||
const handleReset = (values: any) => {
|
||||
initData(initSearchData);
|
||||
};
|
||||
// 搜索按钮点击事件
|
||||
const onSearchFinish = (values: any) => {
|
||||
searchFinishInfo.value = values;
|
||||
if (values.stcd == '' || values.stcd == null) {
|
||||
message.warning('请选择断面');
|
||||
return;
|
||||
}
|
||||
initData(values);
|
||||
};
|
||||
// 值变化事件
|
||||
const onValuesChange = (changedValues: any, allValues: any) => {
|
||||
if ('rvcd' in changedValues || 'rstcd' in changedValues) {
|
||||
if (basicSearchRef.value?.formData) {
|
||||
basicSearchRef.value.formData.stcd = null;
|
||||
}
|
||||
initStcd(allValues);
|
||||
}
|
||||
};
|
||||
// 初始化断面数据
|
||||
const initStcd = (values: any) => {
|
||||
stcdLoading.value = true;
|
||||
setTimeout(() => {
|
||||
stcdLoading.value = false;
|
||||
const params = {
|
||||
filter: {
|
||||
logic: 'and',
|
||||
filters: [
|
||||
values.rvcd &&
|
||||
values.rvcd !== 'all' && {
|
||||
field: 'rvcd',
|
||||
operator: 'eq',
|
||||
dataType: 'string',
|
||||
value: values.rvcd
|
||||
},
|
||||
values.rstcd && {
|
||||
field: 'rstcd',
|
||||
operator: 'eq',
|
||||
dataType: 'string',
|
||||
value: values.rstcd
|
||||
},
|
||||
{
|
||||
field: 'sttpFullPath',
|
||||
operator: 'contains',
|
||||
dataType: 'string',
|
||||
value: 'ENV,ENVM,WT,WTRV'
|
||||
}
|
||||
].filter(Boolean)
|
||||
},
|
||||
select: ['stcd', 'stnm', 'wtDeviceType', 'dtinType', 'mway']
|
||||
};
|
||||
getSurfaceTempAnalysisList(params).then(res => {
|
||||
stcdData.value = res.data?.data?.map(item => ({
|
||||
label: item.stnm,
|
||||
value: item.stcd
|
||||
}));
|
||||
stcdLoading.value = false;
|
||||
});
|
||||
}, 1000);
|
||||
};
|
||||
// 初始化数据
|
||||
const initData = async (values: any) => {
|
||||
loading.value = true;
|
||||
const params = {
|
||||
filter: {
|
||||
logic: 'and',
|
||||
filters: [
|
||||
{
|
||||
field: 'stcd',
|
||||
operator: 'eq',
|
||||
dataType: 'string',
|
||||
value: values.stcd
|
||||
},
|
||||
{
|
||||
field: 'dt',
|
||||
operator: 'gte',
|
||||
dataType: 'date',
|
||||
value: dayjs(values.dt).startOf('year').format('YYYY-MM-DD HH:mm:ss')
|
||||
},
|
||||
{
|
||||
field: 'dt',
|
||||
operator: 'lte',
|
||||
dataType: 'date',
|
||||
value: dayjs(values.dt).endOf('year').format('YYYY-MM-DD HH:mm:ss')
|
||||
}
|
||||
]
|
||||
},
|
||||
sort: [
|
||||
{
|
||||
field: 'baseStepSort',
|
||||
dir: 'asc'
|
||||
},
|
||||
{
|
||||
field: 'rvcd',
|
||||
dir: 'asc'
|
||||
},
|
||||
{
|
||||
field: 'rstcdStepSort',
|
||||
dir: 'asc'
|
||||
},
|
||||
{
|
||||
field: 'stnm',
|
||||
dir: 'asc'
|
||||
},
|
||||
{
|
||||
field: 'dt',
|
||||
dir: 'desc'
|
||||
}
|
||||
],
|
||||
skip: 0,
|
||||
take: 1000
|
||||
};
|
||||
getSurfaceTempAnalysisExcel(params).then(res => {
|
||||
if (!univerInstanceRef.value) {
|
||||
console.error('Univer 实例尚未初始化,请稍后再试');
|
||||
loading.value = false;
|
||||
return;
|
||||
}
|
||||
originalData.value = res.data?.data;
|
||||
const label =
|
||||
stcdData.value.find(item => item.value === values.stcd)?.label || '';
|
||||
const year = dayjs(values.dt).year();
|
||||
|
||||
const { univerAPI } = univerInstanceRef.value;
|
||||
|
||||
const fWorkbook = univerAPI.getActiveWorkbook();
|
||||
const fWorksheet = fWorkbook.getActiveSheet();
|
||||
|
||||
// 设置标题行(第1行,A到AE列,即A1:AE1)
|
||||
const titleRange = fWorksheet.getRange('A1');
|
||||
if (titleRange) {
|
||||
titleRange.setValue(`${label}${year}年监测数据`);
|
||||
}
|
||||
if (res.data.data.length == 0) {
|
||||
message.warning(`当前${label}${year}年暂无数据`);
|
||||
loading.value = false;
|
||||
}
|
||||
univerAPI.year = year;
|
||||
for (let i = 0; i < res.data.data.length; i++) {
|
||||
res.data.data[i].wt = Number(res.data.data[i].wt).toFixed(1);
|
||||
}
|
||||
renderDataToExcel(res.data.data, univerAPI, year, loading);
|
||||
loading.value = false;
|
||||
});
|
||||
};
|
||||
onMounted(() => {
|
||||
// 创建Excel实例
|
||||
const { univer, univerAPI } = createExcelInstance(containerRef.value);
|
||||
// 保存 univer 实例到 ref
|
||||
univerInstanceRef.value = { univer, univerAPI };
|
||||
initStcd(initSearchData);
|
||||
initData(initSearchData);
|
||||
});
|
||||
onUnmounted(() => {
|
||||
// 销毁Excel实例
|
||||
const { univer, univerAPI } = univerInstanceRef.value;
|
||||
univerAPI.dispose();
|
||||
});
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.shuiWenShuJuFenXi-page {
|
||||
position: relative;
|
||||
z-index: 900;
|
||||
pointer-events: all;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
background-color: #ffffff;
|
||||
box-sizing: border-box;
|
||||
overflow: hidden;
|
||||
padding: 20px;
|
||||
}
|
||||
</style>
|
||||
|
||||
Loading…
Reference in New Issue
Block a user