Skip to content

Commit bbdb11d

Browse files
committed
blog: Building the Knowledge Graph: Visualizing Fezcodex in 3D.
1 parent c1b65fd commit bbdb11d

File tree

1 file changed

+93
-0
lines changed

1 file changed

+93
-0
lines changed
Lines changed: 93 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,93 @@
1+
The idea was simple: Fezcodex is growing. With hundreds of blog posts, apps, and project logs, a standard list or grid view just wasn't cutting it anymore. I wanted a way to visualize the *connections* between everything. To see the "brain" of the website.
2+
3+
Enter the **Knowledge Graph Visualization Protocol**.
4+
5+
## The Concept
6+
7+
I wanted a 3D, interactive network graph where:
8+
* **Nodes** represent content (Blog Posts, Apps, Projects).
9+
* **Links** represent relationships (Shared tags, Categories).
10+
* **Interaction** allows users to fly through the data and navigate to content.
11+
12+
It needed to feel like a "cyberspace" visualization from a sci-fi movie—immersive, dark, and slightly chaotic but organized.
13+
14+
## The Tech Stack
15+
16+
* **React**: The core framework.
17+
* **react-force-graph-3d**: The heavy lifter. This library uses WebGL (via Three.js) to render force-directed graphs with great performance.
18+
* **PIML**: My custom markup language for parsing project data.
19+
* **Tailwind CSS**: For the overlay UI and brutalist styling.
20+
21+
## Implementation Details
22+
23+
### 1. Data Extraction (`graphDataManager.js`)
24+
25+
The first challenge was aggregating data from three different sources:
26+
* `posts.json`: A static JSON file containing blog metadata.
27+
* `apps.json`: A structured list of all the mini-apps.
28+
* `projects.piml`: A custom file format for my project portfolio.
29+
30+
I created a utility function `fetchGraphData` that pulls all three.
31+
32+
```javascript
33+
export const fetchGraphData = async () => {
34+
const nodes = [];
35+
const links = [];
36+
const tagMap = new Map();
37+
38+
// ... fetching logic ...
39+
```
40+
41+
For each item, I created a **primary node**. Then, I looked at its `tags`, `category`, or `technologies`. For every tag found, I created a **tag node** (if it didn't exist) and created a **link** between the item and the tag.
42+
43+
This automatically creates clusters. If five posts are tagged "React", they all link to the "React" tag node, pulling them together in the 3D space.
44+
45+
### 2. The 3D Component (`KnowledgeGraphPage.js`)
46+
47+
I used `<ForceGraph3D>` to render the data.
48+
49+
```jsx
50+
<ForceGraph3D
51+
ref={fgRef}
52+
graphData={graphData}
53+
backgroundColor="#050505"
54+
nodeLabel="name"
55+
nodeColor="color"
56+
onNodeClick={handleNodeClick}
57+
// ...
58+
/>
59+
```
60+
61+
### 3. Camera Controls
62+
63+
The "cool factor" comes from the camera movement. When you click a node, I didn't want a hard jump. I wanted a smooth flight.
64+
65+
```javascript
66+
const handleNodeClick = useCallback((node) => {
67+
// Calculate a position slightly "outside" the node
68+
const distance = 40;
69+
const distRatio = 1 + distance/Math.hypot(node.x, node.y, node.z);
70+
71+
if (fgRef.current) {
72+
fgRef.current.cameraPosition(
73+
{ x: node.x * distRatio, y: node.y * distRatio, z: node.z * distRatio }, // new pos
74+
node, // lookAt
75+
3000 // ms duration
76+
);
77+
}
78+
}, []);
79+
```
80+
81+
This calculates a vector from the center (0,0,0) to the node, extends it by a fixed distance, and moves the camera there while focusing on the node.
82+
83+
## Challenges
84+
85+
* **PIML Parsing**: My custom language parser needed to be robust enough to handle the varying structures of the `projects.piml` file.
86+
* **Performance**: Rendering hundreds of text labels in 3D can be heavy. I kept the UI minimal and only showing detailed info on hover.
87+
* **Theme**: Matching the "Brutalist/Cyberpunk" aesthetic required careful tuning of node colors (Emerald for Apps, Red for Posts) and link opacity.
88+
89+
## The Result
90+
91+
The result is a living, breathing map of Fezcodex. It reveals patterns I didn't explicitly plan—like the massive cluster around "React" or the isolated islands of specific game experiments. It's not just a navigation tool; it's a piece of generative art powered by my own work.
92+
93+
Go check it out at `/graph` and fly through the system.

0 commit comments

Comments
 (0)