diff --git a/src/views/Company/components/CompanyOverview/BasicInfoTab/config.ts b/src/views/Company/components/CompanyOverview/BasicInfoTab/config.ts index d633b3b5..9c2a5260 100644 --- a/src/views/Company/components/CompanyOverview/BasicInfoTab/config.ts +++ b/src/views/Company/components/CompanyOverview/BasicInfoTab/config.ts @@ -30,22 +30,23 @@ export interface Theme { } // 黑金主题配置 +// 注:文字颜色使用更亮的金色(#F4D03F)以提高对比度 export const THEME: Theme = { bg: "gray.900", cardBg: "gray.800", tableBg: "gray.700", tableHoverBg: "gray.600", - gold: "#D4AF37", - goldLight: "#F0D78C", + gold: "#F4D03F", // 亮黄金色(用于文字,对比度更好) + goldLight: "#F0D78C", // 浅金色(用于次要文字) textPrimary: "white", textSecondary: "gray.400", - border: "rgba(212, 175, 55, 0.3)", + border: "rgba(212, 175, 55, 0.3)", // 边框保持原色 tabSelected: { - bg: "#D4AF37", + bg: "#D4AF37", // 选中背景保持深金色 color: "gray.900", }, tabUnselected: { - color: "#D4AF37", + color: "#F4D03F", // 未选中使用亮金色 }, }; diff --git a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/atoms/BusinessTreeItem.tsx b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/atoms/BusinessTreeItem.tsx index 9ed5ad7f..b2366cf4 100644 --- a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/atoms/BusinessTreeItem.tsx +++ b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/atoms/BusinessTreeItem.tsx @@ -11,12 +11,12 @@ import { Box, HStack, VStack, Text, Badge, Tag, TagLabel } from '@chakra-ui/reac import { formatPercentage, formatBusinessRevenue } from '@utils/priceFormatters'; import type { BusinessTreeItemProps } from '../types'; -// 黑金主题配置 +// 黑金主题配置(使用更亮的金色提高对比度) const THEME = { bg: 'gray.700', - gold: '#D4AF37', + gold: '#F4D03F', // 亮金色 goldLight: '#F0D78C', - textPrimary: '#D4AF37', + textPrimary: '#F4D03F', // 亮金色(提高对比度) textSecondary: 'gray.400', border: 'rgba(212, 175, 55, 0.5)', }; diff --git a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/atoms/ProcessNavigation.tsx b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/atoms/ProcessNavigation.tsx index 2c4e6518..8f0af035 100644 --- a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/atoms/ProcessNavigation.tsx +++ b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/atoms/ProcessNavigation.tsx @@ -9,9 +9,9 @@ import React, { memo } from 'react'; import { HStack, VStack, Box, Text, Icon, Badge } from '@chakra-ui/react'; import { FaArrowRight } from 'react-icons/fa'; -// 黑金主题配置 +// 黑金主题配置(使用更亮的金色提高对比度) const THEME = { - gold: '#D4AF37', + gold: '#F4D03F', textSecondary: 'gray.400', upstream: { active: 'orange.500', diff --git a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/atoms/ValueChainFilterBar.tsx b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/atoms/ValueChainFilterBar.tsx index 28f7c1b2..21f4ea3c 100644 --- a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/atoms/ValueChainFilterBar.tsx +++ b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/atoms/ValueChainFilterBar.tsx @@ -13,10 +13,10 @@ import { Tab, } from '@chakra-ui/react'; -// 黑金主题配置 +// 黑金主题配置(使用更亮的金色提高对比度) const THEME = { - gold: '#D4AF37', - textPrimary: '#D4AF37', + gold: '#F4D03F', + textPrimary: '#F4D03F', textSecondary: 'gray.400', inputBg: 'gray.700', inputBorder: 'gray.600', diff --git a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/BusinessSegmentsCard.tsx b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/BusinessSegmentsCard.tsx index 0710117c..501c6578 100644 --- a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/BusinessSegmentsCard.tsx +++ b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/BusinessSegmentsCard.tsx @@ -27,9 +27,9 @@ import type { BusinessSegment } from '../types'; const THEME = { cardBg: 'gray.800', innerCardBg: 'gray.700', - gold: '#D4AF37', + gold: '#F4D03F', goldLight: '#F0D78C', - textPrimary: '#D4AF37', + textPrimary: '#F4D03F', textSecondary: 'gray.400', border: 'rgba(212, 175, 55, 0.3)', }; diff --git a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/BusinessStructureCard.tsx b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/BusinessStructureCard.tsx index 83e75818..b3c5e36d 100644 --- a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/BusinessStructureCard.tsx +++ b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/BusinessStructureCard.tsx @@ -23,8 +23,8 @@ import type { BusinessStructure } from '../types'; // 黑金主题配置 const THEME = { cardBg: 'gray.800', - gold: '#D4AF37', - textPrimary: '#D4AF37', + gold: '#F4D03F', + textPrimary: '#F4D03F', border: 'rgba(212, 175, 55, 0.3)', }; diff --git a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/CorePositioningCard/theme.ts b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/CorePositioningCard/theme.ts index a640f522..812935eb 100644 --- a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/CorePositioningCard/theme.ts +++ b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/CorePositioningCard/theme.ts @@ -15,13 +15,13 @@ import type { IconType } from 'react-icons'; // ==================== 主题常量 ==================== export const THEME = { - // 深色背景区域(核心定位) + // 深色背景区域(核心定位)- 使用更亮的金色提高对比度 dark: { bg: '#1A202C', cardBg: '#252D3A', - border: '#C9A961', - borderGradient: 'linear-gradient(90deg, #C9A961, #8B7355)', - titleColor: '#C9A961', + border: '#E8C14D', + borderGradient: 'linear-gradient(90deg, #E8C14D, #A08040)', + titleColor: '#E8C14D', textColor: '#E2E8F0', subtextColor: '#A0AEC0', }, @@ -29,11 +29,11 @@ export const THEME = { light: { bg: '#1E2530', cardBg: '#252D3A', - titleColor: '#C9A961', + titleColor: '#E8C14D', textColor: '#E2E8F0', subtextColor: '#A0AEC0', - tagBg: 'rgba(201, 169, 97, 0.15)', - tagColor: '#C9A961', + tagBg: 'rgba(232, 193, 77, 0.15)', + tagColor: '#E8C14D', }, } as const; diff --git a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/KeyFactorsCard.tsx b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/KeyFactorsCard.tsx index b14e0961..f479f4c6 100644 --- a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/KeyFactorsCard.tsx +++ b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/KeyFactorsCard.tsx @@ -31,9 +31,9 @@ import type { KeyFactors } from '../types'; const THEME = { bg: '#1A202C', cardBg: '#252D3A', - border: '#C9A961', - borderGradient: 'linear-gradient(90deg, #C9A961, #8B7355)', - titleColor: '#C9A961', + border: '#E8C14D', + borderGradient: 'linear-gradient(90deg, #E8C14D, #A08040)', + titleColor: '#E8C14D', textColor: '#E2E8F0', subtextColor: '#A0AEC0', } as const; diff --git a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/TimelineCard.tsx b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/TimelineCard.tsx index 87ab1065..c4ba3085 100644 --- a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/TimelineCard.tsx +++ b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/TimelineCard.tsx @@ -24,9 +24,9 @@ import type { DevelopmentTimeline } from '../types'; const THEME = { bg: '#1A202C', cardBg: '#252D3A', - border: '#C9A961', - borderGradient: 'linear-gradient(90deg, #C9A961, #8B7355)', - titleColor: '#C9A961', + border: '#E8C14D', + borderGradient: 'linear-gradient(90deg, #E8C14D, #A08040)', + titleColor: '#E8C14D', textColor: '#E2E8F0', subtextColor: '#A0AEC0', } as const; diff --git a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/ValueChainCard.tsx b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/ValueChainCard.tsx index 4a3f7ab1..2a80c4d5 100644 --- a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/ValueChainCard.tsx +++ b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/components/ValueChainCard.tsx @@ -34,9 +34,9 @@ import type { ValueChainData, ValueChainNode } from '../types'; // 黑金主题配置 const THEME = { cardBg: 'gray.800', - gold: '#D4AF37', + gold: '#F4D03F', goldLight: '#F0D78C', - textPrimary: '#D4AF37', + textPrimary: '#F4D03F', textSecondary: 'gray.400', }; diff --git a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/organisms/ValueChainNodeCard/index.tsx b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/organisms/ValueChainNodeCard/index.tsx index dd8386ec..02401ed0 100644 --- a/src/views/Company/components/CompanyOverview/DeepAnalysisTab/organisms/ValueChainNodeCard/index.tsx +++ b/src/views/Company/components/CompanyOverview/DeepAnalysisTab/organisms/ValueChainNodeCard/index.tsx @@ -39,7 +39,7 @@ import type { ValueChainNodeCardProps, RelatedCompany } from '../../types'; // 黑金主题配置 const THEME = { cardBg: 'gray.700', - gold: '#D4AF37', + gold: '#F4D03F', goldLight: '#F0D78C', textPrimary: 'white', textSecondary: 'gray.400', diff --git a/src/views/Company/components/CompanyOverview/NewsEventsTab.js b/src/views/Company/components/CompanyOverview/NewsEventsTab.js index 8af0b000..c4677efe 100644 --- a/src/views/Company/components/CompanyOverview/NewsEventsTab.js +++ b/src/views/Company/components/CompanyOverview/NewsEventsTab.js @@ -38,22 +38,22 @@ import { } from "react-icons/fa"; import { getEventDetailUrl } from "@/utils/idEncoder"; -// 黑金主题配色 +// 黑金主题配色(文字使用更亮的金色提高对比度) const THEME_PRESETS = { blackGold: { bg: "#0A0E17", cardBg: "#1A1F2E", cardHoverBg: "#212633", cardBorder: "rgba(212, 175, 55, 0.2)", - cardHoverBorder: "#D4AF37", + cardHoverBorder: "#F4D03F", // 亮金色 textPrimary: "#E8E9ED", textSecondary: "#A0A4B8", textMuted: "#6B7280", - gold: "#D4AF37", + gold: "#F4D03F", // 亮金色(用于文字) goldLight: "#FFD54F", inputBg: "#151922", inputBorder: "#2D3748", - buttonBg: "#D4AF37", + buttonBg: "#D4AF37", // 按钮背景保持深金色 buttonText: "#0A0E17", buttonHoverBg: "#FFD54F", badgeS: { bg: "rgba(255, 195, 0, 0.2)", color: "#FFD54F" }, @@ -61,8 +61,8 @@ const THEME_PRESETS = { badgeB: { bg: "rgba(59, 130, 246, 0.2)", color: "#60A5FA" }, badgeC: { bg: "rgba(107, 114, 128, 0.2)", color: "#9CA3AF" }, tagBg: "rgba(212, 175, 55, 0.15)", - tagColor: "#D4AF37", - spinnerColor: "#D4AF37", + tagColor: "#F4D03F", // 亮金色 + spinnerColor: "#F4D03F", // 亮金色 }, default: { bg: "white", diff --git a/src/views/Company/components/CompanyOverview/components/shareholder/ShareholdersTable.tsx b/src/views/Company/components/CompanyOverview/components/shareholder/ShareholdersTable.tsx index 54762d12..3fbbab47 100644 --- a/src/views/Company/components/CompanyOverview/components/shareholder/ShareholdersTable.tsx +++ b/src/views/Company/components/CompanyOverview/components/shareholder/ShareholdersTable.tsx @@ -10,17 +10,18 @@ import type { Shareholder } from "../../types"; import { THEME } from "../../BasicInfoTab/config"; // antd 表格黑金主题配置 +// 使用更亮的金色以提高对比度 const TABLE_THEME = { token: { colorBgContainer: "#2D3748", // gray.700 colorText: "white", - colorTextHeading: "#D4AF37", // 金色 + colorTextHeading: "#F4D03F", // 亮金色(提高对比度) colorBorderSecondary: "rgba(212, 175, 55, 0.3)", }, components: { Table: { headerBg: "#1A202C", // gray.900 - headerColor: "#D4AF37", // 金色 + headerColor: "#F4D03F", // 亮金色(提高对比度) rowHoverBg: "rgba(212, 175, 55, 0.15)", // 金色半透明,文字更清晰 borderColor: "rgba(212, 175, 55, 0.2)", }, @@ -135,7 +136,7 @@ const ShareholdersTable: React.FC = ({ ellipsis: true, render: (name: string) => ( - {name} + {name} ), }, @@ -158,7 +159,7 @@ const ShareholdersTable: React.FC = ({ responsive: ["md"], sorter: (a: Shareholder, b: Shareholder) => (a.holding_shares || 0) - (b.holding_shares || 0), render: (shares: number) => ( - {formatShares(shares)} + {formatShares(shares)} ), }, { diff --git a/src/views/Company/components/MarketDataView/components/panels/TradeDataPanel/KLineModule.tsx b/src/views/Company/components/MarketDataView/components/panels/TradeDataPanel/KLineModule.tsx index bf0eb21d..e1abe4c9 100644 --- a/src/views/Company/components/MarketDataView/components/panels/TradeDataPanel/KLineModule.tsx +++ b/src/views/Company/components/MarketDataView/components/panels/TradeDataPanel/KLineModule.tsx @@ -1,7 +1,7 @@ // src/views/Company/components/MarketDataView/components/panels/TradeDataPanel/KLineModule.tsx -// K线模块 - 日K线/分时图切换展示(黑金主题 + 专业技术指标 + 商品数据叠加) +// K线模块 - 日K线/分时图切换展示(黑金主题 + 专业技术指标 + 商品数据叠加 + 分时盘口) -import React, { useState, useMemo, useCallback } from 'react'; +import React, { useState, useMemo, useCallback, useEffect } from 'react'; import { Box, Text, @@ -20,11 +20,17 @@ import { MenuItem, MenuDivider, Tooltip, + Grid, + GridItem, } from '@chakra-ui/react'; import { RepeatIcon, InfoIcon, ChevronDownIcon, ViewIcon, ViewOffIcon } from '@chakra-ui/icons'; import { BarChart2, Clock, TrendingUp, Calendar, LineChart, Activity, Pencil } from 'lucide-react'; import ReactECharts from 'echarts-for-react'; +// 导入实时行情 Hook 和五档盘口组件 +import { useRealtimeQuote } from '@views/StockOverview/components/FlexScreen/hooks'; +import OrderBookPanel from '@views/StockOverview/components/FlexScreen/components/OrderBookPanel'; + import { darkGoldTheme, PERIOD_OPTIONS } from '../../../constants'; import { getKLineDarkGoldOption, @@ -90,6 +96,7 @@ const KLineModule: React.FC = ({ onChartClick, selectedPeriod, onPeriodChange, + stockCode, }) => { const [mode, setMode] = useState('daily'); const [subIndicator, setSubIndicator] = useState('MACD'); @@ -97,8 +104,34 @@ const KLineModule: React.FC = ({ const [showAnalysis, setShowAnalysis] = useState(true); const [drawingType, setDrawingType] = useState('NONE'); const [overlayMetrics, setOverlayMetrics] = useState([]); + const [showOrderBook, setShowOrderBook] = useState(true); const hasMinuteData = minuteData && minuteData.data && minuteData.data.length > 0; + // 实时行情数据(用于五档盘口) + const subscribedCodes = useMemo(() => { + if (!stockCode || mode !== 'minute') return []; + return [stockCode]; + }, [stockCode, mode]); + + const { quotes, connected } = useRealtimeQuote(subscribedCodes); + + // 获取当前股票的行情数据 + const currentQuote = useMemo(() => { + if (!stockCode) return null; + // 尝试不同的代码格式 + return quotes[stockCode] || quotes[`${stockCode}.SH`] || quotes[`${stockCode}.SZ`] || null; + }, [quotes, stockCode]); + + // 判断是否在交易时间 + const isInTradingHours = useMemo(() => { + const now = new Date(); + const hours = now.getHours(); + const minutes = now.getMinutes(); + const totalMinutes = hours * 60 + minutes; + // 9:15-11:30 或 13:00-15:00 + return (totalMinutes >= 555 && totalMinutes <= 690) || (totalMinutes >= 780 && totalMinutes <= 900); + }, []); + // 计算股票数据的日期范围(用于查询商品数据) const stockDateRange = useMemo(() => { if (tradeData.length === 0) return undefined; @@ -369,19 +402,35 @@ const KLineModule: React.FC = ({ )} - {/* 分时模式下的刷新按钮 */} + {/* 分时模式下的控制按钮 */} {mode === 'minute' && ( - + <> + {/* 显示/隐藏盘口 */} + + + + + {/* 刷新按钮 */} + + )} {/* 模式切换按钮组 */} @@ -424,7 +473,7 @@ const KLineModule: React.FC = ({ ) ) : ( - // 分时走势图 + // 分时走势图 + 五档盘口 minuteLoading ? (
@@ -441,15 +490,115 @@ const KLineModule: React.FC = ({
) : hasMinuteData ? ( - - - + + {/* 分时图表 */} + + + + + + + {/* 五档盘口 */} + {showOrderBook && ( + + + {/* 盘口标题 */} + + + 五档盘口 + + {/* 连接状态指示 */} + + {isInTradingHours && ( + + {connected.SSE || connected.SZSE ? '实时' : '离线'} + + )} + + + + {/* 当前价格信息 */} + {currentQuote && ( + + + 当前价 + 0 ? '#ff4d4d' : + currentQuote.changePct < 0 ? '#22c55e' : + darkGoldTheme.textPrimary + } + > + {currentQuote.price?.toFixed(2) || '-'} + + + + 涨跌幅 + 0 ? '#ff4d4d' : + currentQuote.changePct < 0 ? '#22c55e' : + darkGoldTheme.textMuted + } + > + {currentQuote.changePct > 0 ? '+' : ''}{currentQuote.changePct?.toFixed(2) || '0.00'}% + + + + )} + + {/* 五档盘口面板 */} + {currentQuote && (currentQuote.bidPrices?.length > 0 || currentQuote.askPrices?.length > 0) ? ( + + ) : ( +
+ + + {isInTradingHours ? '获取盘口数据中...' : '非交易时间'} + + {!isInTradingHours && ( + + 交易时间: 9:30-11:30, 13:00-15:00 + + )} + +
+ )} +
+
+ )} +
) : ( ) diff --git a/src/views/Company/components/MarketDataView/components/panels/TradeDataPanel/MetricOverlaySearch.tsx b/src/views/Company/components/MarketDataView/components/panels/TradeDataPanel/MetricOverlaySearch.tsx index e24c8c2f..080775ea 100644 --- a/src/views/Company/components/MarketDataView/components/panels/TradeDataPanel/MetricOverlaySearch.tsx +++ b/src/views/Company/components/MarketDataView/components/panels/TradeDataPanel/MetricOverlaySearch.tsx @@ -85,7 +85,7 @@ const MetricOverlaySearch: React.FC = ({ setIsSearching(true); try { - const response = await searchMetrics(query, undefined, undefined, 20); + const response = await searchMetrics(query, undefined, '日', 20); setSearchResults(response.results || []); } catch (error) { console.error('Search metrics failed:', error); diff --git a/src/views/Company/components/MarketDataView/components/panels/TradeDataPanel/index.tsx b/src/views/Company/components/MarketDataView/components/panels/TradeDataPanel/index.tsx index 745e0a25..68ab6687 100644 --- a/src/views/Company/components/MarketDataView/components/panels/TradeDataPanel/index.tsx +++ b/src/views/Company/components/MarketDataView/components/panels/TradeDataPanel/index.tsx @@ -16,6 +16,7 @@ export interface TradeDataPanelProps { onChartClick: (params: { seriesName?: string; data?: [number, number] }) => void; selectedPeriod?: number; onPeriodChange?: (period: number) => void; + stockCode?: string; } const TradeDataPanel: React.FC = ({ @@ -28,6 +29,7 @@ const TradeDataPanel: React.FC = ({ onChartClick, selectedPeriod, onPeriodChange, + stockCode, }) => { return ( = ({ onChartClick={onChartClick} selectedPeriod={selectedPeriod} onPeriodChange={onPeriodChange} + stockCode={stockCode} /> ); }; diff --git a/src/views/Company/components/MarketDataView/index.tsx b/src/views/Company/components/MarketDataView/index.tsx index 6f688747..c0b4f188 100644 --- a/src/views/Company/components/MarketDataView/index.tsx +++ b/src/views/Company/components/MarketDataView/index.tsx @@ -153,6 +153,7 @@ const MarketDataView: React.FC = ({ stockCode: propStockCod onChartClick={handleChartClick} selectedPeriod={selectedPeriod} onPeriodChange={setSelectedPeriod} + stockCode={stockCode} /> )} diff --git a/src/views/Company/components/MarketDataView/types.ts b/src/views/Company/components/MarketDataView/types.ts index c3bb5eaf..b6bd20c4 100644 --- a/src/views/Company/components/MarketDataView/types.ts +++ b/src/views/Company/components/MarketDataView/types.ts @@ -299,6 +299,7 @@ export interface KLineModuleProps { onChartClick: (params: { seriesName?: string; data?: [number, number] }) => void; selectedPeriod?: number; onPeriodChange?: (period: number) => void; + stockCode?: string; // 股票代码,用于获取实时盘口数据 } /**