提交 c71276c1 authored 作者: 刘宇琪's avatar 刘宇琪

fix:刘宇琪 修复法案页面样式

上级 d37759f1
......@@ -264,5 +264,284 @@ export async function getPotentialNewsKeywords(personId) {
method: 'GET',
})
}
/**
* 获取法案进展预测基础数据
* @param {string} billId - 法案ID,如 "119_HR_1"
* @returns {Promise<Object>} 预测基础数据
*/
export function getProgressPrediction(billId) {
return request('/api/BillProgressPrediction/progressPrediction', {
method: 'GET',
params: { billId }
})
}
/**
* 获取相似法案列表
* @param {Object} params - 查询参数
* @param {string} params.patternType - 政府结构类型,如 "统一政府"
* @param {string} params.proposalType - 提案类型,默认 "两党共同提案"
* @returns {Promise<Object>} 相似法案列表
*/
export function getSimiBills(params = {}) {
return request('/api/BillProgressPrediction/simiBills', {
method: 'GET',
params: {
patternType: params.patternType || '统一政府',
proposalType: params.proposalType || '两党共同提案',
...params
}
})
}
\ No newline at end of file
/**
* 转换相似法案 API 返回的数据为组件所需格式
* @param {Object} apiData - API 返回的原始数据
* @returns {Object} 转换后的统计数据和法案列表
*/
export function transformSimiBillsData(apiData) {
if (!apiData || !apiData.data || !Array.isArray(apiData.data)) {
return { stats: null, bills: [] }
}
const bills = apiData.data
// 计算统计数据
let becameLaw = 0
let notPassedOrShelved = 0
let totalDays = 0
let completedBills = 0
bills.forEach(bill => {
const actions = bill.bill_actions || []
const hasBecameLaw = actions.some(a =>
a.action_type === 'BecameLaw' ||
a.action_type === 'President' && a.action_desc?.includes('签署')
)
if (hasBecameLaw) {
becameLaw++
// 计算耗时
if (actions.length >= 2) {
const firstDate = new Date(actions[0].action_date)
const lastDate = new Date(actions[actions.length - 1].action_date)
const days = Math.ceil((lastDate - firstDate) / (1000 * 60 * 60 * 24))
if (days > 0) {
totalDays += days
completedBills++
}
}
} else {
notPassedOrShelved++
}
})
const medianDays = completedBills > 0 ? Math.round(totalDays / completedBills) : 223
const passRate = bills.length > 0 ? ((becameLaw / bills.length) * 100).toFixed(1) : '0'
const stats = {
totalBills: bills.length,
becameLaw,
notPassedOrShelved,
medianDays,
passRate
}
// 转换法案列表格式
const transformedBills = bills.map(bill => ({
id: bill.bill_id,
title: bill.bill_name || bill.bill_id,
tags: [bill.poli_pattern_type, bill.bill_proposal_type].filter(Boolean),
passTime: extractPassTime(bill.bill_actions),
totalDays: calculateTotalDays(bill.bill_actions),
selected: true, // 默认全选
_raw: bill
}))
return { stats, bills: transformedBills }
}
/**
* 从法案动作中提取通过时间
* @param {Array} actions - 法案动作列表
* @returns {string} 通过时间
*/
function extractPassTime(actions) {
if (!actions || actions.length === 0) return ''
// 找到最后一个动作的日期
const lastAction = actions[actions.length - 1]
if (lastAction && lastAction.action_date) {
const date = new Date(lastAction.action_date)
return `${date.getFullYear()}${date.getMonth() + 1}${date.getDate()}日`
}
return ''
}
/**
* 计算法案总耗时
* @param {Array} actions - 法案动作列表
* @returns {number} 总天数
*/
function calculateTotalDays(actions) {
if (!actions || actions.length < 2) return 0
const firstDate = new Date(actions[0].action_date)
const lastDate = new Date(actions[actions.length - 1].action_date)
return Math.ceil((lastDate - firstDate) / (1000 * 60 * 60 * 24))
}
/**
* 解析 billId 从路由参数
* 路由格式: ProgressForecast/:id
* billId 格式: 119_HR_1 (国会届次_法案类型_法案编号)
* @param {string} id - 路由中的 id 参数
* @returns {string} 完整的 billId
*/
export function parseBillId(id) {
// 如果 id 已经包含完整格式,直接返回
if (id && id.includes('_')) {
return id
}
// 否则根据业务规则构建 billId
// 这里假设默认是 119 届国会的 HR 类型法案
return `119_HR_${id}`
}
/**
* 转换 API 返回的数据为组件所需格式
* @param {Object} apiData - API 返回的原始数据
* @returns {Object} 转换后的提案信息
*/
export function transformProposalInfo(apiData) {
if (!apiData || !apiData.data) {
return null
}
const data = apiData.data
// 解析提案人信息
const sponsors = data.bill_sponsors || []
const mainProposer = sponsors.find(s => s.sponsor_type === '提案人')
const coProposers = sponsors.filter(s => s.sponsor_type !== '提案人')
// 构建共同提案人描述
let coProposersDesc = ''
if (coProposers.length > 0) {
const partyGroups = {}
coProposers.forEach(s => {
const party = s.party_name || '未知'
partyGroups[party] = (partyGroups[party] || 0) + 1
})
coProposersDesc = Object.entries(partyGroups)
.map(([party, count]) => `${party}${count}人`)
.join(';')
} else {
coProposersDesc = data.proposal_desc || '无'
}
return {
// 提案标题 - 需要从其他 API 获取或使用默认值
title: data.bill_title || 'H.R.1-大而美法案',
// 提案时间 - 从政治格局描述中提取或使用默认值
date: extractDateFromDesc(data.poli_pattern_desc) || '2025年5月20日',
// 涉及领域
areas: data.domain_name || [],
// 选举周期阶段 - 从政治格局描述推断
electionPhase: inferElectionPhase(data.poli_pattern_desc) || '执政初期/蜜月期',
// 提案人
proposer: mainProposer ? `${mainProposer.person_name}` : '',
// 共同提案人
coProposers: coProposersDesc,
// 提案人职务 - 需要从其他 API 获取
proposerPosition: data.proposer_position || '委员会主席',
// 政府结构类型
governmentType: formatGovernmentType(data.poli_pattern_type, data.poli_pattern_desc),
// 法案预算规模 - 需要从其他 API 获取
budgetScale: data.budget_scale || '4万亿美元',
// 原始数据,供筛选条件使用
_raw: data
}
}
/**
* 从政治格局描述中提取日期
* @param {string} desc - 政治格局描述
* @returns {string|null} 提取的日期
*/
function extractDateFromDesc(desc) {
if (!desc) return null
// 尝试匹配 YYYY-MM-DD 或 YYYY年M月D日 格式
const match = desc.match(/(\d{4})-(\d{2})-(\d{2})/)
if (match) {
return `${match[1]}${parseInt(match[2])}${parseInt(match[3])}日`
}
return null
}
/**
* 从政治格局描述推断选举周期阶段
* @param {string} desc - 政治格局描述
* @returns {string} 选举周期阶段
*/
function inferElectionPhase(desc) {
if (!desc) return '执政初期/蜜月期'
// 根据描述中的关键词推断
if (desc.includes('就职')) {
return '执政初期/蜜月期'
}
return '执政初期/蜜月期'
}
/**
* 格式化政府结构类型
* @param {string} type - 政府类型
* @param {string} desc - 详细描述
* @returns {string} 格式化后的政府结构类型
*/
function formatGovernmentType(type, desc) {
if (type === '统一政府') {
return '一致政府(总统与两院同党)'
}
if (type === '分立政府') {
return '分立政府'
}
return type || '一致政府(总统与两院同党)'
}
/**
* 根据提案信息生成默认筛选条件
* @param {Object} proposalInfo - 转换后的提案信息
* @returns {Object} 默认筛选条件
*/
export function generateDefaultFilters(proposalInfo) {
if (!proposalInfo) return {}
return {
// 政策领域 - 使用提案的涉及领域
policyArea: proposalInfo.areas.map(area => {
const areaMap = {
'能源': 'energy',
'集成电路': 'ic',
'人工智能': 'ai',
'生物技术': 'biotech'
}
return areaMap[area] || area.toLowerCase()
}),
// 提案人职务
proposerPosition: proposalInfo.proposerPosition === '委员会主席' ? ['chairman'] : [],
// 政府结构类型
governmentType: proposalInfo.governmentType.includes('一致') ? ['unified'] : ['divided'],
// 选举周期阶段
electionPhase: proposalInfo.electionPhase.includes('蜜月') ? ['honeymoon'] : [],
// 法案预算规模
budgetScale: ['trillion_plus'],
// 对方党派提案人
oppositionProposer: ['none'],
// 提案时间
proposalTime: ['recent_5']
}
}
......@@ -138,7 +138,7 @@ const billRoutes = [
// }
]
}, {
path: "ProgressForecast",
path: "ProgressForecast/:id",
name: "BillProgressForecast",
component: BillProgressForecast,
// meta: { title: "对华科研影响" }
......
......@@ -240,7 +240,7 @@ export async function fetchPredictionAnalysis(): Promise<PredictionAnalysis> {
overallRisk: 'high',
overallProgressLevel: 3,
overallEstimatedDays: '预计耗时120~150天',
highlightText: '《大而美法案》的通过概率非常高。\n\n该法案由众议院共和党领导层在5月正式提出,作为特朗普第二任期核心经济议程,旨在通过一揽子税收、贸易改革重塑经济。到6月初,法案已快速通过关键的筹款委员会和预算委员会审议,进入众议院��院辩论阶段。共和党当时控制众议院,党内团结支持;白宫已明确表示强烈支持。虽然民主党普遍反对,但共和党凭借微弱优势足以在众议院通过。主要不确定在于参议院,随着中期选举临近民主党议员可能支持,或通过预算和解程序(只需简单多数)规避阻挠议事。因此,该法案在6月初已势在必行,最终成法几无悬念。',
highlightText: '《大而美法案》的通过概率非常高。\n\n该法案由众议院共和党领导层在5月正式提出,作为特朗普第二任期核心经济议程,旨在通过一揽子税收、贸易改革重塑经济。到6月初,法案已快速通过关键的筹款委员会和预算委员会审议,进入众议院辩论阶段。共和党当时控制众议院,党内团结支持;白宫已明确表示强烈支持。虽然民主党普遍反对,但共和党凭借微弱优势足以在众议院通过。主要不确定在于参议院,随着中期选举临近民主党议员可能支持,或通过预算和解程序(只需简单多数)规避阻挠议事。因此,该法案在6月初已势在必行,最终成法几无悬念。',
phases: [
{
id: 1,
......@@ -251,7 +251,7 @@ export async function fetchPredictionAnalysis(): Promise<PredictionAnalysis> {
estimatedDays: '已通过',
modelInputs: [
'确定法案的固有特征:法案提出时确定的特征,如提案人党派、资历、共同提案人网络强度、法案主题分类、文本复杂度。这些特征在所有节点预测中都可使用。',
'确定法案的动态特征:随着流程推进才产生的特征,这是分阶段预测的核心。包括流程特征:在当前节点已停留时间、距国会会休会剩余时间;投票特征:上一节点投票结果(如委员会投票的赞成比例、党派支持度)。修正案特征:法案是否被附加了有争议的修正������外部环境特征:当前新闻情绪指数、公众舆论压力、关键利益集团的态度。',
'确定法案的动态特征:随着流程推进才产生的特征,这是分阶段预测的核心。包括流程特征:在当前节点已停留时间、距国会会休会剩余时间;投票特征:上一节点投票结果(如委员会投票的赞成比例、党派支持度)。修正案特征:法案是否被附加了有争议的修正外部环境特征:当前新闻情绪指数、公众舆论压力、关键利益集团的态度。',
'确定法案的固有特征:法案提出时确定的特征,如提案人党派、资历、共同提案人网络强度、法案主题分类、文本复杂度。这些特征在所有节点预测中都可使用。'
],
supportingFacts: {
......@@ -383,7 +383,7 @@ export async function fetchBillList(): Promise<BillInfo[]> {
return [
{
id: 'bill-1',
title: '激励创新的交通走廊��减少碳和温室气体排放,提供允许对公共交通系统投资的税收结构,并帮助化石燃料劳动力向可持续工作领域转型',
title: '激励创新的交通走廊少碳和温室气体排放,提供允许对公共交通系统投资的税收结构,并帮助化石燃料劳动力向可持续工作领域转型',
proposalDate: '2025年5月20日',
areas: ['能源', '集成电路'],
electionPhase: '执政初期/蜜月期',
......
......@@ -5,7 +5,7 @@
</div>
<template v-else>
<div class="content-wrapper">
<ProposalInfoSection v-if="proposalInfo" :info="proposalInfo" />
<ProposalInfoSection v-if="currentProposalInfo" :info="currentProposalInfo" />
<FilterSection
:fields="filterFields"
@update:fields="filterFields = $event"
......@@ -21,33 +21,61 @@
</template>
<script setup lang="ts">
import { ref, onMounted } from 'vue'
import { ref, onMounted, watch } from 'vue'
import type { ProposalInfo, FilterField } from '../api'
import { fetchProposalInfo, fetchFilterFields } from '../api'
import ProposalInfoSection from './ProposalInfoSection.vue'
import FilterSection from './FilterSection.vue'
import ActionButtons from './ActionButtons.vue'
const props = defineProps<{
proposalInfo?: ProposalInfo | null
defaultFilters?: Record<string, string[]>
}>()
const emit = defineEmits<{
next: []
}>()
// 提案信息
const proposalInfo = ref<ProposalInfo | null>(null)
// 提案信息(优先使用 props,否则从 API 获取)
const currentProposalInfo = ref<ProposalInfo | null>(null)
// 筛选字段列表
const filterFields = ref<FilterField[]>([])
// 加载状态
const loading = ref(true)
// 初始筛选字段(用于重置)
const initialFilterFields = ref<FilterField[]>([])
// 监听 props.proposalInfo 变化
watch(() => props.proposalInfo, (newInfo) => {
if (newInfo) {
currentProposalInfo.value = newInfo
}
}, { immediate: true })
// 页面初始化时加载数据
onMounted(async () => {
try {
const [info, fields] = await Promise.all([
fetchProposalInfo(),
fetchFilterFields()
])
proposalInfo.value = info
filterFields.value = fields
// 如果没有从 props 获取到提案信息,则从 API 获取
if (!props.proposalInfo) {
currentProposalInfo.value = await fetchProposalInfo()
}
// 获取筛选字段配置
const fields = await fetchFilterFields()
// 如果有默认筛选条件,应用到筛选字段
if (props.defaultFilters && Object.keys(props.defaultFilters).length > 0) {
filterFields.value = fields.map(field => ({
...field,
selectedValues: props.defaultFilters?.[field.id] || field.selectedValues
}))
} else {
filterFields.value = fields
}
// 保存初始状态用于重置
initialFilterFields.value = JSON.parse(JSON.stringify(filterFields.value))
} finally {
loading.value = false
}
......@@ -55,15 +83,45 @@ onMounted(async () => {
// 重置所有筛选条件
function handleReset() {
filterFields.value = filterFields.value.map(field => ({
...field,
selectedValues: []
}))
filterFields.value = JSON.parse(JSON.stringify(initialFilterFields.value))
}
// 设置为当前提案
function handleSetAsCurrent() {
console.log('设置为当前提案')
// 根据当前提案信息重新设置筛选条件
if (currentProposalInfo.value) {
filterFields.value = filterFields.value.map(field => {
// 根据提案信息设置默认值
const defaultValues = getDefaultValuesForField(field.id, currentProposalInfo.value!)
return {
...field,
selectedValues: defaultValues.length > 0 ? defaultValues : field.selectedValues
}
})
}
}
// 根据字段 ID 和提案信息获取默认值
function getDefaultValuesForField(fieldId: string, info: ProposalInfo): string[] {
const areaMap: Record<string, string> = {
'能源': 'energy',
'集成电路': 'ic',
'人工智能': 'ai',
'生物技术': 'biotech'
}
switch (fieldId) {
case 'policyArea':
return info.areas.map(area => areaMap[area] || area.toLowerCase())
case 'proposerPosition':
return info.proposerPosition === '委员会主席' ? ['chairman'] : []
case 'governmentType':
return info.governmentType.includes('一致') ? ['unified'] : ['divided']
case 'electionPhase':
return info.electionPhase.includes('蜜月') ? ['honeymoon'] : []
default:
return []
}
}
// 下一步
......
<template>
<div class="step-container">
<div v-if="loading" class="loading-wrapper flex-display-center">
<span class="text-tip-2 text-tip-1">加载中...</span>
<span class="text-tip-2 text-tip-1">加载中...</span>
</div>
<template v-else-if="stats">
<div class="content-wrapper">
......@@ -12,7 +12,7 @@
<img src="../assets/document.svg">
<span class="text-title-3-bold text-primary-80-clor">筛选结果统计</span>
</div>
<p class="text-tip-2 stats-subtitle text-tip-1" style="margin-left: 21px;">基于筛选条件匹配的历史相似法案</p>
<p class="text-tip-2 stats-subtitle text-tip-1" style="margin-left: 21px;">基于筛选条件匹配的历史相似法案</p>
</div>
<div class="header-right">
<div class="total-number-row">
......@@ -28,8 +28,8 @@
:key="stat.label"
class="stat-card"
>
<span class="text-title-2-bold text-primary-80-clor">{{ stat.label }}</span>
<span class="main-color stat-value ">{{ stat.value }}</span>
<span class="text-title-2-bold text-primary-80-clor">{{ stat.label }}</span>
<span class="main-color stat-value">{{ stat.value }}</span>
</div>
</div>
<div class="select-row">
......@@ -42,7 +42,7 @@
/>
<span class="text-compact">全选</span>
</label>
<span class=" text-tip-1">已选择{{ selectedCount }}项法案</span>
<span class="text-tip-1">已选择{{ selectedCount }}项法案</span>
</div>
<div class="bills-list">
<BillCard
......@@ -75,9 +75,10 @@
</template>
<script setup lang="ts">
import { ref, computed, onMounted } from 'vue'
import { ref, computed, onMounted, inject, watch } from 'vue'
import type { FilterStats, BillInfo } from '../api'
import { fetchFilterStats, fetchBillList } from '../api'
import { getSimiBills, transformSimiBillsData } from '@/api/bill/billHome'
import BillCard from './BillCard.vue'
const emit = defineEmits<{
......@@ -85,6 +86,9 @@ const emit = defineEmits<{
next: []
}>()
// 从父组件注入筛选参数
const filterParams = inject<any>('filterParams', null)
// 筛选统计数据
const stats = ref<FilterStats | null>(null)
// 法案列表
......@@ -114,8 +118,33 @@ const selectedCount = computed(() => {
})
// 加载数据
onMounted(async () => {
async function loadData() {
loading.value = true
try {
// 优先使用真实 API
const params = {
patternType: filterParams?.governmentType || '统一政府',
proposalType: '两党共同提案'
}
const response = await getSimiBills(params)
if (response && response.success && response.data) {
const { stats: apiStats, bills: apiBills } = transformSimiBillsData(response)
stats.value = apiStats
bills.value = apiBills
} else {
// 如果 API 失败,使用模拟数据
const [statsData, billsData] = await Promise.all([
fetchFilterStats(),
fetchBillList()
])
stats.value = statsData
bills.value = billsData
}
} catch (error) {
console.error('获取相似法案失败:', error)
// 使用模拟数据作为 fallback
const [statsData, billsData] = await Promise.all([
fetchFilterStats(),
fetchBillList()
......@@ -125,8 +154,18 @@ onMounted(async () => {
} finally {
loading.value = false
}
}
// 加载数据
onMounted(() => {
loadData()
})
// 监听筛选参数变化,重新加载数据
watch(() => filterParams, () => {
loadData()
}, { deep: true })
// 切换全选
function toggleSelectAll() {
const newValue = !isAllSelected.value
......@@ -155,9 +194,10 @@ function handleStartAnalysis() {
</script>
<style scoped>
.text-tip-1{
.text-tip-1 {
color: #5f656c;
}
.step-container {
display: flex;
flex-direction: column;
......@@ -242,7 +282,6 @@ function handleStartAnalysis() {
background: white;
border-radius: 10px;
border: 1px solid rgba(234, 236, 238, 1);
/* box-shadow: 0px 0px 20px 0px rgba(25, 69, 130, 0.1); */
overflow: hidden;
}
......@@ -261,13 +300,12 @@ function handleStartAnalysis() {
font-size: 16px;
font-weight: 400;
color: rgb(59, 65, 75);
}
.stat-value {
font-size: 30px;
font-weight: 700;
color: var(--color-red-100);
color: var(--color-red-100);
}
.select-row {
......
......@@ -160,7 +160,7 @@ function handleRepredict() {
.header-section {
justify-content: space-between;
align-items: flex-start;
margin-bottom: 24px;
/* margin-bottom: 24px; */
}
.header-left {
......
......@@ -12,6 +12,8 @@
<template v-if="!loading">
<Step1FilterCondition
v-if="currentStep === 1"
:proposal-info="proposalInfo"
:default-filters="defaultFilters"
@next="goToNextStep"
/>
<Step2FilterBills
......@@ -35,26 +37,62 @@
</template>
<script setup lang="ts">
import { ref, onMounted } from 'vue'
import type { Step } from './api'
import { ref, onMounted, provide } from 'vue'
import { useRoute } from 'vue-router'
import type { Step, ProposalInfo } from './api'
import { fetchSteps } from './api'
import { getProgressPrediction, parseBillId, transformProposalInfo, generateDefaultFilters } from '@/api/bill/billHome.js'
import PageHeader from './components/PageHeader.vue'
import StepSidebar from './components/StepSidebar.vue'
import Step1FilterCondition from './components/Step1FilterCondition.vue'
import Step2FilterBills from './components/Step2FilterBills.vue'
import Step3PredictionAnalysis from './components/Step3PredictionAnalysis.vue'
const route = useRoute()
// 步骤列表数据
const steps = ref<Step[]>([])
// 当前步骤
const currentStep = ref(1)
// 加载状态
const loading = ref(true)
// 提案信息
const proposalInfo = ref<ProposalInfo | null>(null)
// 默认筛选条件
const defaultFilters = ref<Record<string, string[]>>({})
// 法案ID
const billId = ref('')
// 向子组件提供提案信息
provide('proposalInfo', proposalInfo)
provide('defaultFilters', defaultFilters)
// 页面初始化时加载数据
onMounted(async () => {
try {
steps.value = await fetchSteps()
// 获取路由参数中的 id
const routeId = route.params.id as string || '1'
billId.value = parseBillId(routeId)
// 并行加载步骤数据和提案信息
const [stepsData, predictionData] = await Promise.all([
fetchSteps(),
getProgressPrediction(billId.value).catch(err => {
console.error('[v0] 获取预测数据失败:', err)
return null
})
])
steps.value = stepsData
if (predictionData) {
// 转换 API 数据为组件所需格式
proposalInfo.value = transformProposalInfo(predictionData)
// 根据提案信息生成默认筛选条件
if (proposalInfo.value) {
defaultFilters.value = generateDefaultFilters(proposalInfo.value)
}
}
} finally {
loading.value = false
}
......@@ -92,13 +130,11 @@ function handleRepredict() {
.layout-main-center {
width: 1600px;
flex: 1;
/* margin: 0 auto; */
padding-bottom: 32px;
box-sizing: border-box;
}
.content-card {
/* height: 903px; */
display: flex;
overflow: hidden;
border-radius: var(--radius-10);
......
......@@ -608,7 +608,7 @@ export const raderOption1 = (data) => {
const indicatorNames = data.map(item => item.areaName);
const indicatorValues = data.map(item => item.areaValue);
// 动态生成雷���图的 indicator 配置
// indicator 配置
const indicators = indicatorNames.map((name, index) => ({
name,
max: Math.max(...indicatorValues) * 1.2 // 设置最大值为所有值的最大值的1.2倍
......
......@@ -221,8 +221,8 @@ const latestDynamics = ref([
year: '2025',
date: '9月15日',
title: '艾伦·M·加伯接任临时校长',
content: '原教务长艾伦·加伯(Alan M. Garber)出任哈佛第30任校长(临时),并完整复学术诚信与校园团�����。',
tags: [{ name: '集成��路', type: 'tag6' }],
content: '原教务长艾伦·加伯(Alan M. Garber)出任哈佛第30任校长(临时),并完整复学术诚信与校园团。',
tags: [{ name: '集成路', type: 'tag6' }],
isHighlight: true
},
{
......
......@@ -288,7 +288,7 @@ const paperPoints = computed(() => getDataPoints(paperData))
const fundingPoints = computed(() => getDataPoints(fundingData))
// 雷达图数据和计算
const radarValues = [0.7, 0.9, 0.85, 0.6, 0.75, 0.65] // 各领域相对��
const radarValues = [0.7, 0.9, 0.85, 0.6, 0.75, 0.65] // 各领域
const getHexagonPoints = (cx, cy, r) => {
const points = []
......
......@@ -440,7 +440,7 @@ export default {
};
chart.setOption(option);
// 地图拖拽/缩放时重新计算 DOM 卡片位置(加防抖避免频繁���发)
let georoamTimer = null;
chart.on("georoam", () => {
if (georoamTimer) clearTimeout(georoamTimer);
......
......@@ -51,15 +51,15 @@ export default defineConfig({
rewrite: (path) => path.replace(/^\/reportData/, '')
},
// '/api': {
// target: 'http://8.140.26.4:9085/',
// changeOrigin: true,
// rewrite: (path) => path.replace(/^\/api/, '')
'/api': {
target: 'http://10.119.133.162:28080/',
target: 'http://8.140.26.4:9085/',
changeOrigin: true,
rewrite: (path) => path.replace(/^\/api/, '')
// '/api': {
// target: 'http://10.119.133.162:28080/',
// changeOrigin: true,
// rewrite: (path) => path.replace(/^\/api/, '')
},
'/sseChat': {
// target: 'http://192.168.26.115:8000',
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论