feat: 新增热点穿透网状关系图 + 移动端优化
- 新增 /hot-map 热点穿透页:d3-force 力导向网状图展示题材-股票 M:N 关系 - 股票节点面积/颜色按覆盖题材数分级,穿透核心股高亮 - 图/核心股列表双视图切换,列表覆盖题材>2 公司降序展示 - 悬停信息卡、缩放平移、点击跳转股票/题材详情 - 数据采样改为涨幅+热度双榜合并(各 Top50 去重=82 题材),修复覆盖数低估 (有研新材覆盖数 2→10,核心股 66→1124 家) - 移动端适配:触屏 tap 选中底部浮层、标签缩放阈值防重叠、自动 fit、紧凑图例 - 主页/题材列表增加热点穿透入口 Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
@@ -158,3 +158,63 @@ export async function fetchThemeStocks(themeCode: string): Promise<ThemeStocksRe
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/* ── 热点穿透:题材-股票 网状关系图 ── */
|
||||
|
||||
export interface GraphTheme {
|
||||
themeCode: string;
|
||||
themeName: string;
|
||||
bf3: number | null; // 题材涨幅
|
||||
hotValue: number;
|
||||
strengthValue: number | null;
|
||||
stockCount: number; // 题材内股票数
|
||||
}
|
||||
|
||||
export interface GraphStock {
|
||||
securityCode: string;
|
||||
securityName: string;
|
||||
coverCount: number; // 覆盖题材数(穿透强度)
|
||||
f3: number | null; // 涨幅
|
||||
f2: number | null; // 现价
|
||||
f62: number | null; // 主力净流入
|
||||
f100: string; // 行业
|
||||
themeCodes: string[]; // 所属题材代码
|
||||
}
|
||||
|
||||
export interface GraphEdge {
|
||||
themeCode: string;
|
||||
securityCode: string;
|
||||
}
|
||||
|
||||
export interface GraphStats {
|
||||
themeCount: number;
|
||||
stockCount: number;
|
||||
coreCount: number; // 覆盖≥2 的核心股数
|
||||
maxCover: number; // 最大覆盖题材数
|
||||
}
|
||||
|
||||
export interface ThemeGraph {
|
||||
themes: GraphTheme[];
|
||||
stocks: GraphStock[];
|
||||
edges: GraphEdge[];
|
||||
stats: GraphStats;
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取热点穿透图数据(题材-股票 M:N 网状关系)
|
||||
* @param sortField 1=涨幅 4=热度
|
||||
* @param top 题材数量
|
||||
*/
|
||||
export async function fetchThemeGraph(sortField: 1 | 4 = 1, top: number = 30): Promise<ThemeGraph | null> {
|
||||
const baseUrl = getApiBaseUrl();
|
||||
const url = `${baseUrl}/api/themes/graph?sort_field=${sortField}&top=${top}`;
|
||||
|
||||
try {
|
||||
const resp = await fetch(url, { method: "GET", cache: "no-store" });
|
||||
if (!resp.ok) return null;
|
||||
return await resp.json();
|
||||
} catch (err) {
|
||||
console.error("[theme-api] 获取热点穿透图数据失败:", err);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user