Into the Void: a Real-Time 3D Solar System Map

by Sonal_1980 in Design > 3D Design

25 Views, 0 Favorites, 0 Comments

Into the Void: a Real-Time 3D Solar System Map

Screenshot 2026-05-25 at 5.45.46 PM.png
Screenshot 2026-05-25 at 5.16.37 PM.png
Screenshot 2026-05-25 at 5.46.09 PM.png

🗺️ Try the live map here: https://web-production-c9f91.up.railway.app/

💻 View the source code here: https://github.com/sonal141600/into-the-void.git

Space is almost impossible to truly comprehend. As someone working toward designing rocket systems and aerospace components, I spend a lot of time calculating orbital mechanics and looking at distances on paper. But eventually, knowing the numbers wasn't enough—I wanted to actually feel what those numbers meant. I didn't want to just build a static web page with flat dots; I wanted to understand what it actually feels like to travel through that kind of immense, quiet emptiness.

"Into The Void" was born out of that curiosity. It is a real-time, 3D navigational map of our solar system.

Instead of an artistic approximation, this project visualizes actual astronomical scale. By pulling live vector data from the NASA JPL Horizons API, the map tracks the exact, real-time planetary positions against a mathematically accurate backdrop of 9,000 stars. It’s an interactive map that lets you accelerate to the speed of light, navigate across the void, and even leave coordinate-based "messages in a bottle" for future travelers to find.

Here is how I built it.

Supplies

Frontend: HTML, CSS, JavaScript, Three.js

Backend: Python, Flask

Database: SQLite

Data Sources: NASA JPL Horizons API, HYG Star Database

Deployment: Railway.app, GitHub

The Concept & Data (NASA JPL API)

Screenshot 2026-05-25 at 5.56.47 PM.png
Screenshot 2026-05-25 at 5.57.43 PM.png

Space simulators often use static math to plot planets, but I wanted "Into The Void" to reflect reality. To do this, I needed a way to find exactly where the planets are right now.

The Data Source: I used the NASA JPL Horizons API. This is the same system NASA uses to calculate ephemerides (trajectories) for solar system bodies and spacecraft.

How it works: In my Python backend, I wrote a function called fetch_vector(). This function sends an HTTP request to the Horizons API for a specific celestial body (like Mars, which has the ID "499"). It asks for the body's coordinates relative to Earth for the current day.

NASA returns the data as X, Y, and Z coordinates measured in Astronomical Units (AU). My Python script then processes these coordinates, converting them into a format that the frontend can use to plot the planets accurately in our 3D space.

Note: For the asteroid belt, I couldn't pull a single API point, so I calculated the midpoint between Mars and Jupiter and used Keplerian mechanics to plot a realistic coordinate field for the asteroids.

The Backend (Python & Flask)

Screenshot 2026-05-25 at 5.59.17 PM.png

To handle the NASA data and serve the web page, I built a lightweight backend server using Python and Flask.

The Setup: Flask is a web framework that makes it incredibly easy to route data. The backend serves two main purposes:

  1. Serving the App: When a user visits the URL, Flask serves the index.html file containing the 3D environment.
  2. Creating API Endpoints: The frontend JavaScript needs a way to ask for the planetary data. I created custom routes in Flask (like /positions, /stars, and /asteroids) that the frontend can call.

The Star Database: The background of the map is generated using the HYG Database, which contains data on the brightest stars in the sky. Because the database is a massive 50MB CSV file, it was too heavy to download every time the server booted up.

To solve this, I compressed the CSV into a ZIP file. The Flask backend uses Python's zipfile library to read directly from the compressed archive, pulling the coordinates and B-V color indices for 9,000 stars, and calculating their RGB values before sending them to the frontend.

The Frontend (Building the 3D Environment)

Screenshot 2026-05-25 at 6.01.40 PM.png
Screenshot 2026-05-25 at 11.28.33 AM.png

Once the backend has the data, the frontend needs to render it. I used HTML, CSS, and Three.js to build the 3D space.

Rendering the Map: Three.js is a powerful JavaScript library that uses WebGL to draw 3D graphics in the browser.

  1. The Camera: I set up a PerspectiveCamera to act as the player's viewport.
  2. The Stars: The 9,000 stars are rendered using a Points material, scaled by their apparent magnitude, and colored using the RGB data from the backend.
  3. The Planets: To prevent the browser from crashing by loading massive 4K textures for every planet, I used procedural generation (Canvas-based drawing) to create base textures. High-resolution NASA maps are only loaded and applied when you get close to a specific planet.

The UI: I built the Heads-Up Display (HUD) using standard HTML overlays. The UI features a real-time distance calculator, an orbital route map (SVG), and dynamic speed lines drawn on a 2D canvas layer to simulate velocity as you travel.

The Database (Message in a Bottle)

Screenshot 2026-05-25 at 6.02.06 PM.png

What is the point of exploring space if you can't leave your mark? I wanted users to be able to leave temporal notes at specific coordinates for future travelers to find.

The SQLite Integration: To handle this, I integrated SQLite into the Flask backend. When you click "Leave Message" in the app, the frontend sends a POST request containing:

  1. Your current destination
  2. Your current speed
  3. Your exact progress along the route (e.g., 45.2%)
  4. Your text message

The Python server intercepts this and writes it to a local messages.db file along with a timestamp.

Finding Messages: As you travel, the frontend continuously polls the backend (every 5 minutes) via a /messages endpoint. It asks: "Is there a message saved within a 2% radius of my current position on this specific route?" If the database finds a match, the UI triggers a "Signal Detected" alert, displaying the message and calculating how long ago it was left.

Deployment (Launching on Railway)

Screenshot 2026-05-25 at 6.00.25 PM.png

Because "Into The Void" requires a running Python server and a database, it cannot be hosted on a static web host like GitHub Pages. It needs a cloud environment.

The Railway Deployment: I used Railway.app, a cloud platform that makes deploying full-stack apps very fast.

To prepare the app for deployment, I needed three things in my GitHub repository:

  1. app.py: The main Flask server file.
  2. index.html: The frontend file.
  3. requirements.txt: A list of the Python libraries the server needs to install (Flask, requests, etc.).
  4. Procfile: A simple text file containing the line web: python app.py, which tells the Railway server exactly how to boot up the application.

Once I connected my GitHub repository to Railway, it automatically detected the Procfile, installed the requirements, and assigned a live public URL. The real-time map was live!