Quellcode durchsuchen

Revert "11111"

This reverts commit 9c2526bc874e18ab675815b3526c4effafbf0764.
Hexinkui vor 3 Wochen
Ursprung
Commit
d0668dd2fd

Datei-Diff unterdrückt, da er zu groß ist
+ 152 - 241
package-lock.json


+ 1 - 1
package.json

@@ -10,7 +10,7 @@
     "amfe-flexible": "^2.2.1",
     "axios": "^1.13.2",
     "html2canvas": "^1.4.1",
-    "klinecharts": "^9.7.1",
+    "klinecharts": "^8.6.3",
     "postcss-pxtorem": "^6.1.0",
     "vant": "^4.9.21",
     "vue": "^3.2.13",

+ 7 - 7
src/views/bitcoin/lever/CryptocurrencyTrading.vue

@@ -1,12 +1,12 @@
-<template>
-  <div class="trade-page">
-    <h2>BTC/USDT 永续</h2>
-  </div>
-</template>
-
 <script setup>
+
 </script>
 
-<style>
+<template>
+  <div style="margin-top: 60px">开发中</div>
+
+</template>
+
+<style scoped lang="less">
 
 </style>

+ 2 - 2
src/views/bitcoin/lever/TradeSeconds.vue

@@ -63,7 +63,7 @@
     <!-- 这里的 chart-wrapper 负责控制 padding 和高度 -->
     <div class="chart-wrapper">
       <!-- 引入封装好的组件,只需传数据和高度 -->
-      <TradeChart
+      <KlineChart
         :data="kLineData"
         height="100%"
       />
@@ -83,7 +83,7 @@ import ChooseThisCycle from './components/ChooseThisCycle.vue'
 import sellOrder from '@/views/bitcoin/components/sellOrder.vue'
 
 // 1. 引入新封装的组件 (请确保路径正确)
-import TradeChart from '@/views/bitcoin/lever/components/TradeChart.vue'
+import KlineChart from '@/views/bitcoin/lever/components/KLineChart.vue'
 
 const route = useRoute()
 const symbolTitle = ref(route.params.id || 'BTCUSDT')

+ 133 - 0
src/views/bitcoin/lever/components/KLineChart.vue

@@ -0,0 +1,133 @@
+<template>
+  <div class="kline-wrapper" :style="{ height: height }">
+    <div ref="chartContainer" class="kline-chart"></div>
+  </div>
+</template>
+
+<script setup>
+import { onMounted, onBeforeUnmount, ref, watch, nextTick, toRaw } from 'vue'
+import * as klinecharts from 'klinecharts'
+
+const props = defineProps({
+  data: { type: Array, default: () => [] },
+  height: { type: String, default: '100%' },
+  precision: { type: Object, default: () => ({ price: 2, volume: 2 }) },
+  colors: {
+    type: Object,
+    default: () => ({
+      up: '#2EBD85',
+      down: '#F6465D',
+      grid: '#F2F4F6',
+      text: '#929AA5',
+      targetLine: '#4A6EF5'
+    })
+  }
+})
+
+const chartContainer = ref(null)
+let chartInstance = null
+
+const initChart = () => {
+  if (!chartContainer.value) return
+  if (chartInstance) klinecharts.dispose(chartContainer.value)
+
+  chartInstance = klinecharts.init(chartContainer.value)
+
+  // 设置精度
+  const { price, volume } = props.precision
+  if (chartInstance.setPriceVolumePrecision) {
+    chartInstance.setPriceVolumePrecision(price, volume)
+  } else if (chartInstance.setPrecision) {
+    chartInstance.setPrecision(price, volume)
+  }
+
+  // 样式配置
+  const { up, down, grid, text, targetLine } = props.colors
+  chartInstance.setStyleOptions({
+    grid: { show: true, horizontal: { show: true, size: 1, color: grid, style: 'dash', dashValue: [5, 5] }, vertical: { show: false } },
+    candle: {
+      type: 'candle_solid',
+      bar: { upColor: up, downColor: down, noChangeColor: up },
+      priceMark: {
+        show: true,
+        last: { show: true, upColor: up, downColor: down, line: { show: true, style: 'dash' }, text: { show: true, color: '#FFF', paddingLeft: 4, paddingRight: 4, borderRadius: 2 } }
+      },
+      tooltip: { showRule: 'follow_cross', showType: 'rect', dataSource: 'none' }
+    },
+    xAxis: { axisLine: { show: false }, tickLine: { show: false }, tickText: { color: text, size: 10, paddingTop: 8 } },
+    yAxis: { inside: true, axisLine: { show: false }, tickLine: { show: false }, tickText: { color: text, size: 10, paddingLeft: 8 } },
+  })
+
+  chartInstance.createTechnicalIndicator('VOL', false, { id: 'pane_1', heightRatio: 0.2 })
+
+  // 初始加载
+  if (props.data && props.data.length > 0) {
+    chartInstance.applyNewData(toRaw(props.data))
+  }
+}
+
+// --- 🔥 核心修复:智能判断是“更新”还是“重置” ---
+watch(() => props.data, (newData) => {
+  if (!chartInstance) return
+
+  const rawData = toRaw(newData)
+  const currentList = chartInstance.getDataList()
+
+  // 1. 如果新数据为空,清空图表
+  if (rawData.length === 0) {
+    chartInstance.clearData()
+    return
+  }
+
+  // 2. 如果当前图表为空,直接加载
+  if (currentList.length === 0) {
+    chartInstance.applyNewData(rawData)
+    return
+  }
+
+  // 3. 🔥 关键判断:
+  // 如果第一根 K 线的时间戳变了,说明切换了周期或币种 -> 全量重置
+  const firstOld = currentList[0]
+  const firstNew = rawData[0]
+  if (firstOld.timestamp !== firstNew.timestamp) {
+    chartInstance.applyNewData(rawData)
+    return
+  }
+
+  // 4. 如果第一根时间没变,说明是实时跳动或追加 -> 增量更新
+  if (rawData.length > 0) {
+    const lastData = rawData[rawData.length - 1]
+    chartInstance.updateData(lastData)
+  }
+}, { deep: true })
+
+// 监听精度
+watch(() => props.precision, (val) => {
+  if (chartInstance) {
+    if (chartInstance.setPriceVolumePrecision) chartInstance.setPriceVolumePrecision(val.price, val.volume)
+    else if (chartInstance.setPrecision) chartInstance.setPrecision(val.price, val.volume)
+  }
+}, { deep: true })
+
+onMounted(() => {
+  nextTick(() => initChart())
+  window.addEventListener('resize', handleResize)
+})
+
+onBeforeUnmount(() => {
+  window.removeEventListener('resize', handleResize)
+  if (chartInstance) {
+    klinecharts.dispose(chartContainer.value)
+    chartInstance = null
+  }
+})
+
+const handleResize = () => {
+  if (chartInstance) chartInstance.resize()
+}
+</script>
+
+<style scoped>
+.kline-wrapper { width: 100%; position: relative; }
+.kline-chart { width: 100%; height: 100%; }
+</style>

Einige Dateien werden nicht angezeigt, da zu viele Dateien in diesem Diff geändert wurden.