Add new JSON data file and enhance simulation management features
- Introduced a new JSON data file containing detailed actions and quotes related to the 武大声誉修复基金 initiative. - Updated the OasisProfileGenerator to ensure compatibility with the new JSON format, emphasizing the inclusion of user_id. - Modified simulation management to support independent tracking of Twitter and Reddit platforms, including completion status and round information. - Enhanced the SimulationRunner to accurately reflect the completion state of each platform and added checks for overall simulation completion. - Improved the GraphPanel and Step3Simulation components to provide real-time updates and better user feedback during simulations.
This commit is contained in:
@@ -19,10 +19,15 @@
|
||||
<div v-if="graphData" class="graph-view">
|
||||
<svg ref="graphSvg" class="graph-svg"></svg>
|
||||
|
||||
<!-- 构建中提示 -->
|
||||
<div v-if="currentPhase === 1" class="graph-building-hint">
|
||||
<span class="building-dot"></span>
|
||||
实时更新中...
|
||||
<!-- 构建中/模拟中提示 -->
|
||||
<div v-if="currentPhase === 1 || isSimulating" class="graph-building-hint">
|
||||
<div class="memory-icon-wrapper">
|
||||
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" class="memory-icon">
|
||||
<path d="M9.5 2A2.5 2.5 0 0 1 12 4.5v15a2.5 2.5 0 0 1-4.96.44 2.5 2.5 0 0 1-2.96-3.08 3 3 0 0 1-.34-5.58 2.5 2.5 0 0 1 1.32-4.24 2.5 2.5 0 0 1 4.44-4.04z" />
|
||||
<path d="M14.5 2A2.5 2.5 0 0 0 12 4.5v15a2.5 2.5 0 0 0 4.96.44 2.5 2.5 0 0 0 2.96-3.08 3 3 0 0 0 .34-5.58 2.5 2.5 0 0 0-1.32-4.24 2.5 2.5 0 0 0-4.44-4.04z" />
|
||||
</svg>
|
||||
</div>
|
||||
{{ isSimulating ? 'GraphRAG长短期记忆实时更新中' : '实时更新中...' }}
|
||||
</div>
|
||||
|
||||
<!-- 节点/边详情面板 -->
|
||||
@@ -219,7 +224,8 @@ import * as d3 from 'd3'
|
||||
const props = defineProps({
|
||||
graphData: Object,
|
||||
loading: Boolean,
|
||||
currentPhase: Number
|
||||
currentPhase: Number,
|
||||
isSimulating: Boolean
|
||||
})
|
||||
|
||||
const emit = defineEmits(['refresh', 'toggle-maximize'])
|
||||
@@ -1153,30 +1159,41 @@ input:checked + .slider:before {
|
||||
/* Building hint */
|
||||
.graph-building-hint {
|
||||
position: absolute;
|
||||
bottom: 80px;
|
||||
bottom: 160px; /* Moved up from 80px */
|
||||
left: 50%;
|
||||
transform: translateX(-50%);
|
||||
background: rgba(0,0,0,0.75);
|
||||
background: rgba(0, 0, 0, 0.65);
|
||||
backdrop-filter: blur(8px);
|
||||
color: #fff;
|
||||
padding: 8px 16px;
|
||||
border-radius: 20px;
|
||||
font-size: 12px;
|
||||
padding: 10px 20px;
|
||||
border-radius: 30px;
|
||||
font-size: 13px;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 8px;
|
||||
gap: 10px;
|
||||
box-shadow: 0 4px 20px rgba(0, 0, 0, 0.15);
|
||||
border: 1px solid rgba(255, 255, 255, 0.1);
|
||||
font-weight: 500;
|
||||
letter-spacing: 0.5px;
|
||||
z-index: 100;
|
||||
}
|
||||
|
||||
.building-dot {
|
||||
width: 8px;
|
||||
height: 8px;
|
||||
background: #4CAF50;
|
||||
border-radius: 50%;
|
||||
animation: pulse 1.5s ease-in-out infinite;
|
||||
.memory-icon-wrapper {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
animation: breathe 2s ease-in-out infinite;
|
||||
}
|
||||
|
||||
@keyframes pulse {
|
||||
0%, 100% { opacity: 1; transform: scale(1); }
|
||||
50% { opacity: 0.5; transform: scale(0.8); }
|
||||
.memory-icon {
|
||||
width: 18px;
|
||||
height: 18px;
|
||||
color: #4CAF50;
|
||||
}
|
||||
|
||||
@keyframes breathe {
|
||||
0%, 100% { opacity: 0.7; transform: scale(1); filter: drop-shadow(0 0 2px rgba(76, 175, 80, 0.3)); }
|
||||
50% { opacity: 1; transform: scale(1.15); filter: drop-shadow(0 0 8px rgba(76, 175, 80, 0.6)); }
|
||||
}
|
||||
|
||||
/* Loading spinner */
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -41,6 +41,7 @@
|
||||
:graphData="graphData"
|
||||
:loading="graphLoading"
|
||||
:currentPhase="3"
|
||||
:isSimulating="isSimulating"
|
||||
@refresh="refreshGraph"
|
||||
@toggle-maximize="toggleMaximize('graph')"
|
||||
/>
|
||||
@@ -65,7 +66,7 @@
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
import { ref, computed, onMounted } from 'vue'
|
||||
import { ref, computed, onMounted, onUnmounted, watch } from 'vue'
|
||||
import { useRoute, useRouter } from 'vue-router'
|
||||
import GraphPanel from '../components/GraphPanel.vue'
|
||||
import Step3Simulation from '../components/Step3Simulation.vue'
|
||||
@@ -117,6 +118,8 @@ const statusText = computed(() => {
|
||||
return 'Running'
|
||||
})
|
||||
|
||||
const isSimulating = computed(() => currentStatus.value === 'processing')
|
||||
|
||||
// --- Helpers ---
|
||||
const addLog = (msg) => {
|
||||
const time = new Date().toLocaleTimeString('en-US', { hour12: false, hour: '2-digit', minute: '2-digit', second: '2-digit' }) + '.' + new Date().getMilliseconds().toString().padStart(3, '0')
|
||||
@@ -182,12 +185,19 @@ const loadSimulationData = async () => {
|
||||
}
|
||||
|
||||
const loadGraph = async (graphId) => {
|
||||
graphLoading.value = true
|
||||
// 当正在模拟时,自动刷新不显示全屏 loading,以免闪烁
|
||||
// 手动刷新或初始加载时显示 loading
|
||||
if (!isSimulating.value) {
|
||||
graphLoading.value = true
|
||||
}
|
||||
|
||||
try {
|
||||
const res = await getGraphData(graphId)
|
||||
if (res.success) {
|
||||
graphData.value = res.data
|
||||
addLog('图谱数据加载成功')
|
||||
if (!isSimulating.value) {
|
||||
addLog('图谱数据加载成功')
|
||||
}
|
||||
}
|
||||
} catch (err) {
|
||||
addLog(`图谱加载失败: ${err.message}`)
|
||||
@@ -202,6 +212,32 @@ const refreshGraph = () => {
|
||||
}
|
||||
}
|
||||
|
||||
// --- Auto Refresh Logic ---
|
||||
let graphRefreshTimer = null
|
||||
|
||||
const startGraphRefresh = () => {
|
||||
if (graphRefreshTimer) return
|
||||
addLog('开启图谱实时刷新 (30s)')
|
||||
// 立即刷新一次,然后每30秒刷新
|
||||
graphRefreshTimer = setInterval(refreshGraph, 30000)
|
||||
}
|
||||
|
||||
const stopGraphRefresh = () => {
|
||||
if (graphRefreshTimer) {
|
||||
clearInterval(graphRefreshTimer)
|
||||
graphRefreshTimer = null
|
||||
addLog('停止图谱实时刷新')
|
||||
}
|
||||
}
|
||||
|
||||
watch(isSimulating, (newValue) => {
|
||||
if (newValue) {
|
||||
startGraphRefresh()
|
||||
} else {
|
||||
stopGraphRefresh()
|
||||
}
|
||||
}, { immediate: true })
|
||||
|
||||
onMounted(() => {
|
||||
addLog('SimulationRunView 初始化')
|
||||
|
||||
@@ -212,6 +248,10 @@ onMounted(() => {
|
||||
|
||||
loadSimulationData()
|
||||
})
|
||||
|
||||
onUnmounted(() => {
|
||||
stopGraphRefresh()
|
||||
})
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
|
||||
Reference in New Issue
Block a user