A complete blockchain implementation featuring: - synord: Full node with GHOSTDAG consensus - explorer-web: Modern React blockchain explorer with 3D DAG visualization - CLI wallet and tools - Smart contract SDK and example contracts (DEX, NFT, token) - WASM crypto library for browser/mobile
88 lines
2.2 KiB
TypeScript
88 lines
2.2 KiB
TypeScript
/**
|
|
* DAG visualization utilities for 3D rendering.
|
|
* Transforms API data to react-force-graph-3d format.
|
|
*/
|
|
|
|
import type { DagVisualization, DagBlock, DagEdge } from './types';
|
|
|
|
/** Node format expected by ForceGraph3D */
|
|
export interface GraphNode extends DagBlock {
|
|
id: string;
|
|
val: number; // Node size
|
|
}
|
|
|
|
/** Link format expected by ForceGraph3D */
|
|
export interface GraphLink {
|
|
source: string;
|
|
target: string;
|
|
isSelectedParent: boolean;
|
|
}
|
|
|
|
/** Graph data format for ForceGraph3D */
|
|
export interface GraphData {
|
|
nodes: GraphNode[];
|
|
links: GraphLink[];
|
|
}
|
|
|
|
/** Color scheme for block types */
|
|
export const BLOCK_COLORS = {
|
|
chain: '#8b5cf6', // synor purple (chain blocks)
|
|
blue: '#3b82f6', // blue (honest blocks)
|
|
red: '#ef4444', // red (potentially malicious/delayed)
|
|
hover: '#fbbf24', // amber (hover highlight)
|
|
} as const;
|
|
|
|
/** Edge colors */
|
|
export const EDGE_COLORS = {
|
|
selectedParent: '#fbbf24', // amber
|
|
normal: '#4b5563', // gray-600
|
|
} as const;
|
|
|
|
/**
|
|
* Transform DagVisualization API response to ForceGraph3D format.
|
|
*/
|
|
export function transformToGraphData(dag: DagVisualization): GraphData {
|
|
const nodes: GraphNode[] = dag.blocks.map((block) => ({
|
|
...block,
|
|
id: block.hash,
|
|
val: Math.max(1, block.txCount) * 5, // Node size based on tx count
|
|
}));
|
|
|
|
const links: GraphLink[] = dag.edges.map((edge) => ({
|
|
source: edge.from,
|
|
target: edge.to,
|
|
isSelectedParent: edge.isSelectedParent,
|
|
}));
|
|
|
|
return { nodes, links };
|
|
}
|
|
|
|
/**
|
|
* Get node color based on block type.
|
|
*/
|
|
export function getNodeColor(node: GraphNode | DagBlock): string {
|
|
if (node.isChainBlock) return BLOCK_COLORS.chain;
|
|
if (node.isBlue) return BLOCK_COLORS.blue;
|
|
return BLOCK_COLORS.red;
|
|
}
|
|
|
|
/**
|
|
* Get link color based on relationship type.
|
|
*/
|
|
export function getLinkColor(link: GraphLink | DagEdge): string {
|
|
return link.isSelectedParent ? EDGE_COLORS.selectedParent : EDGE_COLORS.normal;
|
|
}
|
|
|
|
/**
|
|
* Get link width based on relationship type.
|
|
*/
|
|
export function getLinkWidth(link: GraphLink | DagEdge): number {
|
|
return link.isSelectedParent ? 2 : 1;
|
|
}
|
|
|
|
/**
|
|
* Format timestamp for tooltip display.
|
|
*/
|
|
export function formatBlockTime(timestamp: number): string {
|
|
return new Date(timestamp).toLocaleString();
|
|
}
|