fix: 边API响应增加created_at/updated_at,星图展示关系时间戳
This commit is contained in:
@ -808,7 +808,8 @@ def get_graph():
|
|||||||
|
|
||||||
# 查询关系(边)
|
# 查询关系(边)
|
||||||
cursor.execute("""
|
cursor.execute("""
|
||||||
SELECT r.id, r.source_id, r.target_id, r.relation_type, r.confidence, r.status
|
SELECT r.id, r.source_id, r.target_id, r.relation_type,
|
||||||
|
r.confidence, r.status, r.created_at, r.updated_at
|
||||||
FROM relations r
|
FROM relations r
|
||||||
WHERE r.status = 'active'
|
WHERE r.status = 'active'
|
||||||
""")
|
""")
|
||||||
@ -821,7 +822,9 @@ def get_graph():
|
|||||||
"target": row['target_id'],
|
"target": row['target_id'],
|
||||||
"relation_type": row['relation_type'],
|
"relation_type": row['relation_type'],
|
||||||
"confidence": row['confidence'],
|
"confidence": row['confidence'],
|
||||||
"status": row['status']
|
"status": row['status'],
|
||||||
|
"created_at": row['created_at'],
|
||||||
|
"updated_at": row['updated_at']
|
||||||
})
|
})
|
||||||
|
|
||||||
return jsonify({
|
return jsonify({
|
||||||
|
|||||||
@ -548,6 +548,7 @@
|
|||||||
let currentHighlightIds = [];
|
let currentHighlightIds = [];
|
||||||
let currentHighlightEdgeIds = new Set(); // 存储高亮的边ID
|
let currentHighlightEdgeIds = new Set(); // 存储高亮的边ID
|
||||||
let edgeParticles = {}; // 存储边的流动光点 {edgeId: {mesh, progress, edge}}
|
let edgeParticles = {}; // 存储边的流动光点 {edgeId: {mesh, progress, edge}}
|
||||||
|
let edgeLabels = []; // 存储边标签
|
||||||
|
|
||||||
// 颜色映射
|
// 颜色映射
|
||||||
const typeColors = {
|
const typeColors = {
|
||||||
@ -812,11 +813,13 @@ function init() {
|
|||||||
// 清除旧的对象(包括边粒子)
|
// 清除旧的对象(包括边粒子)
|
||||||
nodeMeshes.forEach(mesh => scene.remove(mesh));
|
nodeMeshes.forEach(mesh => scene.remove(mesh));
|
||||||
edgeLines.forEach(line => scene.remove(line));
|
edgeLines.forEach(line => scene.remove(line));
|
||||||
|
edgeLabels.forEach(label => scene.remove(label));
|
||||||
Object.keys(edgeParticles).forEach(key => {
|
Object.keys(edgeParticles).forEach(key => {
|
||||||
scene.remove(edgeParticles[key].mesh);
|
scene.remove(edgeParticles[key].mesh);
|
||||||
});
|
});
|
||||||
nodeMeshes = [];
|
nodeMeshes = [];
|
||||||
edgeLines = [];
|
edgeLines = [];
|
||||||
|
edgeLabels = [];
|
||||||
edgeParticles = {};
|
edgeParticles = {};
|
||||||
|
|
||||||
if (nodes.length === 0) return;
|
if (nodes.length === 0) return;
|
||||||
@ -1081,6 +1084,53 @@ function init() {
|
|||||||
|
|
||||||
scene.add(line);
|
scene.add(line);
|
||||||
edgeLines.push(line);
|
edgeLines.push(line);
|
||||||
|
|
||||||
|
// 边标签(中间位置显示关系类型 + 时间戳)
|
||||||
|
const midX = (pos1.x + pos2.x) / 2;
|
||||||
|
const midY = (pos1.y + pos2.y) / 2;
|
||||||
|
const midZ = (pos1.z + pos2.z) / 2;
|
||||||
|
|
||||||
|
const labelCanvas = document.createElement('canvas');
|
||||||
|
const labelCtx = labelCanvas.getContext('2d');
|
||||||
|
labelCanvas.width = 256;
|
||||||
|
labelCanvas.height = 48;
|
||||||
|
labelCtx.clearRect(0, 0, labelCanvas.width, labelCanvas.height);
|
||||||
|
|
||||||
|
// 时间戳文本
|
||||||
|
const ts = edge.created_at || '';
|
||||||
|
const tsShort = ts ? ts.substring(0, 10) : '';
|
||||||
|
let labelText = edge.relation_type;
|
||||||
|
if (tsShort) labelText += '\n' + tsShort;
|
||||||
|
|
||||||
|
labelCtx.font = '16px Courier New';
|
||||||
|
labelCtx.fillStyle = color;
|
||||||
|
labelCtx.textAlign = 'center';
|
||||||
|
labelCtx.shadowColor = color;
|
||||||
|
labelCtx.shadowBlur = 4;
|
||||||
|
labelCtx.fillText(edge.relation_type, 128, 20);
|
||||||
|
if (tsShort) {
|
||||||
|
labelCtx.font = '12px Courier New';
|
||||||
|
labelCtx.fillStyle = '#999999';
|
||||||
|
labelCtx.fillText(tsShort, 128, 38);
|
||||||
|
}
|
||||||
|
|
||||||
|
const labelTex = new THREE.CanvasTexture(labelCanvas);
|
||||||
|
labelTex.needsUpdate = true;
|
||||||
|
const labelMat = new THREE.SpriteMaterial({
|
||||||
|
map: labelTex,
|
||||||
|
transparent: true,
|
||||||
|
opacity: 0.7,
|
||||||
|
depthTest: false,
|
||||||
|
depthWrite: false,
|
||||||
|
blending: THREE.AdditiveBlending
|
||||||
|
});
|
||||||
|
const edgeLabel = new THREE.Sprite(labelMat);
|
||||||
|
edgeLabel.scale.set(5, 1, 1);
|
||||||
|
edgeLabel.position.set(midX, midY, midZ);
|
||||||
|
edgeLabel.userData = { edgeId: edge.id };
|
||||||
|
|
||||||
|
scene.add(edgeLabel);
|
||||||
|
edgeLabels.push(edgeLabel);
|
||||||
});
|
});
|
||||||
|
|
||||||
// 调整相机位置以适应所有节点
|
// 调整相机位置以适应所有节点
|
||||||
|
|||||||
Reference in New Issue
Block a user