Nil Order is a procedurally generated Open World inspired by The Legend Of Zelda: Breath Of The Wild. It is based on a smoothed voxel grid. It means that instead of having a “Minecraft” blocky looking environment (like this one), we are aiming for a more conventional looking game. Our idea is mainly inspired by Breath Of the Wild and Monster Hunter.

Rather than starting from scratch like I did in the NanoVoxel project, we decided to use Unity. This choice was also driven by my desire of exploring the limits of this engine, mostly in the multi-threading and geometry capacity areas. The project started in April 2017 and is on hiatus since July 2017.

The team is composed of Cédric Cadiergues (3D Artist), Robin Blanc (Technical Artist) and myself Pierre Planeau (Programmer). I am in charge of designing and implementing the world generation and voxel smoothing algorithms. The character behaviour and camera are made by Robin.

We are trying to recreate the feeling of freedom that we felt when exploring Breath Of The Wild, but with procedural worlds. Additionally, we don’t want to limit ourselves with a heightmap terrain because we intend to have interesting landscapes to explore. Therefore, we chose the voxel approach. The problem is that voxels don’t feel very smooth when displayed as cubes, thus the need for a smoothing algorithm.

Voxel Smoothing

My goal is to achieve something close to what Daybreak Game Company did in Everquest Landmark. I believe their technology is based on a smoothed Marching Cubes algorithm, but I want to explore other ways of smoothing voxels.

Everquest Landmark
Voxel smoothing in Everquest Landmark

I stumbled upon the Smooth Isosurfaces with Flats from Binary Grids publication during my research. And although this algorithm looks very promising, I am a simple man. So I looked for something simpler. After some more research, I found the Constrained Elastic SurfaceNets publication by Sarah F. Frisken Gibson. The idea, so simple, of averaging every vertex position with its direct neighbors, is what appealed to me the most about this approach.

Another great aspect of this approach is that it does not generate more geometry. Indeed, the concept is that the algorithm takes every vertices of the mesh you want to smooth, weights them, and moves them according to their weight relative to the weight of their direct neighbors. This is so great because a blocky voxel terrain is extremely cheap in terms of polygons. As a consequence, making a smoothed terrain is as cheap as a blocky one (in terms of memory/poly count).

Eventually, after a few naive implementations of the algorithm, I came up with a satisfying result.

5 passes of Constrained Elastic SurfaceNets
5 passes of Constrained Elastic SurfaceNets
Pass 0
Pass 5 + Grass

However as you can see on the image above, there are some glitches on the terrain meshes. This is because the algorithm works well with “finite” meshes. But in my case, I am trying to smooth an expanding world terrain. The terrain is sliced in multiple chunks of voxels and all chunks might not even exist yet when the smooth needs to occur. This leads to discontinuity between the chunks meshes as illustrated below.

Mesh discontinuity between Chunks
Mesh discontinuity between Chunks

Chunk Smoothing

To limit this effect, I decided to constrain the vertices located on the edges of a chunk. For each side of the chunk, I forbid the side vertices to move away from the plane that separates the two chunks. This way I get rid of the holes between my chunks. Great! But now the vertices separating two chunks look blocky, because they are not allowed to move.. To counter this, I re-run the smoothing algorithm but only on the vertices separating chunks with the constraint of never leaving their plane (so basically a 2D version of the algorithm). And it works great, except for the corners (as illustrated below) because the vertices located in the chunk corners are part of multiple planes. So far I haven’t fixed this.

Chunk Corner Problem

Another approach to get rid of the discontinuity between chunks would be to generate bigger chunks than necessary. To smooth them, then to take only the part of the mesh that represents the actual chunk. This would cost a lot more memory and CPU but could completely solve the problem.

Nil Order Images

More On Voxel Smoothing Article about smooth voxel terrain:

psmilek video about his own smooth voxel engine:

Constrained Elastic SurfaceNets Publication:

Smooth Isosurfaces with Flats from Binary Grids Publication:

Dual Marching Cubes: Primal Contouring of Dual Grids Publication:

Pierre Planeau

My name is Pierre and I run this website. You can learn more about me over here and some of my personal projects over there. 🙂