From a3c508233dd94b50c8005ec3a5d40b91341d6434 Mon Sep 17 00:00:00 2001
From: spring <2396852758@qq.com>
Date: 星期四, 29 一月 2026 17:58:30 +0800
Subject: [PATCH] Merge branch 'dev_New' of http://114.132.189.42:9002/r/product-inventory-management into dev_New

---
 src/views/reportAnalysis/financialAnalysis/components/left-bottom.vue |  264 ++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 264 insertions(+), 0 deletions(-)

diff --git a/src/views/reportAnalysis/financialAnalysis/components/left-bottom.vue b/src/views/reportAnalysis/financialAnalysis/components/left-bottom.vue
new file mode 100644
index 0000000..7aa8c4e
--- /dev/null
+++ b/src/views/reportAnalysis/financialAnalysis/components/left-bottom.vue
@@ -0,0 +1,264 @@
+<template>
+  <div>
+    <PanelHeader title="鏋勬垚鍒嗘瀽" />
+    <div class="main-panel panel-item-customers">
+      <div class="filters-row">
+        <ProductTypeSwitch
+          v-model="amountType"
+          :options="amountTypeOptions"
+          @change="handleTypeChange"
+        />
+      </div>
+      <!-- <CarouselCards :items="cardItems" :visible-count="3" /> -->
+      <div class="pie-chart-wrapper">
+        <div class="pie-background"></div>
+        <Echarts
+          ref="chart"
+          :chartStyle="chartStyle"
+          :legend="landLegend"
+          :series="landSeries"
+          :tooltip="landTooltip"
+          :color="landColors"
+          :options="pieOptions"
+          style="height: 320px"
+          class="land-chart"
+        />
+      </div>
+    </div>
+  </div>
+</template>
+
+<script setup>
+import { ref, onMounted, computed } from 'vue'
+import Echarts from '@/components/Echarts/echarts.vue'
+import PanelHeader from './PanelHeader.vue'
+import ProductTypeSwitch from './ProductTypeSwitch.vue'
+import { rawMaterialPurchaseAmountRatio } from '@/api/viewIndex.js'
+
+/**
+ * @introduction 鎶婃暟缁勪腑key鍊肩浉鍚岀殑閭d竴椤规彁鍙栧嚭鏉ワ紝缁勬垚涓�涓璞�
+ * @param {鍙傛暟绫诲瀷} array 浼犲叆鐨勬暟缁� [{a:"1",b:"2"},{a:"2",b:"3"}]
+ * @param {鍙傛暟绫诲瀷} key  灞炴�у悕 a
+ * @return {杩斿洖绫诲瀷璇存槑}
+ */
+function array2obj(array, key) {
+  const resObj = {}
+  for (let i = 0; i < array.length; i++) {
+    resObj[array[i][key]] = array[i]
+  }
+  return resObj
+}
+
+// 褰撳墠绫诲瀷锛�1=鏀嚭 2=鏀跺叆
+const amountType = ref(1)
+
+const amountTypeOptions = [
+  { label: 1, text: '鏀嚭' },
+  { label: 2, text: '鏀跺叆' },
+]
+
+// 鏁版嵁鍒楄〃锛堟潵鑷帴鍙o級
+const dataList = ref([])
+
+// 鍗$墖鏁版嵁
+const cardItems = ref([])
+
+// 棰滆壊鍒楄〃
+const landColors = ['#26FFCB', '#24CBFF', '#35FBF4', '#2651FF', '#D1E4F5', '#5782F7', '#2F67EF', '#82BAFF']
+
+const landObjData = computed(() => array2obj(dataList.value, 'name'))
+
+// 鍥句緥閰嶇疆锛堝彸渚х珫鎺掞級
+const landLegend = computed(() => {
+  const data = dataList.value.map((d, idx) => ({
+    name: d.name,
+    icon: 'circle',
+    textStyle: {
+      fontSize: 18,
+      color: landColors[idx % landColors.length],
+    },
+  }))
+
+  return {
+    orient: 'vertical',
+    top: 'center',
+    left: '52%',
+    itemGap: 30,
+    show: true,
+    data: data,
+    formatter: function (name) {
+      const item = landObjData.value[name]
+      if (!item) return name
+      return `{title|${name}}{value|${item.value}}{unit|鍏儅{percent|${item.rate}}{unit|%}`
+    },
+    textStyle: {
+      rich: {
+        value: {
+          color: '#43e8fc',
+          fontSize: 14,
+          fontWeight: 600,
+          padding: [0, 0, 0, 10],
+        },
+        unit: {
+          color: '#82baff',
+          fontSize: 12,
+          fontWeight: 600,
+          padding: [0, 10, 0, 0],
+        },
+        percent: {
+          color: '#43e8fc',
+          fontSize: 14,
+          fontWeight: 600,
+          padding: [0, 0, 0, 0],
+        },
+        title: {
+          fontSize: 12,
+          padding: [0, 0, 0, 0],
+        },
+      },
+    },
+  }
+})
+
+// 鎻愮ず妗�
+const landTooltip = {
+  trigger: 'item',
+  formatter: '{a} <br/>{b} : {c}鍏� ({d}%)',
+}
+
+// 鍙屽眰鐜舰楗煎浘
+// 鍙屽眰鐜舰楗煎浘
+const landSeries = ref([
+  {
+    name: '鏋勬垚鍒嗘瀽',
+    type: 'pie',
+    radius: ['40%', '60%'],
+    center: ['25%', '50%'],
+    itemStyle: {
+      borderColor: '#0a1c3a',
+      borderWidth: 2,
+      color: function (params) {
+        return landColors[params.dataIndex % landColors.length]
+      },
+    },
+    label: {
+      show: false
+    },
+    minAngle: 15,
+    data: dataList.value,
+    animationType: 'scale',
+    animationEasing: 'elasticOut',
+    animationDelay: function () {
+      return Math.random() * 200
+    },
+  },
+  {
+    // 鍐呭湀
+    type: 'pie',
+    radius: ['40%', '45%'],
+    center: ['25%', '50%'],
+    silent: true,
+    label: {
+      show: false,
+    },
+    labelLine: {
+      show: false,
+    },
+    itemStyle: {
+      color: 'rgba(0, 127, 255, 0.25)',
+    },
+    data: [1],
+  },
+])
+
+const chartStyle = {
+  width: '100%',
+  height: '100%',
+}
+
+const pieOptions = {
+  backgroundColor: 'transparent',
+  textStyle: { color: '#B8C8E0' },
+}
+
+const fetchData = () => {
+  // 鐩墠鎺ュ彛鍙湁鏀嚭鏋勬垚鍗犳瘮锛屽厛蹇界暐绫诲瀷鍙傛暟
+  // 棰勭暀鎵╁睍锛氬悗缁彲鏍规嵁 amountType 鍒囦笉鍚屾帴鍙�
+  rawMaterialPurchaseAmountRatio()
+    .then((res) => {
+      if (res.code === 200 && Array.isArray(res.data)) {
+        const items = res.data
+        cardItems.value = items.map((item) => ({
+          label: item.name,
+          value: item.value,
+          unit: '鍏�',
+          rate: item.rate,
+        }))
+        dataList.value = items.map((it) => ({
+          name: it.name,
+          value: parseFloat(it.value) || 0,
+          rate: it.rate,
+          children: [],
+        }))
+        landSeries.value[0].data = dataList.value
+      }
+    })
+    .catch((err) => {
+      console.error('鑾峰彇鍘熸潗鏂欓噰璐噾棰濆崰姣斿け璐�:', err)
+    })
+}
+
+const handleTypeChange = () => {
+  fetchData()
+}
+
+onMounted(() => {
+  fetchData()
+})
+</script>
+
+<style scoped>
+.main-panel {
+  display: flex;
+  flex-direction: column;
+  gap: 20px;
+}
+
+.filters-row {
+  display: flex;
+  justify-content: flex-end;
+  align-items: center;
+  gap: 12px;
+  margin-bottom: 10px;
+}
+
+.panel-item-customers {
+  border: 1px solid #1a58b0;
+  padding: 18px;
+  width: 100%;
+  height: 449px;
+}
+
+.pie-chart-wrapper {
+  position: relative;
+  width: 100%;
+  height: 320px;
+  background: transparent;
+}
+
+
+.pie-background {
+  position: absolute;
+  left: 25%;
+  top: 50%;
+  transform: translate(-51.5%, -50%);
+  width: 310px;
+  height: 310px;
+  background-image: url('@/assets/BI/鐜懓鍥捐竟妗�.png');
+  background-size: contain;
+  background-position: center;
+  background-repeat: no-repeat;
+  z-index: 1;
+  pointer-events: none;
+}
+</style>

--
Gitblit v1.9.3