Tag Archives: generate

Generating more accurate 3D models

One of things that regularly surprised us was the quality of the models that we were able to produce.

There were two factors which contributed to this: the quality of the texture and the detail in the height map.

We had already found the highest quality texture that the Google Static Maps API would give us, so the next step was the height maps.

The main issue with the detail of the height maps was finding the perfect balance between clone time and detail.

First of all, I moved the blurring of the height maps from the PHP to the JS thanks to stackblur.js. The gaussian blur filter in PHP is extremely slow, and is lacking in options, which forced me to apply the filter 50 times over in a for-loop, greatly increasing the clone time. On our sandbox, this cut the clone time from several 10s of seconds down to under 3 seconds!

Now that the clone time was reduced, I attempted to increase the detail in the height maps.

The main issue here was the Google Elevation API. It would reject and requests if they were either too large (i.e. requesting too many elevation points in one request) or too frequent. If either were rejected, the request would have to be resent, adding more time to the cloning process.

The first thing I did was to refactor the request code to continuously request the data until it is complete in a self-invoking loop, rather than a set of fixed-size chained requests. This made it much easier to fiddle with the height map detail variables.

With the new request code in place, I was able to crank up the detail variables to much higher values. The original resolution was 20x20px; increasing this to 100x100px produced amazing results. All the crevices and valleys would show up on the model in amazing detail. The only problem being that the clone time shot up to over a minute. We felt that a short clone time greatly outweighed the quality of the models. An average user would not realise unless they had a comparison.

Agreeing upon anything less than 30 seconds of clone time, we settled on a resolution of 40x40px; not a great increase,but an increase nonetheless!

Generating 3D terrain models using Google Elevation API, Google Static Maps and ThreeJS

By combining Google Elevation API, Google Static Maps API and ThreeJS, we can automatically generate and display 3D topographical representations of real-world areas using only code.

The following lists out the step-by-step process we went through in order to produce the outcome.

Getting the elevation data:

  1. Split the world into tiles
  2. Work out which tile the user has selected
  3. Get the latlng (latitude and longitude) boundaries of that tile
  4. Divide the tile into another grid (30×30)
  5. Loop through the grid, row by row, and get the latlng of each of those divisions
  6. Request the elevation of each latlng from Google Elevation API and store in an array

Generating the height map:

A height map is a grey scale image where white means high and black means low.

In RGB, white = 255 and black = 0.

  1. Take the elevation array and find the maximum and minimum value
  2. Normalise all the data so that the minimum value = 0
  3. Calculate the ratio of all the values so that they lie between 0 and 255
  4. Convert the array into a string, with each column delimited by a comma and each new row signified by a dash, and pass the string into a PHP script
  5. The PHP parses and loops through the string to draw out the grey scale image pixel by pixel, which is then saved to disk

Getting the satellite image:

  1. From the selected tile boundaries, calculate the centre latlng of that tile
  2. Request the satellite image using Google Static Maps (proxying through a PHP script to bypass the Cross-Origin Policy)

Rendering the model:

  1. ThreeJS is used to generate a mesh and downloads the height map and the satellite image
  2. The height map is applied as a displacement map
  3. The satellite image is applied as a texture