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

Merge branch 'pre' of http://8.140.26.4:10003/caijian/risk-monitor into fk-dev

流水线 #214 已通过 于阶段
in 1 分 43 秒
差异被折叠。
......@@ -2,67 +2,65 @@ import request from "@/api/request.js";
// 中美博弈概览V2:最新风险动态统计
export function getLatestRiskUpdates(params) {
return request({
method: 'GET',
url: `/api/rivalryIndexV2/LatestRiskUpdates`,
params: params
})
return request({
method: "GET",
url: `/api/rivalryIndexV2/LatestRiskUpdates`,
params: params
});
}
// 中美博弈概览V2:最新风险信号
export function getLatestRisks() {
return request({
method: 'GET',
url: `/api/rivalryIndexV2/LatestRisks`,
})
return request({
method: "GET",
url: `/api/rivalryIndexV2/LatestRisks`
});
}
// 中美博弈概览V2:美对华制裁措施数量趋势
export function geDomainContainmentTrend(params) {
return request({
method: 'GET',
url: `/api/rivalryIndexV2/DomainContainmentTrend`,
params: params
})
return request({
method: "GET",
url: `/api/rivalryIndexV2/DomainContainmentTrend`,
params: params
});
}
// 中美博弈概况:获取榜单字典
export function getChartDict() {
return request({
method: 'GET',
url: `/api/union/summary/chartDict`,
})
return request({
method: "GET",
url: `/api/union/summary/chartDict`
});
}
// 中美博弈概况:获取年份
export function getYear(id) {
return request({
method: "GET",
url: `/api/union/summary/chartYear/${id}`
});
}
// 中美博弈概况:中美科技实力对比
export function getCompare(id) {
return request({
method: 'GET',
url: `/api/union/summary/compare/${id}`,
})
export function getCompare(id, year) {
return request({
method: "GET",
url: `/api/union/summary/compare/${id}/${year}`
});
}
// 中美博弈分析
export function getTechnologyGameAnalysis() {
return request({
method: 'GET',
url: `/api/rivalryIndexV2/TechnologyGameAnalysis`,
})
return request({
method: "GET",
url: `/api/rivalryIndexV2/TechnologyGameAnalysis`
});
}
//中美博弈概览V7:美国政府部门对华制裁最新动态
export function getGovernmentSanctionsDynamics() {
return request({
method: 'GET',
url: `/api/rivalryIndex/governmentSanctionsDynamics`,
})
}
\ No newline at end of file
return request({
method: "GET",
url: `/api/rivalryIndex/governmentSanctionsDynamics`
});
}
......@@ -46,6 +46,7 @@
img {
width: 100%;
height: 100%;
display: block;
}
}
......
......@@ -2,6 +2,8 @@
const thinkTank = () => import('@/views/thinkTank/index.vue')
const ThinkTankDetail = () => import('@/views/thinkTank/ThinkTankDetail/index.vue')
const ReportDetail = () => import('@/views/thinkTank/ReportDetail/index.vue')
const SurveyProjectView = () => import('@/views/thinkTank/SurveyProjectView/index.vue')
const CongressHearingView = () => import('@/views/thinkTank/CongressHearingView/index.vue')
const ReportOriginal = () => import('@/views/thinkTank/reportOriginal/index.vue')
const allThinkTank= () => import('@/views/thinkTank/allThinkTank/index.vue')
const MultiThinkTankViewAnalysis= () => import('@/views/thinkTank/MultiThinkTankViewAnalysis/index.vue')
......@@ -40,6 +42,16 @@ const thinktankRoutes = [
name: "ReportOriginal",
component: ReportOriginal,
},
{
path: "/thinkTank/SurveyProjectView/:id",
name: "SurveyProjectView",
component: SurveyProjectView,
},
{
path: "/thinkTank/CongressHearingView/:id",
name: "CongressHearingView",
component: CongressHearingView,
},
{
path: "/thinkTank/allThinkTank",
......
......@@ -14,10 +14,20 @@
size="default"
style="margin-left: 15px; width: 240px; height: 32px"
v-model="origin"
@change="handleGetCompare()"
@change="handleOriginChange()"
>
<el-option :value="value.id" :label="value.name" v-for="(value, index) in originList" :key="index" />
</el-select>
<el-select
class="select-item"
size="default"
style="margin-left: 15px; width: 200px; height: 32px"
v-model="year"
@change="handleGetCompare()"
>
<el-option :value="value" :label="value" v-for="(value, index) in yearList" :key="index" />
</el-select>
</div>
</div>
<div style="display: flex; height: 650px; width: 100%; padding-top: 12px">
......@@ -237,7 +247,7 @@ import Echarts from "@/components/Chart/index.vue";
import mockData from "./mock.json";
import radarChart from "./radarChart3.js";
import { getCompare, getChartDict, getTechnologyGameAnalysis } from "@/api/zmOverview/risk/index.js";
import { getCompare, getChartDict, getYear, getTechnologyGameAnalysis } from "@/api/zmOverview/risk/index.js";
import icon1 from "./icon/btn-icon-0.png";
import icon2 from "./icon/btn-icon-1.png";
import icon3 from "./icon/btn-icon-2.png";
......@@ -351,10 +361,32 @@ const handleGetChartDict = async () => {
console.error("获取数据来源error", error);
}
};
const yearList = ref([]);
const year = ref("");
//年份
const handleGetYear = async () => {
try {
const res = await getYear(origin.value);
console.log("年份", res);
if (res.code === 200 && res.data) {
yearList.value = res.data;
year.value = res.data[0];
}
} catch (error) {
console.error("获取年份error", error);
}
};
// 数据来源改变时,年份列表也会改变
const handleOriginChange = async () => {
await handleGetYear();
};
//中美科技实力对比
const handleGetCompare = async () => {
try {
const res = await getCompare(origin.value);
const res = await getCompare(origin.value, year.value);
console.log("中美科技实力对比", res);
if (res.code === 200 && res.data) {
tableData.value = res.data[0].children;
......@@ -392,6 +424,7 @@ const handlegetTechnologyGameAnalysis = async () => {
};
onMounted(async () => {
await handleGetChartDict();
await handleGetYear();
await handleGetCompare();
await handlegetTechnologyGameAnalysis();
// const dom = document.getElementById("char");
......@@ -463,7 +496,13 @@ const handleIndicatorChange = indicator => {
const years = chinaData.map(item => item.year.toString());
const chinaValues = chinaData.map(item => item.value);
const usaValues = usaData.map(item => item.value);
console.log("中国", chinaValues);
console.log("美国", usaValues);
// chinaValues和usaValues的最小值和最大值
const min = Math.min(...chinaValues, ...usaValues);
const max = Math.max(...chinaValues, ...usaValues);
lineOption.value.yAxis.min = Math.floor(min - 1);
lineOption.value.yAxis.max = Math.ceil(max + 1);
lineOption.value.xAxis.data = years;
lineOption.value.series = [
{
......@@ -566,9 +605,11 @@ const lineOption = ref({
},
yAxis: {
type: "value",
// name: "指数",
nameLocation: "top",
nameGap: 35,
min: 77,
name: "指数",
nameLocation: "end",
nameGap: 1,
padding: [0, -50, 0, 0],
nameTextStyle: {
color: "#666",
fontSize: 13,
......@@ -589,7 +630,7 @@ const lineOption = ref({
}
},
axisLabel: {
color: "#ccc",
color: "#666",
fontSize: 14,
fontWeight: 400,
formatter: value => {
......
......@@ -25,8 +25,8 @@
</div>
</div>
</div> -->
<NewsList :newsList="leftList" @item-click="handleToNewsDetail" @more-click="handleToMoreNews" img="image"
title="title" content="content" from="from" />
<NewsList :newsList="leftList" @item-click="item => gotoNewsDetail(item.id)" @more-click="handleToMoreNews"
img="image" title="title" content="content" from="from" />
<MessageBubble :messageList="rightList" imageUrl="personImage" @more-click="handleToSocialDetail"
@person-click="handleToSocialDetail" name="name" content="content" source="orgName" image-url="image" />
<!-- <div class="right">
......@@ -60,6 +60,8 @@ import title03 from './assets/title03.png'
import title01bg from './assets/title01bg.png'
import title02bg from './assets/title02bg.png'
import title03bg from './assets/title03bg.png'
import { useGotoNewsDetail } from '@/router/modules/news';
const gotoNewsDetail = useGotoNewsDetail()
// 合作限制-查询社交媒体接口
const getCoopRestrictionSocialData = async () => {
......
......@@ -12,50 +12,52 @@
<el-carousel ref="carouselRef" height="412px" direction="horizontal" :autoplay="true" :interval="5000"
arrow="never" indicator-position="none" @change="handleCarouselChange">
<el-carousel-item v-for="(item, index) in coopRestrictionTrends" :key="item.ID || index">
<div class="carousel-item-content">
<div class="left-center">
<img :src="item.IMAGEURL || defaultImg" alt="" />
<div class="left-center-main">
<div class="left-center-main-title">{{ item.LIMITNAME || "暂无动态" }}</div>
<div class="left-center-main-ul">
<ul>
<li>
<span class="ul-title">数据来源:</span>
<span class="ul-content">{{ item.ORGNAME || "未知" }}</span>
</li>
<li>
<span class="ul-title">合作限制类型:</span>
<span class="ul-content">{{ item.LIMITTYPE || "未知" }}</span>
</li>
<li>
<span class="ul-title">发布日期:</span>
<span class="ul-content">{{ item.LIMITDATE || "未知" }}</span>
</li>
<li>
<span class="ul-title">涉及领域:</span>
<div class="ul-tags" v-if="item.AREA">
<span v-for="(field, fIndex) in typeof item.AREA === 'string'
? item.AREA.split(',')
: item.AREA" :key="fIndex" class="ul-pie" :class="'cl' + ((fIndex % 3) + 1)">
{{ field }}
</span>
</div>
<span v-else class="ul-content">未知</span>
</li>
</ul>
</div>
<div class="left-center">
<img :src="item.IMAGEURL || defaultImg" alt="" />
<div class="left-center-main">
<div class="left-center-main-title">{{ item.LIMITNAME || "暂无动态" }}</div>
<div class="left-center-main-ul">
<ul>
<li>
<span class="ul-title">数据来源:</span>
<span class="ul-content">{{ item.ORGNAME || "未知" }}</span>
</li>
<li>
<span class="ul-title">合作限制类型:</span>
<span class="ul-content">{{ item.LIMITTYPE || "未知" }}</span>
</li>
<li>
<span class="ul-title">发布日期:</span>
<span class="ul-content">{{ item.LIMITDATE || "未知" }}</span>
</li>
<li>
<span class="ul-title">涉及领域:</span>
<div class="ul-tags" v-if="item.AREA">
<span v-for="(field, fIndex) in typeof item.AREA === 'string'
? item.AREA.split(',')
: item.AREA" :key="fIndex" class="ul-pie" :class="'cl' + ((fIndex % 3) + 1)">
{{ field }}
</span>
</div>
<span v-else class="ul-content">未知</span>
</li>
</ul>
</div>
<!-- <div class="left-center-title">{{ item.LIMITTYPE }}</div> -->
</div>
<div class="left-bottom">
<ul>
<li class="left-bottom-li">内容摘要:</li>
</ul>
<div class="left-bottom-content">
{{ item.INTRODUCTION || "暂无内容摘要" }}
</div>
<div class="left-center-type" v-if="item.type">{{ item.type }}</div>
<!-- <div class="left-center-title">{{ item.LIMITTYPE }}</div> -->
</div>
<div class="left-bottom">
<ul>
<li class="left-bottom-li">内容摘要:</li>
</ul>
<div class="left-bottom-content">
{{ item.INTRODUCTION || "暂无内容摘要" }}
</div>
</div>
</el-carousel-item>
<!-- 无数据时的占位展示 -->
......@@ -108,6 +110,7 @@
查看更多
</div>
</div> -->
<RiskSignal :list="riskSignals" @more-click="handleToMoreRiskSignal" postDate="time" name="content"
riskLevel="title" @item-click="handleClickToDetail" />
</div>
......@@ -233,7 +236,7 @@ onMounted(() => {
.left {
width: 1064px;
height: 460px;
height: 450px;
margin-right: 16px;
border-radius: 10px;
background-color: #fff;
......@@ -330,6 +333,7 @@ onMounted(() => {
.left-center-main {
width: 439px;
height: 175px;
position: relative;
.left-center-main-title {
margin-left: 19px;
......@@ -420,6 +424,29 @@ onMounted(() => {
}
}
}
}
.left-center-type {
position: absolute;
top: 0;
right: 0;
height: 32px;
font-family: "Source Han Sans CN";
font-weight: 700;
font-size: 18px;
line-height: 24px;
letter-spacing: 0px;
text-align: left;
color: rgb(5, 95, 194);
background-color: rgb(231, 243, 255);
align-items: center;
border-radius: 4px;
padding-left: 8px;
padding-right: 8px;
padding-top: 3px;
padding-bottom: 5px;
}
.left-center-title {
......@@ -439,7 +466,7 @@ onMounted(() => {
}
.left-bottom {
margin: 17px 0 0 62px;
margin: 17px 0 0 59px;
ul {
list-style-position: inside;
......
......@@ -15,7 +15,8 @@
<div class="main-content" ref="homeMainRef" :class="{ 'scroll-main': isShow }">
<div class="home-top-bg"></div>
<!-- 搜索栏部分 -->
<SearchContainer v-if="homeMainRef" placeholder="搜索合作限制" :containerRef="homeMainRef" areaName="" />
<SearchContainer v-if="homeMainRef" :countInfo="cooperationCountInfo" placeholder="搜索合作限制"
:containerRef="homeMainRef" areaName="" />
<!-- 最新动态 -->
<div class="newdata" id="position1">
......@@ -57,9 +58,36 @@ import newData from "./components/dataNew/index.vue";
import askPage from "./components/askPage/index.vue";
import dataSub from "./components/dataSub/index.vue";
import resLib from "./components/resLib/index.vue";
import { getCoopRestrictionStatistics } from "@/api/coopRestriction/coopRestriction.js";
import { useContainerScroll } from "@/hooks/useScrollShow";
const cooperationCountInfo = ref([]);
// const
const getCooperationCountInfo = async () => {
try {
const res = await getCoopRestrictionStatistics();
if (res && res.code === 200) {
// console.log('----getStatCountInfo', res.data)
cooperationCountInfo.value = [
{
name: "相关法案",
count: res.data.billCounts
},
{
name: "相关政令",
count: res.data.aocounts
},
{
name: "相关政府公告",
count: res.data.ggcounts
},
];
}
} catch (error) {
console.error("获取首页统计接口失败:", error);
}
};
// 搜索框
const input = ref("");
const homeMainRef = ref(null);
......@@ -71,7 +99,9 @@ const router = useRouter();
const handleSearch = () => {
console.log("搜索内容:", input.value);
};
onMounted(() => {
getCooperationCountInfo();
});
// 锚点跳转
const handleToPosi = id => {
const element = document.getElementById(id);
......@@ -106,6 +136,7 @@ const handleToPosi = id => {
.coop-page {
width: 100%;
height: 100%;
display: flex;
// .breadcrumb {
// width: 100%;
// height: 64px;
......@@ -138,6 +169,12 @@ const handleToPosi = id => {
top: -64px;
}
:deep(.search-container .search-center) {
width: 440px;
gap: 40px;
justify-content: center;
}
.search {
width: 960px;
height: 168px;
......@@ -467,8 +504,6 @@ const handleToPosi = id => {
}
}
.scroll-main {
height: calc(100% - 144px) !important;
}
}
</style>
......@@ -2,7 +2,7 @@
<div class="wrap">
<div class="box1">
<AnalysisBox title="相关政令" :showAllBtn="false">
<div class="box1-main">
<div class="box1-main" v-loading="isLoading">
<el-empty v-if="!siderList?.length" style="padding: 60px 0;" description="暂无数据" :image-size="100" />
<el-scrollbar height="100%" always>
<div class="left-item" :class="{ 'item-active': false }" v-for="(item, index) in siderList" :key="index" @click="handleClickDecree(item)">
......@@ -18,9 +18,11 @@
</div>
<div class="box2">
<AnalysisBox title="政令关系挖掘" :showAllBtn="false">
<el-empty v-if="!siderList?.length" style="padding: 60px 0;" description="暂无数据" :image-size="100" />
<div class="box2-main" v-if="graphData.nodes?.length">
<GraphChart :nodes="graphData.nodes" :links="graphData.links" layoutType="force" @handleClickNode="handleClickNode" />
<div style="height: 100%; width: 100%;" v-loading="isLoading">
<el-empty v-if="!siderList?.length" style="padding: 60px 0;" description="暂无数据" :image-size="100" />
<div class="box2-main" v-if="graphData.nodes?.length">
<GraphChart :nodes="graphData.nodes" :links="graphData.links" layoutType="force" @handleClickNode="handleClickNode" />
</div>
</div>
</AnalysisBox>
</div>
......@@ -28,7 +30,7 @@
<el-dialog v-model="dialogVisible" width="1000px" class="viewpoint-dialog">
<template #header>
<div class="viewpoint-header">
<div class="viewpoint-title">冲突关系</div>
<div class="viewpoint-title">关联关系</div>
</div>
</template>
<div class="viewpoint-body">
......@@ -61,7 +63,7 @@ import icon1629 from "./assets/icons/icon1629.png";
const route = useRoute();
// 冲突关系
// 关联关系
const dialogVisible = ref(false);
// 基本信息
......@@ -123,13 +125,16 @@ const handleClickNode = ({data}) => {
if (node) handleClickDecree(node)
}
}
const isLoading = ref(false);
const initGraphChart = () => {
isLoading.value = true;
Promise.all([onDecreeSummaryData(), handleGetRelateOrder()]).then(() => {
if (mainInfo.value.id && siderList.value.length) {
graphData.links = siderList.value.map(onFormatLink)
graphData.nodes = siderList.value.map(onFormatNode)
graphData.nodes.unshift(onFormatNode(mainInfo.value))
}
isLoading.value = false;
})
}
const onFormatLink = (item, index) => {
......@@ -185,7 +190,7 @@ const handleClickDecree = decree => {
// })
};
// 冲突关系
// 关联关系
const graphContainer = ref(null);
let graph = null;
const onRelationChart = () => {
......
......@@ -183,7 +183,7 @@ const headerChartData = (row) => {
switch (contentType.value) {
case 1:
onDecreeRelatedChain(row.id)
onDecreeRelatedChain(row.orgId)
break;
case 2:
onDecreeRelatedEntitie(row.orgId)
......
......@@ -384,7 +384,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane :aiContent="radarChart.loading ? '解读生成中...' : radarChart.interpretation" />
<AiPane :aiContent="radarChart.interpretation" />
</div>
</template>
</custom-container>
......@@ -409,7 +409,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane :aiContent="trendChart.loading ? '解读生成中...' : trendChart.interpretation" />
<AiPane :aiContent="trendChart.interpretation" />
</div>
</template>
</custom-container>
......@@ -830,7 +830,6 @@ const handleToRiskSignalDetail = item => {
});
// 打开新页面
window.open(routeData.href, "_blank");
};
const sanctionList = ref([]);
......@@ -1042,7 +1041,6 @@ const handleToSocialDetail = item => {
}
});
window.open(route.href, "_blank");
};
// 获取趋势图数据
const fetchTrendData = async () => {
......@@ -1180,7 +1178,6 @@ const handleToEntityListNoId = item => {
});
// 打开一个新页面
window.open(routeData.href, "_blank");
} else if (item.nameZh == "商业管制清单") {
const routeData = router.resolve({
path: "/exportControl/commercialControlList",
......@@ -1195,8 +1192,8 @@ const handleToEntityListNoId = item => {
}
};
const billList = ref([]);
const curBillListIndex = ref(0);
// const billList = ref([]);
// const curBillListIndex = ref(0);
const searchExportControlText = ref("");
const infoListColor = ref(["rgba(206, 79, 81, 1)", "rgba(114, 46, 209, 1)", "rgba(132, 136, 142, 1)", "rgba(132, 136, 142, 1)"]);
......@@ -1391,8 +1388,8 @@ const fetchSanctionList = async () => {
const tags = Array.isArray(item.techDomains)
? item.techDomains
: item.techDomain
? [item.techDomain]
: item.techDomainList || [];
? [item.techDomain]
: item.techDomainList || [];
const fullTime = item.startTime
? formatAnyDateToChinese(item.startTime)
......@@ -1422,8 +1419,8 @@ const fetchSanctionList = async () => {
countTag: item.cnEntityCount
? `${item.cnEntityCount}家中国实体`
: item.ruleOrgCount
? `${item.ruleOrgCount}家关联实体`
: item.countTag || ""
? `${item.ruleOrgCount}家关联实体`
: item.countTag || ""
};
});
totalAll.value = res.totalElements;
......@@ -1666,12 +1663,11 @@ const handlePerClick = item => {
const route = router.resolve({
path: "/characterPage",
query: {
type: item.type || [1, 2, 3][Math.floor(Math.random() * 3)],
type: item.personType || [1, 2, 3][Math.floor(Math.random() * 3)],
personId: item.personId
}
});
window.open(route.href, "_blank");
};
// 处理点击社交媒体消息的方法
// const handleInfoClick = item => {
......@@ -1751,17 +1747,16 @@ const chart1Data = ref({
});
const handleSanc = item => {
console.log(item);
console.log("activeResourceTabItem.value.id", activeResourceTabItem.value.id);
window.sessionStorage.setItem("curTabName", `${item.postDate}${item.title}》`);
const route = router.resolve({
path: "/exportControl/singleSanction",
query: {
id: item.id,
sanTypeId: activeResourceTabItem.value.id
sanTypeId: activeResourceTabItem.value.id.join(",")
}
});
window.open(route.href, "_blank");
};
// 查看更多风险信号
......@@ -2368,8 +2363,7 @@ const handleMediaClick = item => {
overflow-y: auto;
.home-top-bg {
background:
url("./assets/images/background.png"),
background: url("./assets/images/background.png"),
linear-gradient(180deg, rgba(229, 241, 254, 1) 0%, rgba(246, 251, 255, 0) 30%);
background-size: 100% 100%;
position: absolute;
......
......@@ -60,7 +60,7 @@
<div class="list-content" v-for="(ele, j) in element.cclChildren" :key="j">
<div class="content-title" @click="ele.isExpand = !ele.isExpand">
<div class="code-zone">
<!-- <div class="dot" v-if="ele.isDot"></div> -->
<div class="dot" v-if="ele.changeFlag"></div>
<span class="code">{{ ele.cclCode }}</span>
</div>
<span class="name">{{ ele.cclTitleZh }}</span>
......@@ -121,9 +121,9 @@ const getTechFields = async () => {
const res = await getAreaType();
if (res && res.code === 200) {
console.log("-----getTechFields", res.data);
techFields.value = res.data;
techFields.value = [{ id: "all", name: "全部领域", checked: true }].concat(res.data);
// 默认选中第一个
techFields.value[0].checked = true;
// techFields.value[0].checked = true;
}
} catch (error) {
console.error("获取科技领域字典失败:", error);
......@@ -136,9 +136,9 @@ const getControlReasonList = async () => {
const res = await getControlReason();
if (res && res.code === 200) {
console.log("-----getControlReasonList", res.data);
controlReason.value = res.data;
controlReason.value = [{ id: "all", name: "全部", checked: true }].concat(res.data);
// 默认选中第一个
controlReason.value[0].checked = true;
// controlReason.value[0].checked = true;
}
} catch (error) {
console.error("获取管控原因字典失败:", error);
......@@ -151,8 +151,19 @@ const viewNew = ref(true);
// 获取ccl清单列表
const getCclList = async () => {
let techDomains = techFields.value.filter(item => item.checked).map(item => +item.id);
let controls = controlReason.value.filter(item => item.checked).map(item => +item.id);
let techDomains = [];
const allTech = techFields.value.find(item => item.id === "all"); // ✅ 修正点1
if (!allTech || !allTech.checked) {
techDomains = techFields.value.filter(item => item.checked && item.id !== "all").map(item => item.id); // 注意:这里 map 的是 value,假设后端需要的是 value 字段
}
let controls = [];
const allReason = controlReason.value.find(item => item.id === "all"); // ✅ 修正点2
if (!allReason || !allReason.checked) {
controls = controlReason.value.filter(item => item.checked && item.id !== "all").map(item => item.id);
}
// let techDomains = techFields.value.filter(item => item.checked).map(item => +item.id);
// let controls = controlReason.value.filter(item => item.checked).map(item => +item.id);
const params = {
categoryCode: currentCCLType.value,
techDomainIds: techDomains,
......@@ -161,7 +172,7 @@ const getCclList = async () => {
isLatest: viewNew.value,
recordId: currentCCLVersion.value || ""
};
console.log(JSON.stringify(params));
console.log("cclList参数:", params);
try {
// const res = await getCclQuery(null);
const res = await getCclQuery(params);
......@@ -272,8 +283,34 @@ const getCCLVersionListApi = async () => {
};
// 筛选逻辑处理
const handleFilterChange = (item, list, type) => {
console.log(item, list, type);
const handleFilterChange = (item, listRef, type) => {
const list = listRef;
const allItem = list.find(i => i.id === "all"); // ✅ 关键修正
if (!allItem) return;
if (item.id === "all") {
if (item.checked) {
list.forEach(i => {
if (i.id !== "all") i.checked = false;
});
} else {
const hasOtherChecked = list.some(i => i.id !== "all" && i.checked);
if (!hasOtherChecked && list.length > 1) {
const firstNonAll = list.find(i => i.id !== "all");
if (firstNonAll) firstNonAll.checked = true;
}
}
} else {
if (item.checked) {
allItem.checked = false;
} else {
const hasAnyChecked = list.some(i => i.id !== "all" && i.checked);
if (!hasAnyChecked) {
allItem.checked = true;
}
}
}
getCclList();
};
......@@ -373,6 +410,9 @@ onMounted(async () => {
:deep(.el-input__wrapper) {
padding: 0 11px;
border: 1px solid rgba(0, 0, 0, 0.1);
background-color: #fff;
border-radius: 3px;
}
:deep(.el-input__inner) {
......
......@@ -10,7 +10,7 @@
</div>
<div class="department">{{ headerTitle.department }}</div>
</div>
<div class="btn"><img :src="icon01" alt />切换</div>
<!-- <div class="btn"><img :src="icon01" alt />切换</div> -->
</div>
<div class="header-nav">
<div
......
......@@ -125,7 +125,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane :aiContent="sanctionCountChart.loading ? '解读生成中...' : sanctionCountChart.interpretation" />
<AiPane :aiContent="sanctionCountChart.interpretation" />
</div>
</AnalysisBox>
</div>
......@@ -174,7 +174,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane :aiContent="rankChart.loading ? '解读生成中...' : rankChart.interpretation" />
<AiPane :aiContent="rankChart.interpretation" />
</div>
</AnalysisBox>
</div>
......@@ -206,7 +206,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane :aiContent="domainChart.loading ? '解读生成中...' : domainChart.interpretation" />
<AiPane :aiContent="domainChart.interpretation" />
</div>
</AnalysisBox>
</div>
......@@ -238,7 +238,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane :aiContent="typeChart.loading ? '解读生成中...' : typeChart.interpretation" />
<AiPane :aiContent="typeChart.interpretation" />
</div>
</AnalysisBox>
</div>
......
......@@ -532,6 +532,7 @@ watch(customDateRange, () => {
padding: 0 11px;
border: 1px solid rgba(170, 173, 177, 1);
background-color: #fff;
border-radius: 3px;
}
:deep(.el-input__inner) {
......
......@@ -63,7 +63,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane :aiContent="domainChart.loading ? '解读生成中...' : domainChart.interpretation" />
<AiPane :aiContent="domainChart.interpretation" />
</div>
</AnalysisBox>
</div>
......@@ -113,7 +113,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane :aiContent="typeChart.loading ? '解读生成中...' : typeChart.interpretation" />
<AiPane :aiContent="typeChart.interpretation" />
</div>
</AnalysisBox>
</div>
......@@ -154,11 +154,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane
:aiContent="
countryDistributionChart.loading ? '解读生成中...' : countryDistributionChart.interpretation
"
/>
<AiPane :aiContent="countryDistributionChart.interpretation" />
</div>
</AnalysisBox>
</div>
......@@ -202,11 +198,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane
:aiContent="
regionDistributionChart.loading ? '解读生成中...' : regionDistributionChart.interpretation
"
/>
<AiPane :aiContent="regionDistributionChart.interpretation" />
</div>
</AnalysisBox>
</div>
......
......@@ -146,7 +146,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane :aiContent="revenueChart.loading ? '解读生成中...' : revenueChart.interpretation" />
<AiPane :aiContent="revenueChart.interpretation" />
</div>
</div>
</AnalysisBox>
......@@ -188,7 +188,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane :aiContent="marketChart.loading ? '解读生成中...' : marketChart.interpretation" />
<AiPane :aiContent="marketChart.interpretation" />
</div>
</div>
</AnalysisBox>
......@@ -249,7 +249,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane :aiContent="rdChart.loading ? '解读生成中...' : rdChart.interpretation" />
<AiPane :aiContent="rdChart.interpretation" />
</div>
</div>
</AnalysisBox>
......@@ -310,7 +310,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane :aiContent="shareChart.loading ? '解读生成中...' : shareChart.interpretation" />
<AiPane :aiContent="shareChart.interpretation" />
</div>
</div>
</AnalysisBox>
......
......@@ -60,13 +60,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane
:aiContent="
rdInstrumentDependencyChart.loading
? '解读生成中...'
: rdInstrumentDependencyChart.interpretation
"
/>
<AiPane :aiContent="rdInstrumentDependencyChart.interpretation" />
</div>
</div>
</AnalysisBox>
......@@ -102,13 +96,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane
:aiContent="
rdInstrumentImportCountryChart.loading
? '解读生成中...'
: rdInstrumentImportCountryChart.interpretation
"
/>
<AiPane :aiContent="rdInstrumentImportCountryChart.interpretation" />
</div>
</div>
</AnalysisBox>
......@@ -177,13 +165,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane
:aiContent="
internationalCooperationChart.loading
? '解读生成中...'
: internationalCooperationChart.interpretation
"
/>
<AiPane :aiContent="internationalCooperationChart.interpretation" />
</div>
</div>
</AnalysisBox>
......@@ -252,11 +234,7 @@
</div>
<div class="ai-pane">
<AiButton />
<AiPane
:aiContent="
internationalPaperChart.loading ? '解读生成中...' : internationalPaperChart.interpretation
"
/>
<AiPane :aiContent="internationalPaperChart.interpretation" />
</div>
</div>
</AnalysisBox>
......
......@@ -31,7 +31,7 @@
<div class="info-row">
<div class="label">发布人:</div>
<div class="value link">
<img :src="defaultTitle" alt="" class="icon avatar" />
<img :src="formattedData.avartar || defaultTitle" alt="" class="icon avatar" />
<span @click="handleClick">{{ formattedData.postPersonName }} ></span>
</div>
</div>
......@@ -46,13 +46,16 @@
<div class="content-title">制裁实体分布:</div>
<div class="distribution-list">
<div class="list-item" v-for="(item, index) in entityDistribution" :key="index">
<img :src="flag" alt="" class="flag" />
<img :src="item.imageUrl || flag" alt="" class="flag" />
<div class="country-name">{{ item.name }}</div>
<div class="progress-bar-container">
<div class="progress-bar" :style="{
width: item.width,
background: item.gradient
}"></div>
<div
class="progress-bar"
:style="{
width: item.width,
background: item.gradient
}"
></div>
</div>
<div class="count" :class="{ highlight: index === 0 }">{{ item.count }}</div>
</div>
......@@ -95,13 +98,25 @@
</div>
<div class="filter-right">
<el-checkbox v-model="onlyChina" label="只看中国实体" />
<el-select v-model="filterField" placeholder="全部领域" style="width: 150px; margin: 0 12px 0 16px">
<el-select
v-model="filterField"
placeholder="全部领域"
style="width: 150px; margin: 0 12px 0 16px"
>
<el-option label="全部领域" value="" />
<el-option v-for="item in domainOptions" :key="item.value" :label="item.label" :value="item.value" />
<el-option
v-for="item in domainOptions"
:key="item.value"
:label="item.label"
:value="item.value"
/>
</el-select>
<el-input v-model="searchKeyword" placeholder="搜索实体"
<el-input
v-model="searchKeyword"
placeholder="搜索实体"
style="width: 150px; border: 1px solid rgba(170, 173, 177, 0.4); border-radius: 5px"
:suffix-icon="Search" />
:suffix-icon="Search"
/>
</div>
</div>
<div class="stats-row">
......@@ -116,20 +131,28 @@
<div class="stats-info">
<div class="stat-item">
<span class="dot red"></span>
<span class="text">新增 <span class="num red">{{ addCount }}</span> 家 (50%规则涉及<span class="num red">{{
addRuleCount
}}</span>家)</span>
<span class="text"
>新增 <span class="num red">{{ addCount }}</span> 家 (50%规则涉及<span class="num red">{{
addRuleCount
}}</span
>家)</span
>
</div>
<div class="stat-item">
<span class="dot green"></span>
<span class="text">移除 <span class="num green">{{ removeCount }}</span> 家 (50%规则涉及<span
class="num green">{{ removeRuleCount }}</span>家)</span>
<span class="text"
>移除 <span class="num green">{{ removeCount }}</span> 家 (50%规则涉及<span
class="num green"
>{{ removeRuleCount }}</span
>家)</span
>
</div>
</div>
</div>
</div>
<div class="right-content">
<div class="sanction-group-list">
<el-empty v-if="sanctionList.length === 0" description="暂无制裁清单" />
<div class="sanction-group" v-for="(group, index) in sanctionList" :key="index">
<el-table :data="group.entities" style="width: 100%">
<el-table-column label="实体名称" min-width="280">
......@@ -145,8 +168,14 @@
</el-table-column>
<el-table-column label="涉及领域" width="180" align="center">
<template #default="scope">
<span v-for="(item, index) in scope.row.fields" :key="index" class="tag"
:style="getTagStyle(item)" style="margin: 0 2px">{{ item }}</span>
<span
v-for="(item, index) in scope.row.fields"
:key="index"
class="tag"
:style="getTagStyle(item)"
style="margin: 0 2px"
>{{ item }}</span
>
</template>
</el-table-column>
<el-table-column prop="location" label="上市地点" width="90" align="center" />
......@@ -154,8 +183,11 @@
<el-table-column prop="revenue" label="营收(亿元)" width="110" align="center" />
<el-table-column label="50%规则子企业" width="180" align="center">
<template #default="scope">
<span v-if="scope.row.subsidiaryCount" class="subsidiary-link"
@click="handleSubsidiaryClick(scope.row)">
<span
v-if="scope.row.subsidiaryCount"
class="subsidiary-link"
@click="handleSubsidiaryClick(scope.row)"
>
{{ scope.row.subsidiaryText }}
<span class="blue-text">{{ scope.row.subsidiaryCount }}家 ></span>
</span>
......@@ -173,8 +205,12 @@
</div>
</div>
<!-- 50%规则子企业弹框 -->
<RuleSubsidiaryDialog v-model="subsidiaryDialogVisible" :company-name="currentSubsidiaryCompanyName"
:total-count="currentSubsidiaryCount" :data-list="currentSubsidiaryList" />
<RuleSubsidiaryDialog
v-model="subsidiaryDialogVisible"
:company-name="currentSubsidiaryCompanyName"
:total-count="currentSubsidiaryCount"
:data-list="currentSubsidiaryList"
/>
</div>
</template>
......@@ -267,7 +303,7 @@ const getSanctionOverviewList = async () => {
removeCount.value = data.removeCount || 0;
removeRuleCount.value = data.removeRuleCount || 0;
const list = data.sanList || [];
const list = activeTab.value === "add" ? data.sanList : data.removeList || [];
sanctionList.value = list.map(item => ({
reason: item.sanReason,
entities: (item.orgList || []).map(org => ({
......@@ -281,8 +317,8 @@ const getSanctionOverviewList = async () => {
subsidiaryText:
org.ruleOrgList && org.ruleOrgList.length > 0
? (org.ruleOrgList[0].orgName.length > 10
? org.ruleOrgList[0].orgName.slice(0, 10) + "..."
: org.ruleOrgList[0].orgName) + "...等"
? org.ruleOrgList[0].orgName.slice(0, 10) + "..."
: org.ruleOrgList[0].orgName) + "...等"
: ""
}))
}));
......@@ -342,10 +378,12 @@ const getUrlParams = () => {
// 单次制裁-制裁概况-制裁实体国家分布
const getEntityCountry = async () => {
try {
const res = await getSingleSanctionEntityCountry({
const params = {
sanRecordId: sanRecordId.value,
sanTypeId: sanTypeId.value || 1 // 实体清单固定1
});
sanTypeId: sanTypeId.value || 1 // 默认为1
};
console.log("params --:", params);
const res = await getSingleSanctionEntityCountry(params);
if (res.code === 200) {
const rawData = res.data || [];
const maxCount = Math.max(...rawData.map(item => item.count || 0), 1);
......@@ -413,7 +451,8 @@ const formattedData = computed(() => {
fileCode: info.fileCode ? `${info.fileCode} ` : "",
administrativeOrderId: info.administrativeOrderId ? `No. ${info.administrativeOrderId}` : "",
postPersonName: info.postPersonName,
domains: info.domainNames
domains: info.domainNames,
avartar: info.postPersonAvatarUrl
};
});
......@@ -510,6 +549,7 @@ const entityDistribution = ref([
const sanTypeId = ref("");
onMounted(() => {
// 获取路由参数中的sanTypeId
console.log("route.query.sanTypeId --:", route.query.sanTypeId);
sanTypeId.value = route.query.sanTypeId || "1";
// 获取URL参数
getUrlParams();
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论