From 87cc632c03654fcc94594539a6ec54c4281f3ee7 Mon Sep 17 00:00:00 2001
From: yangfan <784310601@qq.com>
Date: Thu, 14 May 2026 11:18:55 +0800
Subject: [PATCH] =?UTF-8?q?=E6=96=B0=E5=A2=9E=E9=A6=96=E9=A1=B5=E8=AF=A6?=
=?UTF-8?q?=E6=83=85=E5=90=88=E8=AE=A1=E9=A1=B5?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
---
src/views/stock/SecondBoardCalendar.vue | 173 +++++++++++++++++-------
1 file changed, 122 insertions(+), 51 deletions(-)
diff --git a/src/views/stock/SecondBoardCalendar.vue b/src/views/stock/SecondBoardCalendar.vue
index 7df0a58..7076513 100644
--- a/src/views/stock/SecondBoardCalendar.vue
+++ b/src/views/stock/SecondBoardCalendar.vue
@@ -77,11 +77,21 @@
炸板
- {{ formatRatio(day.stat.break_next_profit_count, day.stat.break_count) }}
+ {{
+ formatRatio(
+ day.stat.break_next_profit_count,
+ getProfitDataCount(day.stat, "break"),
+ )
+ }}
涨停板
- {{ formatRatio(day.stat.limit_next_profit_count, day.stat.limit_count) }}
+ {{
+ formatRatio(
+ day.stat.limit_next_profit_count,
+ getProfitDataCount(day.stat, "limit"),
+ )
+ }}
@@ -123,7 +133,7 @@
{{
formatRatio(
selectedDayStat?.limit_next_profit_count,
- selectedDayStat?.limit_count,
+ getProfitDataCount(selectedDayStat, "limit"),
)
}}
@@ -132,58 +142,35 @@
{{
formatRatio(
selectedDayStat?.break_next_profit_count,
- selectedDayStat?.break_count,
+ getProfitDataCount(selectedDayStat, "break"),
)
}}
-
-
-
-
-
-
+
+
+
- {{ formatLimitTime(row.first_limit_time) }}
+
+ {{ formatStatus(row.status) }}
+
-
-
- {{ formatOpenTimes(row.open_times) }}
-
-
-
- {{ formatPrice(row.t_high) }}
-
-
- {{ formatPrice(row.t_close) }}
-
-
- {{ formatPrice(row.next_high) }}
-
-
-
- {{ formatProfitFlag(row.next_intraday_profitable) }}
-
-
-
-
- {{ formatSignedRate(row.next_high_profit_pct) }}
-
-
-
-
-
-
@@ -281,6 +268,13 @@ const detailDialogTitle = computed(() => {
const detailStocks = computed(() =>
Array.isArray(selectedDayStat.value?.stocks) ? selectedDayStat.value.stocks : [],
);
+const totalStocks = computed(() => {
+ const stocks = Array.isArray(selectedDayStat.value?.total_stocks)
+ ? selectedDayStat.value.total_stocks
+ : detailStocks.value;
+
+ return sortStocksByLimitTime(stocks);
+});
const limitStocks = computed(() =>
sortStocksByLimitTime(
detailStocks.value.filter((stock) => stock?.status === "limit"),
@@ -291,6 +285,26 @@ const breakStocks = computed(() =>
detailStocks.value.filter((stock) => stock?.status === "break"),
),
);
+const detailTabs = computed(() => [
+ {
+ name: "total",
+ label: "合计",
+ stocks: totalStocks.value,
+ showStatus: true,
+ },
+ {
+ name: "limit",
+ label: "涨停板",
+ stocks: limitStocks.value,
+ showStatus: false,
+ },
+ {
+ name: "break",
+ label: "炸板",
+ stocks: breakStocks.value,
+ showStatus: false,
+ },
+]);
const statMap = computed(() => {
const map = new Map();
@@ -371,7 +385,11 @@ const openDayDetail = (day) => {
if (!day?.stat) return;
selectedDay.value = day;
- activeDetailTab.value = limitStocks.value.length ? "limit" : "break";
+ activeDetailTab.value = totalStocks.value.length
+ ? "total"
+ : limitStocks.value.length
+ ? "limit"
+ : "break";
detailVisible.value = true;
};
@@ -399,11 +417,14 @@ const fetchMonthData = async (withLoading = true) => {
};
const sortStocksByLimitTime = (stocks) =>
- [...stocks].sort(
- (left, right) =>
+ [...stocks].sort((left, right) => {
+ const timeDiff =
getLimitTimeSortValue(left?.first_limit_time) -
- getLimitTimeSortValue(right?.first_limit_time),
- );
+ getLimitTimeSortValue(right?.first_limit_time);
+
+ if (timeDiff !== 0) return timeDiff;
+ return String(left?.ts_code || "").localeCompare(String(right?.ts_code || ""));
+ });
const sortLimitTimeColumn = (left, right) =>
getLimitTimeSortValue(left?.first_limit_time) -
@@ -445,6 +466,14 @@ const formatCount = (value) => {
const formatRatio = (numerator, denominator) =>
`${formatCount(numerator)}/${formatCount(denominator)}`;
+const getProfitDataCount = (stat, type) => {
+ if (!stat) return 0;
+
+ const nextDataKey = type === "break" ? "break_next_data_count" : "limit_next_data_count";
+ const fallbackKey = type === "break" ? "break_count" : "limit_count";
+ return stat[nextDataKey] ?? stat[fallbackKey];
+};
+
const formatPrice = (value) => {
if (value === null || value === undefined || value === "") return "--";
@@ -466,6 +495,12 @@ const formatProfitFlag = (value) => {
return "--";
};
+const formatStatus = (value) => {
+ if (value === "limit") return "封板";
+ if (value === "break") return "炸板";
+ return "--";
+};
+
const formatLimitTime = (value) => {
if (value === null || value === undefined || value === "") return "--";
return String(value);
@@ -477,6 +512,9 @@ const formatOpenTimes = (value) => {
const number = Number(value);
return Number.isFinite(number) ? number : "--";
};
+
+const getStockRowClassName = ({ row }) =>
+ row?.status === "break" ? "break-stock-row" : "";