Skip to content


Switch branches/tags

Name already in use

A tag already exists with the provided branch name. Many Git commands accept both tag and branch names, so creating this branch may cause unexpected behavior. Are you sure you want to create this branch?

Latest commit


Git stats


Failed to load latest commit information.

πŸ—οΈ aframe-city-builder

A-Frame project demonstrating touch controls for building a VR city scene.

Build a New City Now: >> <<

HTC Vive or Oculus Rift with accompanying controllers required to add items to scene.

Load Existing City


* * * *

Feature Highlights

  • Place voxel objects in a fun virtual city of your creation
  • Navigate available voxel objects with a scrolling menu interface in VR
  • Place base plates for streets, grass, parks and residential lots that snap to a simple grid layout
  • Save and load your city to/from JSON format
  • Support for Oculus Touch and HTC Vive Controllers (VR headset and controllers required)
  • Convenience utilities in /utils for creating new object JSON groups for aspiring city voxel artists


How do I add new objects to City Builder?

City Builder is only as cool as the objects you can place! So let's add more! (Some day I'd love to have a sketchfab-like fancy cloud interface for uploading objects, an in-app voxel editor and more, but for now you'll have to do a bunch of manual work.)

Step-By-Step Guide

(1) Make the object - I suggest using MagicaVoxel:

(2) Come up with a filename - Each object has unique filename according to this suggested naming convention: "creator_group_object". For example "kfarr_bases_valencia" or "mmmm_obj_candle".

(3) Export to OBJ and take preview image For each object, there are multiple files using the same filename but with different extensions to represent their function in the application:

  • .jpg - A preview image used to represent the object in a menu interface, stored here: /assets/preview/. Should be 1:1 aspect ratio, suggested 256 x 256 dimensions. (Required)
  • .obj, .mtl, .png - Object file format used when placing into A-Frame scene, stored as three files per model here: /assets/obj/ (Required)
  • .vox - The object's raw source file that can be edited again in the future, stored here: /assets/vox/ (Optional)

(4) Add to JSON File - To enable placement of the object within the City Builder app, the object needs to be included in a "creator_group" JSON file. Here's an example: /assets/mmmm_veh.json

To make it easier to add a large number of objects at once, there is a utility script to create a new "creator_group" JSON file here: /utils/json_builder.js

(5) Load JSON file from City Builder - You must add the newly created JSON "creator_group" file to the list of included model definitions upon load of City Builder app. Add your filename to this list:

(5) Test it out! Take a screenshot while you're testing! Submit a pull request and include a note and your fancy screenshot!

Need inspiration? What are some other objects to make?

  • more cool vehicles
  • flying things
  • more "bases" like intersection, left turn, right turn, green park only, pedestrian and bike path only
  • more advanced light poles, signals, signs
  • people
  • trains

How can I contribute to City Builder?

Fork this repo, start making changes, and submit a pull request! Also feel free to file an issue or reach out directly with your idea and I can try to help make your idea work.

Need inspiration? Here is a partial wishlist for City Builder features:


  • remove old UI2D, add same icons as action menu bar! old dialog pops open #9
  • updating hash should trigger loading new city #10
  • show HUD message for save success with city name - in VR and on browser desktop #11
  • scale large/small (and rotate?) with both grips being pressed (what would happen to undo?) #6
  • remove load and save functions from index html file, can add to action-controls or new component #12
  • add to chrome/daydream vr whitelist #13
  • erase tool #14
  • placing an object directly over another (especially for snapping baseplates) should replace the existing object, not place both on same location
  • create a nice "screensaver" or "viewer" mode to entice people to enter VR. For example: show a list of cities and/or show a city at the start by default
  • try adding basic avatar presence using something like:
  • auto save with visual indicator (this might be required for multi-user collaboration - i want to see what they've added immediately)
  • try inverted teleport from forked repo
  • add sunlight day cycle as aframe component; try adding shadow to this too
  • error handling when city in hash cannot be loaded from firebase
  • inspect (magnifying glass)
  • show stats in addition to city name - size of city (objects, area), population (number of chr objects)
  • load directly from voxel
  • ability for select bar component to delay loading / init - fetch first set of optgroup options from database instead of in index.html
  • blender baking of AO texture and progressive application of AO textures after scene fully loaded
  • support for google draco object compression
  • add a small haptic feedback see:
  • create components from the useful a-frame stuff (menu switcher, save/load json, desktop dialog ui, message notification)
  • sound effects - commodore 64 style?
  • aframe city website - have a central registry of objects (json file is fine to start) that is not in index.html file ui inspiration - -> this could be done without a server -> use a git based site builder service. register this as
  • try progressive enhancement to replace obj with baked ply after loading
  • load new scenes without destroying original (load by appending) - does not handle collision case
  • add some clouds
  • send a VR postcard to facebook / social media
  • integrate with to generate street blocks
  • auth / storage service
  • highlight currently overlapping grid location
  • cars to follow prescribed course on roads
  • add aframe snowplay type support
  • persistent multiuser world
  • use geolocation api to with virtual citybuilder locations to create "mini second life"
  • physics
  • try isometric view on mobile / non-vr devices (examples aframevr/aframe#84 and
  • add non-flat lowpoly terrain like this example




πŸ—οΈ A-Frame project demonstrating touch controls for building a VR city scene







No packages published

Contributors 4