Browse Source
Adds zoom and centering buttons. Implements D3 properly and updates everything to Svelte 5 and CSS styles.master
12 changed files with 1407 additions and 354 deletions
@ -1,30 +1,61 @@
@@ -1,30 +1,61 @@
|
||||
<!-- |
||||
Legend Component |
||||
|
||||
Displays a legend explaining the different node and link types in the |
||||
event network visualization. |
||||
--> |
||||
<script lang="ts"> |
||||
// Optional class name to apply to the legend container |
||||
export let className: string = ""; |
||||
</script> |
||||
|
||||
<div class="leather-legend {className}"> |
||||
<h3 class="text-lg font-bold mb-2 h-leather">Legend</h3> |
||||
<h3 class="h-leather">Legend</h3> |
||||
<ul class="legend-list"> |
||||
<!-- Index event node --> |
||||
<li class="legend-item"> |
||||
<div class="legend-icon"> |
||||
<span class="legend-circle" style="background-color: hsl(200, 70%, 75%)"> |
||||
<span |
||||
class="legend-circle" |
||||
style="background-color: hsl(200, 70%, 75%)" |
||||
> |
||||
<span class="legend-letter">I</span> |
||||
</span> |
||||
<span class="legend-letter">I</span> |
||||
</div> |
||||
<span>Index events (kind 30040) - Each with a unique pastel color</span> |
||||
<span class="legend-text">Index events (kind 30040) - Each with a unique pastel color</span> |
||||
</li> |
||||
|
||||
<!-- Content event node --> |
||||
<li class="legend-item"> |
||||
<div class="legend-icon"> |
||||
<span class="legend-circle content"></span> |
||||
<span class="legend-letter">C</span> |
||||
<span class="legend-circle content"> |
||||
<span class="legend-letter">C</span> |
||||
</span> |
||||
</div> |
||||
<span>Content events (kinds 30041, 30818) - Publication sections</span> |
||||
<span class="legend-text">Content events (kinds 30041, 30818) - Publication sections</span> |
||||
</li> |
||||
|
||||
<!-- Link arrow --> |
||||
<li class="legend-item"> |
||||
<svg class="w-6 h-6 mr-2" viewBox="0 0 24 24"> |
||||
<path d="M4 12h16M16 6l6 6-6 6" class="network-link-leather" /> |
||||
<path |
||||
d="M4 12h16M16 6l6 6-6 6" |
||||
class="network-link-leather" |
||||
stroke-width="2" |
||||
fill="none" |
||||
/> |
||||
</svg> |
||||
<span>Arrows indicate reading/sequence order</span> |
||||
<span class="legend-text">Arrows indicate reading/sequence order</span> |
||||
</li> |
||||
</ul> |
||||
</div> |
||||
|
||||
<style> |
||||
.legend-circle.content { |
||||
background-color: var(--content-color, #d6c1a8); |
||||
} |
||||
|
||||
:global(.dark) .legend-circle.content { |
||||
background-color: var(--content-color-dark, #FFFFFF); |
||||
} |
||||
</style> |
||||
|
||||
@ -1,35 +1,79 @@
@@ -1,35 +1,79 @@
|
||||
/** |
||||
* Type definitions for the Event Network visualization |
||||
*
|
||||
* This module defines the core data structures used in the D3 force-directed |
||||
* graph visualization of Nostr events. |
||||
*/ |
||||
|
||||
import type { NDKEvent } from "@nostr-dev-kit/ndk"; |
||||
|
||||
export interface NetworkNode extends d3.SimulationNodeDatum { |
||||
id: string; |
||||
event?: NDKEvent; |
||||
level: number; |
||||
kind: number; |
||||
title: string; |
||||
content: string; |
||||
author: string; |
||||
type: "Index" | "Content"; |
||||
naddr?: string; |
||||
nevent?: string; |
||||
x?: number; |
||||
y?: number; |
||||
isContainer?: boolean; |
||||
/** |
||||
* Base interface for nodes in a D3 force simulation |
||||
* Represents the physical properties of a node in the simulation |
||||
*/ |
||||
export interface SimulationNodeDatum { |
||||
index?: number; // Node index in the simulation
|
||||
x?: number; // X position
|
||||
y?: number; // Y position
|
||||
vx?: number; // X velocity
|
||||
vy?: number; // Y velocity
|
||||
fx?: number | null; // Fixed X position (when node is pinned)
|
||||
fy?: number | null; // Fixed Y position (when node is pinned)
|
||||
} |
||||
|
||||
/** |
||||
* Base interface for links in a D3 force simulation |
||||
* Represents connections between nodes |
||||
*/ |
||||
export interface SimulationLinkDatum<NodeType> { |
||||
source: NodeType | string | number; // Source node or identifier
|
||||
target: NodeType | string | number; // Target node or identifier
|
||||
index?: number; // Link index in the simulation
|
||||
} |
||||
|
||||
/** |
||||
* Represents a node in the event network visualization |
||||
* Extends the base simulation node with Nostr event-specific properties |
||||
*/ |
||||
export interface NetworkNode extends SimulationNodeDatum { |
||||
id: string; // Unique identifier (event ID)
|
||||
event?: NDKEvent; // Reference to the original NDK event
|
||||
level: number; // Hierarchy level in the network
|
||||
kind: number; // Nostr event kind (30040 for index, 30041/30818 for content)
|
||||
title: string; // Event title
|
||||
content: string; // Event content
|
||||
author: string; // Author's public key
|
||||
type: "Index" | "Content"; // Node type classification
|
||||
naddr?: string; // NIP-19 naddr identifier
|
||||
nevent?: string; // NIP-19 nevent identifier
|
||||
isContainer?: boolean; // Whether this node is a container (index)
|
||||
} |
||||
|
||||
export interface NetworkLink extends d3.SimulationLinkDatum<NetworkNode> { |
||||
source: NetworkNode; |
||||
target: NetworkNode; |
||||
isSequential: boolean; |
||||
/** |
||||
* Represents a link between nodes in the event network |
||||
* Extends the base simulation link with event-specific properties |
||||
*/ |
||||
export interface NetworkLink extends SimulationLinkDatum<NetworkNode> { |
||||
source: NetworkNode; // Source node (overridden to be more specific)
|
||||
target: NetworkNode; // Target node (overridden to be more specific)
|
||||
isSequential: boolean; // Whether this link represents a sequential relationship
|
||||
} |
||||
|
||||
/** |
||||
* Represents the complete graph data for visualization |
||||
*/ |
||||
export interface GraphData { |
||||
nodes: NetworkNode[]; |
||||
links: NetworkLink[]; |
||||
nodes: NetworkNode[]; // All nodes in the graph
|
||||
links: NetworkLink[]; // All links in the graph
|
||||
} |
||||
|
||||
/** |
||||
* Represents the internal state of the graph during construction |
||||
* Used to track relationships and build the final graph |
||||
*/ |
||||
export interface GraphState { |
||||
nodeMap: Map<string, NetworkNode>; |
||||
links: NetworkLink[]; |
||||
eventMap: Map<string, NDKEvent>; |
||||
referencedIds: Set<string>; |
||||
nodeMap: Map<string, NetworkNode>; // Maps event IDs to nodes
|
||||
links: NetworkLink[]; // All links in the graph
|
||||
eventMap: Map<string, NDKEvent>; // Maps event IDs to original events
|
||||
referencedIds: Set<string>; // Set of event IDs referenced by other events
|
||||
} |
||||
@ -0,0 +1,19 @@
@@ -0,0 +1,19 @@
|
||||
/** |
||||
* Type declarations for D3.js and related modules
|
||||
*
|
||||
* These declarations allow TypeScript to recognize D3 imports without requiring |
||||
* detailed type definitions. For a project requiring more type safety, consider |
||||
* using the @types/d3 package and its related sub-packages. |
||||
*/ |
||||
|
||||
// Core D3 library
|
||||
declare module 'd3'; |
||||
|
||||
// Force simulation module for graph layouts
|
||||
declare module 'd3-force'; |
||||
|
||||
// DOM selection and manipulation module
|
||||
declare module 'd3-selection'; |
||||
|
||||
// Drag behavior module
|
||||
declare module 'd3-drag'; |
||||
Loading…
Reference in new issue