|  |  | 
 |  |  |           /> | 
 |  |  |         </el-card> | 
 |  |  |       </el-tab-pane> | 
 |  |  |  | 
 |  |  |       <!-- 指标统计(多维度销售分析) --> | 
 |  |  |       <el-tab-pane label="指标统计" name="indicatorStats"> | 
 |  |  |         <el-card class="box-card"> | 
 |  |  |           <!-- KPI 汇总 --> | 
 |  |  |           <el-row :gutter="20" class="stats-row"> | 
 |  |  |             <el-col :span="6"> | 
 |  |  |               <div class="stat-card"> | 
 |  |  |                 <div class="stat-icon" style="background: #ecf5ff;"> | 
 |  |  |                   <el-icon :size="30" color="#409eff"><Document /></el-icon> | 
 |  |  |                 </div> | 
 |  |  |                 <div class="stat-content"> | 
 |  |  |                   <div class="stat-value">{{ indicatorKpis.orderCount.toLocaleString() }}</div> | 
 |  |  |                   <div class="stat-label">订单数量</div> | 
 |  |  |                 </div> | 
 |  |  |               </div> | 
 |  |  |             </el-col> | 
 |  |  |             <el-col :span="6"> | 
 |  |  |               <div class="stat-card"> | 
 |  |  |                 <div class="stat-icon" style="background: #f0f9ff;"> | 
 |  |  |                   <el-icon :size="30" color="#67c23a"><Tickets /></el-icon> | 
 |  |  |                 </div> | 
 |  |  |                 <div class="stat-content"> | 
 |  |  |                   <div class="stat-value">¥{{ indicatorKpis.salesAmount.toLocaleString() }}</div> | 
 |  |  |                   <div class="stat-label">销售额</div> | 
 |  |  |                 </div> | 
 |  |  |               </div> | 
 |  |  |             </el-col> | 
 |  |  |             <el-col :span="6"> | 
 |  |  |               <div class="stat-card"> | 
 |  |  |                 <div class="stat-icon" style="background: #fef0f0;"> | 
 |  |  |                   <el-icon :size="30" color="#e6a23c"><Van /></el-icon> | 
 |  |  |                 </div> | 
 |  |  |                 <div class="stat-content"> | 
 |  |  |                   <div class="stat-value">{{ indicatorKpis.shipmentRate }}%</div> | 
 |  |  |                   <div class="stat-label">发货率</div> | 
 |  |  |                 </div> | 
 |  |  |               </div> | 
 |  |  |             </el-col> | 
 |  |  |             <el-col :span="6"> | 
 |  |  |               <div class="stat-card"> | 
 |  |  |                 <div class="stat-icon" style="background: #f4f4f5;"> | 
 |  |  |                   <el-icon :size="30" color="#f56c6c"><Wallet /></el-icon> | 
 |  |  |                 </div> | 
 |  |  |                 <div class="stat-content"> | 
 |  |  |                   <div class="stat-value">{{ indicatorKpis.collectionRate }}%</div> | 
 |  |  |                   <div class="stat-label">回款率</div> | 
 |  |  |                 </div> | 
 |  |  |               </div> | 
 |  |  |             </el-col> | 
 |  |  |           </el-row> | 
 |  |  |  | 
 |  |  |           <!-- 维度筛选 --> | 
 |  |  |           <el-row :gutter="20" class="search-row"> | 
 |  |  |             <el-col :span="6"> | 
 |  |  |               <el-select v-model="indicatorFilter.product" placeholder="产品" clearable> | 
 |  |  |                 <el-option label="全部产品" value="" /> | 
 |  |  |                 <el-option label="P.O 42.5普通硅酸盐水泥" value="P.O 42.5普通硅酸盐水泥" /> | 
 |  |  |                 <el-option label="P.S 32.5矿渣硅酸盐水泥" value="P.S 32.5矿渣硅酸盐水泥" /> | 
 |  |  |                 <el-option label="P.C 32.5复合硅酸盐水泥" value="P.C 32.5复合硅酸盐水泥" /> | 
 |  |  |               </el-select> | 
 |  |  |             </el-col> | 
 |  |  |             <el-col :span="6"> | 
 |  |  |               <el-select v-model="indicatorFilter.customer" placeholder="客户" clearable> | 
 |  |  |                 <el-option label="全部客户" value="" /> | 
 |  |  |                 <el-option label="华东建材集团" value="华东建材集团" /> | 
 |  |  |                 <el-option label="长江混凝土公司" value="长江混凝土公司" /> | 
 |  |  |                 <el-option label="浦江水泥制品厂" value="浦江水泥制品厂" /> | 
 |  |  |               </el-select> | 
 |  |  |             </el-col> | 
 |  |  |             <el-col :span="6"> | 
 |  |  |               <el-select v-model="indicatorFilter.region" placeholder="区域" clearable> | 
 |  |  |                 <el-option label="全部区域" value="" /> | 
 |  |  |                 <el-option label="华东地区" value="华东地区" /> | 
 |  |  |                 <el-option label="华南地区" value="华南地区" /> | 
 |  |  |                 <el-option label="华北地区" value="华北地区" /> | 
 |  |  |               </el-select> | 
 |  |  |             </el-col> | 
 |  |  |             <el-col :span="6"> | 
 |  |  |               <el-date-picker v-model="indicatorFilter.dateRange" type="daterange" range-separator="至" | 
 |  |  |                               start-placeholder="开始日期" end-placeholder="结束日期" value-format="YYYY-MM-DD" style="width: 100%" /> | 
 |  |  |             </el-col> | 
 |  |  |             <el-col :span="24" style="text-align: right; margin-top: 10px;"> | 
 |  |  |               <el-button type="primary" @click="applyIndicatorFilter">查询</el-button> | 
 |  |  |               <el-button @click="resetIndicatorFilter">重置</el-button> | 
 |  |  |               <el-button @click="exportIndicatorTable">导出报表</el-button> | 
 |  |  |               <el-button @click="exportIndicatorChart">导出图表</el-button> | 
 |  |  |             </el-col> | 
 |  |  |           </el-row> | 
 |  |  |  | 
 |  |  |           <!-- 图表区 --> | 
 |  |  |           <div class="chart-container"> | 
 |  |  |             <div ref="indicatorChartRef" style="width: 100%; height: 360px;"></div> | 
 |  |  |           </div> | 
 |  |  |  | 
 |  |  |           <!-- 业绩统计(团队维度,无个人姓名) --> | 
 |  |  |           <el-table :data="teamPerformanceList" border stripe style="margin-top: 20px;"> | 
 |  |  |             <el-table-column prop="team" label="销售团队" width="140" /> | 
 |  |  |             <el-table-column prop="orderCount" label="订单数" width="100" /> | 
 |  |  |             <el-table-column prop="salesAmount" label="销售额" width="140"> | 
 |  |  |               <template #default="scope">¥{{ scope.row.salesAmount.toLocaleString() }}</template> | 
 |  |  |             </el-table-column> | 
 |  |  |             <el-table-column prop="shipmentRate" label="发货率" width="100"> | 
 |  |  |               <template #default="scope">{{ scope.row.shipmentRate }}%</template> | 
 |  |  |             </el-table-column> | 
 |  |  |             <el-table-column prop="collectionRate" label="回款率" width="100"> | 
 |  |  |               <template #default="scope">{{ scope.row.collectionRate }}%</template> | 
 |  |  |             </el-table-column> | 
 |  |  |             <el-table-column prop="attainment" label="目标达成率" width="120"> | 
 |  |  |               <template #default="scope"> | 
 |  |  |                 <el-tag :type="scope.row.attainment >= 100 ? 'success' : scope.row.attainment >= 80 ? 'warning' : 'danger'"> | 
 |  |  |                   {{ scope.row.attainment }}% | 
 |  |  |                 </el-tag> | 
 |  |  |               </template> | 
 |  |  |             </el-table-column> | 
 |  |  |           </el-table> | 
 |  |  |         </el-card> | 
 |  |  |       </el-tab-pane> | 
 |  |  |     </el-tabs> | 
 |  |  |  | 
 |  |  |     <!-- 价格策略对话框 --> | 
 |  |  | 
 |  |  |         <el-row :gutter="20"> | 
 |  |  |           <el-col :span="12"> | 
 |  |  |             <el-form-item label="策略类型" prop="strategyType"> | 
 |  |  |               <el-select v-model="priceStrategyForm.strategyType" placeholder="请选择策略类型" style="width: 100%;"> | 
 |  |  |               <el-select v-model="priceStrategyForm.strategyType" placeholder="请选择策略类型" style="width: 100%;" :disabled="priceStrategyDialogMode === 'view'"> | 
 |  |  |                 <el-option label="专属价格" value="专属价格"></el-option> | 
 |  |  |                 <el-option label="阶梯报价" value="阶梯报价"></el-option> | 
 |  |  |                 <el-option label="促销折扣" value="促销折扣"></el-option> | 
 |  |  | 
 |  |  |           </el-col> | 
 |  |  |           <el-col :span="12"> | 
 |  |  |             <el-form-item label="客户名称" prop="customerName"> | 
 |  |  |               <el-select v-model="priceStrategyForm.customerName" placeholder="请选择客户" style="width: 100%;"> | 
 |  |  |               <el-select v-model="priceStrategyForm.customerName" placeholder="请选择客户" style="width: 100%;" :disabled="priceStrategyDialogMode === 'view'"> | 
 |  |  |                 <el-option label="华东建材集团" value="华东建材集团"></el-option> | 
 |  |  |                 <el-option label="长江混凝土公司" value="长江混凝土公司"></el-option> | 
 |  |  |                 <el-option label="浦江水泥制品厂" value="浦江水泥制品厂"></el-option> | 
 |  |  | 
 |  |  |         <el-row :gutter="20"> | 
 |  |  |           <el-col :span="12"> | 
 |  |  |             <el-form-item label="产品名称" prop="productName"> | 
 |  |  |               <el-select v-model="priceStrategyForm.productName" placeholder="请选择产品" style="width: 100%;"> | 
 |  |  |               <el-select v-model="priceStrategyForm.productName" placeholder="请选择产品" style="width: 100%;" :disabled="priceStrategyDialogMode === 'view'"> | 
 |  |  |                 <el-option label="P.O 42.5普通硅酸盐水泥" value="P.O 42.5普通硅酸盐水泥"></el-option> | 
 |  |  |                 <el-option label="P.S 32.5矿渣硅酸盐水泥" value="P.S 32.5矿渣硅酸盐水泥"></el-option> | 
 |  |  |                 <el-option label="P.C 32.5复合硅酸盐水泥" value="P.C 32.5复合硅酸盐水泥"></el-option> | 
 |  |  | 
 |  |  |           </el-col> | 
 |  |  |           <el-col :span="12"> | 
 |  |  |             <el-form-item label="规格型号" prop="specification"> | 
 |  |  |               <el-input v-model="priceStrategyForm.specification" placeholder="请输入规格型号" /> | 
 |  |  |               <el-input v-model="priceStrategyForm.specification" placeholder="请输入规格型号" :disabled="priceStrategyDialogMode === 'view'" /> | 
 |  |  |             </el-form-item> | 
 |  |  |           </el-col> | 
 |  |  |         </el-row> | 
 |  |  |         <el-row :gutter="20"> | 
 |  |  |           <el-col :span="12"> | 
 |  |  |             <el-form-item label="基础价格(元/吨)" prop="basePrice"> | 
 |  |  |               <el-input-number v-model="priceStrategyForm.basePrice" :min="0" :precision="2" style="width: 100%;" /> | 
 |  |  |               <el-input-number v-model="priceStrategyForm.basePrice" :min="0" :precision="2" style="width: 100%;" :disabled="priceStrategyDialogMode === 'view'" /> | 
 |  |  |             </el-form-item> | 
 |  |  |           </el-col> | 
 |  |  |           <el-col :span="12"> | 
 |  |  |             <el-form-item label="策略价格" prop="strategyPrice"> | 
 |  |  |               <el-input v-model="priceStrategyForm.strategyPrice" placeholder="如: ¥350/吨 或 9折" /> | 
 |  |  |               <el-input v-model="priceStrategyForm.strategyPrice" placeholder="如: ¥350/吨 或 9折" :disabled="priceStrategyDialogMode === 'view'" /> | 
 |  |  |             </el-form-item> | 
 |  |  |           </el-col> | 
 |  |  |         </el-row> | 
 |  |  | 
 |  |  |                 placeholder="选择生效日期" | 
 |  |  |                 style="width: 100%" | 
 |  |  |                 value-format="YYYY-MM-DD" | 
 |  |  |                 :disabled="priceStrategyDialogMode === 'view'" | 
 |  |  |               /> | 
 |  |  |             </el-form-item> | 
 |  |  |           </el-col> | 
 |  |  | 
 |  |  |                 placeholder="选择失效日期" | 
 |  |  |                 style="width: 100%" | 
 |  |  |                 value-format="YYYY-MM-DD" | 
 |  |  |                 :disabled="priceStrategyDialogMode === 'view'" | 
 |  |  |               /> | 
 |  |  |             </el-form-item> | 
 |  |  |           </el-col> | 
 |  |  |         </el-row> | 
 |  |  |         <el-form-item label="策略说明" prop="description"> | 
 |  |  |           <el-input type="textarea" v-model="priceStrategyForm.description" :rows="3" placeholder="请输入策略说明" /> | 
 |  |  |           <el-input type="textarea" v-model="priceStrategyForm.description" :rows="3" placeholder="请输入策略说明" :disabled="priceStrategyDialogMode === 'view'" /> | 
 |  |  |         </el-form-item> | 
 |  |  |       </el-form> | 
 |  |  |       <template #footer> | 
 |  |  |         <el-button @click="priceStrategyDialogVisible = false">取消</el-button> | 
 |  |  |         <el-button type="primary" @click="handleSavePriceStrategy">保存</el-button> | 
 |  |  |         <el-button @click="priceStrategyDialogVisible = false">{{ priceStrategyDialogMode === 'view' ? '关闭' : '取消' }}</el-button> | 
 |  |  |         <el-button v-if="priceStrategyDialogMode !== 'view'" type="primary" @click="handleSavePriceStrategy">保存</el-button> | 
 |  |  |       </template> | 
 |  |  |     </el-dialog> | 
 |  |  |   </div> | 
 |  |  | 
 |  |  |  | 
 |  |  | const priceStrategyDialogVisible = ref(false) | 
 |  |  | const priceStrategyDialogTitle = ref('新增价格策略') | 
 |  |  | const priceStrategyDialogMode = ref('add') // add | edit | view | 
 |  |  | const priceStrategyForm = reactive({ | 
 |  |  |   strategyType: '', | 
 |  |  |   customerName: '', | 
 |  |  | 
 |  |  | const handleAddPriceStrategy = () => { | 
 |  |  |   priceStrategyDialogTitle.value = '新增价格策略' | 
 |  |  |   resetPriceStrategyForm() | 
 |  |  |   priceStrategyDialogMode.value = 'add' | 
 |  |  |   priceStrategyDialogVisible.value = true | 
 |  |  | } | 
 |  |  |  | 
 |  |  | const handleViewPriceStrategy = (row) => { | 
 |  |  |   ElMessage.info('查看策略详情: ' + row.strategyNo) | 
 |  |  |   priceStrategyDialogTitle.value = '查看价格策略' | 
 |  |  |   Object.assign(priceStrategyForm, row) | 
 |  |  |   priceStrategyDialogMode.value = 'view' | 
 |  |  |   priceStrategyDialogVisible.value = true | 
 |  |  | } | 
 |  |  |  | 
 |  |  | const handleEditPriceStrategy = (row) => { | 
 |  |  |   priceStrategyDialogTitle.value = '编辑价格策略' | 
 |  |  |   Object.assign(priceStrategyForm, row) | 
 |  |  |   priceStrategyDialogMode.value = 'edit' | 
 |  |  |   priceStrategyDialogVisible.value = true | 
 |  |  | } | 
 |  |  |  | 
 |  |  | 
 |  |  |     cancelButtonText: '取消', | 
 |  |  |     type: 'warning' | 
 |  |  |   }).then(() => { | 
 |  |  |     // 本地假数据删除:从列表中移除并更新总数 | 
 |  |  |     const index = priceStrategyList.value.findIndex(item => item.id === row.id) | 
 |  |  |     if (index > -1) { | 
 |  |  |       priceStrategyList.value.splice(index, 1) | 
 |  |  |       if (pricePagination.total > 0) pricePagination.total -= 1 | 
 |  |  |     } | 
 |  |  |     ElMessage.success('删除成功') | 
 |  |  |   }) | 
 |  |  | } | 
 |  |  | 
 |  |  |   profitPagination.pageSize = val.limit | 
 |  |  | } | 
 |  |  |  | 
 |  |  | // ========== 指标统计(多维度分析) ========== | 
 |  |  | const indicatorKpis = reactive({ | 
 |  |  |   orderCount: 1280, | 
 |  |  |   salesAmount: 9650000, | 
 |  |  |   shipmentRate: 89.2, | 
 |  |  |   collectionRate: 76.4 | 
 |  |  | }) | 
 |  |  |  | 
 |  |  | const indicatorFilter = reactive({ | 
 |  |  |   product: '', | 
 |  |  |   customer: '', | 
 |  |  |   region: '', | 
 |  |  |   dateRange: [] | 
 |  |  | }) | 
 |  |  |  | 
 |  |  | const indicatorChartRef = ref(null) | 
 |  |  | let indicatorChart = null | 
 |  |  |  | 
 |  |  | const teamPerformanceList = ref([ | 
 |  |  |   { team: '华东团队A', orderCount: 320, salesAmount: 2850000, shipmentRate: 90, collectionRate: 80, attainment: 105 }, | 
 |  |  |   { team: '华北团队B', orderCount: 280, salesAmount: 2150000, shipmentRate: 86, collectionRate: 73, attainment: 92 }, | 
 |  |  |   { team: '华南团队C', orderCount: 210, salesAmount: 1850000, shipmentRate: 88, collectionRate: 70, attainment: 78 }, | 
 |  |  |   { team: '西南团队D', orderCount: 180, salesAmount: 1500000, shipmentRate: 83, collectionRate: 68, attainment: 74 } | 
 |  |  | ]) | 
 |  |  |  | 
 |  |  | const initIndicatorChart = () => { | 
 |  |  |   if (!indicatorChartRef.value) return | 
 |  |  |   if (indicatorChart) indicatorChart.dispose() | 
 |  |  |   indicatorChart = echarts.init(indicatorChartRef.value) | 
 |  |  |   const option = { | 
 |  |  |     title: { text: '多维度销售指标趋势', left: 'center' }, | 
 |  |  |     tooltip: { trigger: 'axis' }, | 
 |  |  |     legend: { data: ['订单数', '销售额', '发货率', '回款率'], top: 30 }, | 
 |  |  |     grid: { left: '3%', right: '4%', bottom: '3%', containLabel: true }, | 
 |  |  |     xAxis: { type: 'category', data: ['2024-12', '2025-01', '2025-02', '2025-03', '2025-04', '2025-05'] }, | 
 |  |  |     yAxis: [ | 
 |  |  |       { type: 'value', name: '数量/金额', axisLabel: { formatter: '{value}' } }, | 
 |  |  |       { type: 'value', name: '比例(%)', min: 0, max: 100, axisLabel: { formatter: '{value}%' } } | 
 |  |  |     ], | 
 |  |  |     series: [ | 
 |  |  |       { name: '订单数', type: 'bar', data: [180, 220, 210, 260, 205, 225], itemStyle: { color: '#409eff' } }, | 
 |  |  |       { name: '销售额', type: 'bar', data: [820, 950, 910, 1080, 980, 1020], itemStyle: { color: '#67c23a' } }, | 
 |  |  |       { name: '发货率', type: 'line', yAxisIndex: 1, data: [86, 89, 88, 91, 87, 90], itemStyle: { color: '#e6a23c' } }, | 
 |  |  |       { name: '回款率', type: 'line', yAxisIndex: 1, data: [72, 76, 74, 79, 75, 78], itemStyle: { color: '#f56c6c' } } | 
 |  |  |     ] | 
 |  |  |   } | 
 |  |  |   indicatorChart.setOption(option) | 
 |  |  | } | 
 |  |  |  | 
 |  |  | const applyIndicatorFilter = () => { | 
 |  |  |   // 使用假数据模拟查询,刷新KPI和图表 | 
 |  |  |   // 仅演示:随机微调以体现筛选效果 | 
 |  |  |   const random = (base, delta) => { | 
 |  |  |     const v = base + Math.round((Math.random() - 0.5) * delta) | 
 |  |  |     return v < 0 ? 0 : v | 
 |  |  |   } | 
 |  |  |   indicatorKpis.orderCount = random(1280, 120) | 
 |  |  |   indicatorKpis.salesAmount = random(9650000, 350000) | 
 |  |  |   indicatorKpis.shipmentRate = (85 + Math.random() * 10).toFixed(1) * 1 | 
 |  |  |   indicatorKpis.collectionRate = (70 + Math.random() * 12).toFixed(1) * 1 | 
 |  |  |  | 
 |  |  |   setTimeout(() => initIndicatorChart(), 200) | 
 |  |  | } | 
 |  |  |  | 
 |  |  | const resetIndicatorFilter = () => { | 
 |  |  |   indicatorFilter.product = '' | 
 |  |  |   indicatorFilter.customer = '' | 
 |  |  |   indicatorFilter.region = '' | 
 |  |  |   indicatorFilter.dateRange = [] | 
 |  |  |   applyIndicatorFilter() | 
 |  |  | } | 
 |  |  |  | 
 |  |  | const exportIndicatorTable = () => { | 
 |  |  |   // 导出团队业绩为CSV(假导出) | 
 |  |  |   const header = ['销售团队', '订单数', '销售额', '发货率(%)', '回款率(%)', '目标达成率(%)'] | 
 |  |  |   const rows = teamPerformanceList.value.map(r => [ | 
 |  |  |     r.team, | 
 |  |  |     r.orderCount, | 
 |  |  |     r.salesAmount, | 
 |  |  |     r.shipmentRate, | 
 |  |  |     r.collectionRate, | 
 |  |  |     r.attainment | 
 |  |  |   ]) | 
 |  |  |   const csv = [header, ...rows].map(r => r.join(',')).join('\n') | 
 |  |  |   const blob = new Blob([csv], { type: 'text/csv;charset=utf-8;' }) | 
 |  |  |   const url = URL.createObjectURL(blob) | 
 |  |  |   const link = document.createElement('a') | 
 |  |  |   link.href = url | 
 |  |  |   link.download = '指标统计-团队业绩.csv' | 
 |  |  |   document.body.appendChild(link) | 
 |  |  |   link.click() | 
 |  |  |   document.body.removeChild(link) | 
 |  |  |   URL.revokeObjectURL(url) | 
 |  |  | } | 
 |  |  |  | 
 |  |  | const exportIndicatorChart = () => { | 
 |  |  |   if (!indicatorChart) return | 
 |  |  |   const url = indicatorChart.getDataURL({ type: 'png', pixelRatio: 2, backgroundColor: '#fff' }) | 
 |  |  |   const link = document.createElement('a') | 
 |  |  |   link.href = url | 
 |  |  |   link.download = '指标统计-图表.png' | 
 |  |  |   document.body.appendChild(link) | 
 |  |  |   link.click() | 
 |  |  |   document.body.removeChild(link) | 
 |  |  | } | 
 |  |  |  | 
 |  |  | // 生命周期 | 
 |  |  | onMounted(() => { | 
 |  |  |   // 组件挂载后不立即初始化图表,等待用户切换到对应标签页 | 
 |  |  | 
 |  |  |       initPriceChart() | 
 |  |  |     } else if (newVal === 'profitAnalysis') { | 
 |  |  |       initProfitChart() | 
 |  |  |     } else if (newVal === 'indicatorStats') { | 
 |  |  |       initIndicatorChart() | 
 |  |  |     } | 
 |  |  |   }) | 
 |  |  | }) |