提交 04313969 authored 作者: coderBryanFu's avatar coderBryanFu

update

...@@ -100,7 +100,7 @@ ...@@ -100,7 +100,7 @@
</div> </div>
<div class="select-box"> <div class="select-box">
<div class="rank-btns"> <div class="rank-btns">
<!-- <div class="rank-btn" :class="{ active: rankType === 'institution' }" @click="rankType = 'institution'"> <div class="rank-btn" :class="{ active: rankType === 'institution' }" @click="rankType = 'institution'">
对我打压机构 对我打压机构
</div> </div>
<div class="rank-btn" :class="{ active: rankType === 'enterprise' }" @click="rankType = 'enterprise'"> <div class="rank-btn" :class="{ active: rankType === 'enterprise' }" @click="rankType = 'enterprise'">
...@@ -108,22 +108,58 @@ ...@@ -108,22 +108,58 @@
</div> </div>
<div class="rank-btn" :class="{ active: rankType === 'school' }" @click="rankType = 'school'"> <div class="rank-btn" :class="{ active: rankType === 'school' }" @click="rankType = 'school'">
受打压院校 受打压院校
</div> --> </div>
</div> </div>
<el-select v-model="selectedField" placeholder="全部领域" class="field-select"> <el-select v-model="selectedField" placeholder="全部领域" class="field-select">
<el-option v-for="item in fieldOptions" :key="item.value" :label="item.label" :value="item.value" /> <el-option v-for="item in fieldOptions" :key="item.value" :label="item.label" :value="item.value" />
</el-select> </el-select>
</div> </div>
<div class="main-box"> <div class="main-box">
<div v-for="(item, index) in rankList" :key="index" class="rank-item"> <!-- 机构排行的原有样式 -->
<div class="rank-num" :class="'rank-' + (index + 1)">{{ index + 1 }}</div> <template v-if="rankType === 'institution'">
<img :src="defaultImg" alt="" class="rank-icon" /> <div v-for="(item, index) in rankList" :key="index" class="rank-item">
<div class="rank-name">{{ item.name }}</div> <div class="rank-num" :class="'rank-' + (index + 1)">{{ index + 1 }}</div>
<div class="rank-progress-container"> <img :src="defaultImg" alt="" class="rank-icon" />
<div class="rank-progress-bar" :style="{ width: getProgressWidth(item.count) }"></div> <div class="rank-name" :title="item.name">{{ item.name }}</div>
<div class="rank-progress-container">
<div class="rank-progress-bar" :style="{ width: getProgressWidth(item.count) }"></div>
</div>
<div class="rank-count">{{ item.count }}</div>
</div> </div>
<div class="rank-count">{{ item.count }}</div> </template>
</div> <!-- 企业/院校排行的表格样式 -->
<template v-else>
<div class="table-header">
<div class="col-rank"></div>
<div class="col-name" style="color: rgb(59, 65, 75);font-weight: 700;">{{ rankType === 'enterprise' ? '公司名称' : '院校名称' }}</div>
<div class="col-domain" style="color: rgb(59, 65, 75);font-weight: 700;">所属领域</div>
<div class="col-date" style="color: rgb(59, 65, 75);font-weight: 700;">制裁时间</div>
<div class="col-member" v-if="rankType !== 'school'" style="color: rgb(59, 65, 75);font-weight: 700;">关键人物</div>
</div>
<div class="table-list">
<div v-for="(item, index) in rankList" :key="index" class="table-row">
<div class="col-rank rank-num" :class="'rank-' + (index + 1)">{{ index + 1 }}</div>
<div class="col-name flex-align">
<img :src="defaultImg" class="rank-icon" />
<span class="text-ellipsis" :title="item.name">{{ item.name }}</span>
</div>
<div class="col-domain">
<div class="domain-tags">
<span
v-for="(tag, tIndex) in item.domains.slice(0, rankType === 'enterprise' ? 2 : 3)"
:key="tIndex"
class="mini-tag"
:class="getTagClass(tag)"
>
{{ tag }}
</span>
</div>
</div>
<div class="col-date">{{ item.date }}</div>
<div class="col-member" v-if="rankType !== 'school'">{{ item.member }}</div>
</div>
</div>
</template>
</div> </div>
</div> </div>
</div> </div>
...@@ -278,71 +314,7 @@ const handleClickTitle = item => { ...@@ -278,71 +314,7 @@ const handleClickTitle = item => {
window.open(href, "_blank"); window.open(href, "_blank");
}; };
const timelineList = ref([ const timelineList = ref([]);
{
date: "2025年 5月",
tags: ["人工智能", "航空航天"],
title: "《国家量子倡议再授权法案》发布",
content: "计划将国家量子倡议延长至2034年,新增研发中心、测试平台,并首次将NASA...",
info: "11月15日 · 参议院 · 科技法案"
},
{
date: "2025年 6月",
tags: ["人工智能"],
title: "《国家量子倡议再授权法案》发布",
content: "计划将国家量子倡议延长至2034年,新增研发中心、测试平台,并首次将NASA...",
info: "11月15日 · 参议院 · 科技法案"
},
{
date: "2025年 7月",
tags: ["集成电路"],
title: "《国家量子倡议再授权法案》发布",
content: "计划将国家量子倡议延长至2034年,新增研发中心、测试平台,并首次将NASA...",
info: "11月15日 · 参议院 · 科技法案"
},
{
date: "2025年 8月",
tags: ["新材料", "量子科技"],
title: "《国家量子倡议再授权法案》发布",
content: "计划将国家量子倡议延长至2034年,新增研发中心、测试平台,并首次将NASA...",
info: "11月15日 · 参议院 · 科技法案"
},
{
date: "2025年 9月",
tags: ["人工智能", "航空航天"],
title: "《国家量子倡议再授权法案》发布",
content: "计划将国家量子倡议延长至2034年,新增研发中心、测试平台,并首次将NASA...",
info: "11月15日 · 参议院 · 科技法案"
},
{
date: "2025年 10月",
tags: ["新材料", "能源"],
title: "《国家量子倡议再授权法案》发布",
content: "计划将国家量子倡议延长至2034年,新增研发中心、测试平台,并首次将NASA...",
info: "11月15日 · 参议院 · 科技法案"
},
{
date: "2025年 11月",
tags: ["人工智能", "航空航天"],
title: "《国家量子倡议再授权法案》发布",
content: "计划将国家量子倡议延长至2034年,新增研发中心、测试平台,并首次将NASA...",
info: "11月15日 · 参议院 · 科技法案"
},
{
date: "2025年 12月",
tags: ["新材料", "能源"],
title: "《国家量子倡议再授权法案》发布",
content: "计划将国家量子倡议延长至2034年,新增研发中心、测试平台,并首次将NASA...",
info: "11月15日 · 参议院 · 科技法案"
},
{
date: "2025年 12月",
tags: ["集成电路"],
title: "《国家量子倡议再授权法案》发布",
content: "计划将国家量子倡议延长至2034年,新增研发中心、测试平台,并首次将NASA...",
info: "11月15日 · 参议院 · 科技法案"
}
]);
// 处理时间线数据的方法 // 处理时间线数据的方法
const processTimelineData = rawData => { const processTimelineData = rawData => {
...@@ -746,94 +718,7 @@ const handleGetAllDomainCount = async () => { ...@@ -746,94 +718,7 @@ const handleGetAllDomainCount = async () => {
} catch (error) {} } catch (error) {}
}; };
const box5Data = ref({ const box5Data = ref({});
title: [
"2024-12",
"2025-1",
"2025-2",
"2025-3",
"2025-4",
"2025-5",
"2025-6",
"2025-7",
"2025-8",
"2025-9",
"2025-10",
"2025-11"
],
data: [
{
name: "集成电路",
color: "#0052D9",
value: [87, 78, 74, 67, 60, 59, 63, 66, 63, 58, 56, 62]
},
{
name: "生物科技",
color: "#00A79D",
value: [13, 13, 8, 13, 20, 37, 34, 25, 22, 20, 27, 18]
},
{
name: "量子科技",
color: "#7B61FF",
value: [18, 16, 12, 16, 16, 26, 30, 29, 25, 25, 33, 25]
},
{
name: "新一代信息技术",
color: "#FF9F1C",
value: [10, 22, 22, 34, 48, 51, 46, 55, 55, 60, 68, 70]
},
{
name: "人工智能",
color: "#E34D59",
value: [25, 34, 39, 45, 53, 54, 50, 47, 50, 54, 56, 51]
},
{
name: "通信网络",
color: "#0052D9",
value: [22, 26, 31, 31, 38, 33, 26, 38, 36, 40, 45, 47]
},
{
name: "新能源",
color: "#2BA471",
value: [53, 44, 43, 41, 34, 29, 57, 44, 61, 67, 61, 61]
},
{
name: "先进制造",
color: "#363B42",
value: [70, 75, 78, 75, 75, 80, 73, 51, 71, 77, 80, 89]
},
{
name: "航空航天",
color: "#3762F0",
value: [18, 16, 12, 16, 16, 26, 30, 29, 25, 25, 33, 25]
},
{
name: "海洋",
color: "#76D1FF",
value: [13, 13, 8, 13, 20, 37, 34, 25, 22, 20, 27, 18]
},
{
name: "新材料",
color: "#FFD900",
value: [10, 22, 22, 34, 48, 51, 46, 55, 55, 60, 68, 70]
},
{
name: "深海",
color: "#002060",
value: [22, 26, 31, 31, 38, 33, 26, 38, 36, 40, 45, 47]
},
{
name: "极地",
color: "#A6A6A6",
value: [53, 44, 43, 41, 34, 29, 57, 44, 61, 67, 61, 61]
},
{
name: "核",
color: "#FFB3B3",
value: [25, 34, 39, 45, 53, 54, 50, 47, 50, 54, 56, 51]
}
]
});
const handleGetDomainContainmentTrend = async () => { const handleGetDomainContainmentTrend = async () => {
try { try {
...@@ -910,60 +795,18 @@ const processDomainTrendData = rawData => { ...@@ -910,60 +795,18 @@ const processDomainTrendData = rawData => {
}; };
}; };
const tagColors = [
{
text: "航空航天",
textColor: "#1677FF", // 蓝色文字
bgColor: "#E6F7FF" // 浅蓝色背景
},
{
text: "能源",
textColor: "#1677FF",
bgColor: "#E6F7FF"
},
{
text: "新材料",
textColor: "#5993EE",
bgColor: "#E6F7FF"
},
{
text: "生物科技",
textColor: "#5993EE",
bgColor: "#E6F7FF"
},
{
text: "人工智能",
textColor: "#D9001B",
bgColor: "#FFECEC"
},
{
text: "集成电路",
textColor: "#1677FF",
bgColor: "#E6F7FF"
}
];
const getTagColor = tagName => {
const foundTag = tagColors.find(tag => tag.text === tagName);
return foundTag ? { textColor: foundTag.textColor, bgColor: foundTag.bgColor } : { textColor: "#000", bgColor: "#fff" };
};
const rankList = ref([ const rankList = ref([]);
{ name: "美国商务部", count: 45 },
{ name: "美国财政部", count: 38 }, const maxCount = computed(() => {
{ name: "美国白宫", count: 36 }, if (!rankList.value || rankList.value.length === 0) return 0;
{ name: "美国国务院", count: 34 }, return Math.max(...rankList.value.map(item => item.count || 0));
{ name: "美国战争部", count: 33 }, });
{ name: "联邦参议院", count: 31 },
{ name: "美国美国国土安全部", count: 28 },
{ name: "美国贸易代表办公室", count: 20 },
{ name: "联邦通信委员会", count: 16 },
{ name: "美国食品药品监督管理局", count: 12 }
]);
const maxCount = Math.max(...rankList.value.map(item => item.count));
const getProgressWidth = count => { const getProgressWidth = count => {
return (count / maxCount) * 100 + "%"; if (!maxCount.value) return "0%";
return (count / maxCount.value) * 100 + "%";
}; };
// 处理排名数据的方法 // 处理排名数据的方法
...@@ -973,10 +816,25 @@ const processRankingData = rawData => { ...@@ -973,10 +816,25 @@ const processRankingData = rawData => {
} }
return rawData.map(item => { return rawData.map(item => {
// 格式化日期:2025-10-08 -> 2025.10.8
let formattedDate = "";
if (item.sanctionDate) {
const date = new Date(item.sanctionDate);
if (!isNaN(date.getTime())) {
formattedDate = `${date.getFullYear()}.${date.getMonth() + 1}.${date.getDate()}`;
} else {
formattedDate = item.sanctionDate;
}
}
return { return {
name: item.orgName || "", name: item.orgName || "",
count: item.orgCount || 0, count: item.orgCount || 0,
orgPicture: item.orgPicture // 保留原始图片字段,以防后续需要使用 orgPicture: item.orgPicture,
// 新增字段
domains: item.domainList ? item.domainList.map(d => d.name) : [],
date: formattedDate,
member: item.keyMember || "-"
}; };
}); });
}; };
...@@ -989,16 +847,13 @@ const rankTypeMap = { ...@@ -989,16 +847,13 @@ const rankTypeMap = {
// 获取领域遏制排名数据 // 获取领域遏制排名数据
const handleGetDomainContainmentRanking = async () => { const handleGetDomainContainmentRanking = async () => {
rankList.value = [];
try { try {
console.log("获取领域遏制排名数据", rankTypeMap[rankType.value], selectedField.value);
const res = await getDomainContainmentRanking( const res = await getDomainContainmentRanking(
rankTypeMap[rankType.value], rankTypeMap[rankType.value],
!!selectedField.value ? selectedField.value : "" !!selectedField.value ? selectedField.value : ""
); );
console.log("获取领域遏制排名数据", rankTypeMap[rankType.value], selectedField.value);
console.log("美对华领域打压遏制排行", res);
if (res.code === 200 && res.data) { if (res.code === 200 && res.data) {
// 处理返回的数据结构 // 处理返回的数据结构
const processedData = processRankingData(res.data); const processedData = processRankingData(res.data);
...@@ -1443,6 +1298,7 @@ watch(activeDate, () => { ...@@ -1443,6 +1298,7 @@ watch(activeDate, () => {
display: flex; display: flex;
align-items: center; align-items: center;
height: 30px; height: 30px;
flex-shrink: 0;
.rank-num { .rank-num {
width: 24px; width: 24px;
...@@ -1515,6 +1371,167 @@ watch(activeDate, () => { ...@@ -1515,6 +1371,167 @@ watch(activeDate, () => {
text-align: right; text-align: right;
} }
} }
// 新增表格样式
.table-header {
display: flex;
align-items: center;
padding-bottom: 12px;
// border-bottom: 1px solid #eee;
margin-bottom: 8px;
div {
font-family: "Microsoft YaHei";
font-size: 16px;
color: #5f656c;
font-weight: 400;
}
}
.table-list {
flex: 1;
overflow-y: auto;
display: flex;
flex-direction: column;
gap: 16px;
}
.table-row {
display: flex;
align-items: center;
height: 40px;
.rank-num {
font-family: Microsoft YaHei;
font-size: 16px;
font-weight: 700;
text-align: center;
color: #3b414b;
&.rank-1 {
color: #d94b4b;
}
&.rank-2 {
color: #e3935d;
}
&.rank-3 {
color: #ebd348;
}
}
.flex-align {
display: flex;
align-items: center;
}
.rank-icon {
width: 30px;
height: 30px;
margin-right: 12px;
}
.text-ellipsis {
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
font-family: "Microsoft YaHei";
font-size: 16px;
font-weight: 700;
line-height: 30px;
color: rgb(59, 65, 75);
}
.domain-tags {
display: flex;
gap: 6px;
flex-wrap: wrap;
.mini-tag {
padding: 2px 6px;
border-radius: 4px;
font-size: 12px;
font-family: "Microsoft YaHei";
line-height: 1.2;
white-space: nowrap;
// 复用已有的tag颜色逻辑,需要配合 getTagClass
&.tag-item {
// 基础样式
}
&.tag-blue {
color: rgba(9, 88, 217, 1);
background: rgba(230, 244, 255, 1);
border-color: rgba(186, 224, 255, 1);
border: 1px solid rgba(186, 224, 255, 1);
}
&.tag-green {
color: rgba(56, 158, 13, 1);
background: rgba(246, 255, 237, 1);
border-color: rgba(217, 247, 190, 1);
border: 1px solid rgba(217, 247, 190, 1);
}
&.tag-red {
color: rgba(245, 34, 45, 1);
background: rgba(255, 241, 240, 1);
border-color: rgba(255, 163, 158, 1);
border: 1px solid rgba(255, 163, 158, 1);
}
&.tag-orange {
color: rgba(250, 140, 22, 1);
background: rgba(255, 247, 230, 1);
border-color: rgba(255, 213, 145, 1);
border: 1px solid rgba(255, 213, 145, 1);
}
&.tag-purple {
color: rgba(114, 46, 209, 1);
background: rgba(249, 240, 255, 1);
border-color: rgba(211, 173, 247, 1);
border: 1px solid rgba(211, 173, 247, 1);
}
&.tag-cyan {
color: rgba(19, 194, 194, 1);
background: rgba(230, 255, 251, 1);
border-color: rgba(135, 232, 222, 1);
border: 1px solid rgba(135, 232, 222, 1);
}
}
}
}
// 列宽控制
.col-rank {
width: 50px;
text-align: center;
flex-shrink: 0;
}
.col-name {
flex: 1.5;
min-width: 0;
margin-right: 16px;
}
.col-domain {
flex: 1.5;
min-width: 0;
margin-right: 16px;
}
.col-date {
width: 100px;
flex-shrink: 0;
font-family: "Microsoft YaHei";
font-size: 16px;
font-weight: 400;
line-height: 24px;
color: rgb(59, 65, 75);
text-align: left;
}
.col-member {
width: 80px;
flex-shrink: 0;
font-family: "Microsoft YaHei";
font-size: 16px;
color: rgb(59, 65, 75);
text-align: center;
}
} }
} }
} }
......
...@@ -48,7 +48,7 @@ ...@@ -48,7 +48,7 @@
:class="{ active: activeDate === item.type }" :class="{ active: activeDate === item.type }"
@click="handleDateClick(item.type)" @click="handleDateClick(item.type)"
> >
<img :src="activeDate === item.type ? item.activeIcon : item.icon" alt="" /> <!-- <img :src="activeDate === item.type ? item.activeIcon : item.icon" alt="" /> -->
<span>{{ item.name }}</span> <span>{{ item.name }}</span>
</div> </div>
</div> </div>
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论