30

Is there a way to generate a DEM, programatically or otherwise, that will feed into ArcGIS Desktop for further spatial analysis?

Perhaps this needs to be broken down into smaller incremental steps:

  1. Generate a grid
  2. Fill grid with values where: 0 > value < maxElevation
  3. Neighbouring cells: (x1-x2) < maxSlope
PolyGeo
  • 65,136
  • 29
  • 109
  • 338
Michael Markieta
  • 5,411
  • 5
  • 36
  • 65
  • 6
    The site @Igor points you to suggests a need to clarify this question. It focuses on "synthetic terrains," apparently to create backgrounds for games and the like. Most of those techniques do not appear to focus on recreating actual DEMs: "realistic" is in the eye of the beholder rather than having any scientific content. In your question, "further spatial analysis" suggests you need your synthetic DEMs to reproduce certain characteristics of some class of actual DEMs. If this is so, just what features do you need to capture? – whuber Feb 28 '12 at 16:30
  • Also take a look at this. – Rodrigo Aug 15 '17 at 02:08
  • Mods, please clarify where you see more than one question here if you feel adamant that this question must remain closed. – bugmenot123 May 19 '23 at 10:52
  • 1
    @bugmenot123 I agree. There is one question - how to generate a synthetic DEM. The dot points aren't additional questions, just an attempt to show some thinking on how it might be done. – user2856 May 22 '23 at 23:49

8 Answers8

20

You can use fractals for this: Artificial DEMs created with fractals.

The upper row was generated with the fractal dimension d=2.0005 (left: elevation map, right: aspect map), the lower row with fractal dimension d=2.90 (left: elevation map, right: aspect map). I used r.surf.fractal of GRASS GIS. Then simply export the artificial DEM with r.out.gdal (or the GUI) to GeoTIFF.

markusN
  • 12,976
  • 31
  • 48
7

You could also consider having a script that takes random part of an existing real DEM.

johanvdw
  • 6,207
  • 27
  • 42
  • Plus it would need some kind of filltering at the end to nivelate those mosaic edges of random parts.. – najuste Nov 26 '12 at 08:02
7

Here is an R solution using a Gaussian Kernel to add autocorrelation to a random raster. Although, I have to say that the GRASS r.surf.fractal function, suggested by @markusN, seems like the best approach.

require(raster)

# Create 100x100 random raster with a Z range of 500-1500
r <- raster(ncols=100, nrows=100, xmn=0)
  r[] <- runif(ncell(r), min=500, max=1500)  

# Gaussian Kernel Function
GaussianKernel <- function(sigma=s, n=d) {
          m <- matrix(nc=n, nr=n)
            col <- rep(1:n, n)
            row <- rep(1:n, each=n)
          x <- col - ceiling(n/2)
          y <- row - ceiling(n/2)
         m[cbind(row, col)] <- 1/(2*pi*sigma^2) * exp(-(x^2+y^2)/(2*sigma^2))
        m / sum(m)
       }

# Create autocorrelated raster using 9x9 Gaussian Kernel with a sigma of 1
r.sim <- focal(r, w=GaussianKernel(sigma=1, n=9))

# Plot results
par(mfcol=c(1,2))
  plot(r, main="Random Raster")
  plot(r.sim, main="Autocorrelated Random Raster sigma=1, n=9")
Jeffrey Evans
  • 31,750
  • 2
  • 47
  • 94
6

Here's a great resource on terrain generation algorithms and software on vterrain.org: http://vterrain.org/Elevation/Artificial/

Igor Brejc
  • 3,677
  • 29
  • 28
6

Try or read this page for some good information. and second link show you the way of random digital elevatin model.

  1. Numerical and Scientific Python and Data Visualisation
  2. creating elevation/height field gdal numpy python
PolyGeo
  • 65,136
  • 29
  • 109
  • 338
urcm
  • 22,533
  • 4
  • 57
  • 109
4

You could try using Perlin noise to create some random fractal terrain. This answer on Stackoverflow explains a way you could get started in Python. The trick would be to zoom in on a very small area of the noisy grid so it's not too irregular looking.

Jason Scheirer
  • 18,002
  • 2
  • 53
  • 72
3

This code can be used to create a "Hill slope" DEM of just about any number of rows and columns:

# Building a fake hillslope
# hisllop is 5 rows by 6 columns

x <- seq(-15, 15, by=0.01)
z <- 1/(1+1.5^-x)
plot(z)

z <- 150 - (1-z)*5
plot(z)

# Doing it by hand - DELETE if needed - JUST HERE AS AN EXAMPLE!!!
elev <- c(mean(z[0:500]), mean(z[501:1000]), mean(z[1001:1500]), mean(z[1501:2000]), mean(z[2001:2500]),mean(z[2501:3000]))
plot(elev, type="l")


# doing it by loop
bins <- 6      # could also be considered the length or the hillslope - AKa the number of columns
elev1 <- numeric(bins)


for(i in 0:(bins-1))
{
  begin <- floor( (0 + (length(z)/bins)*i) )
  print(begin)
  end <- floor( ( (length(z)/bins) * (i+1) ) )
  print(end)
  print(mean(z[begin:end]))
  elev1[i+1] <- mean(z[begin:end])  

}

plot(elev1, type="l")


# Making the hillslope wide - AKA creating identical rows
width <- 5

# creating empty matric
hillslope <- matrix(0, nrow=bins, ncol=width)

#overwriting the matrix with the elevation column
system.time(
  { 
    for(i in 1:width) 
      hillslope[,i] <- elev1; 
    hillslope <- as.data.frame(hillslope) 
    }
  )



# applying random error grid
error <- rnorm((width*bins), mean = 0, sd = 0.25)
error.matrix <- as.matrix(error, nrow=bins )



random.hillslope <- as.matrix(hillslope + error.matrix)
image(random.hillslope)
traggatmot
  • 2,080
  • 1
  • 22
  • 43
3

libnoise gives you what you want. You will likely have to customize it to some extent. Check the 'complex planetary surface' example.

libnoise is a portable C++ library that is used to generate coherent noise, a type of smoothly-changing noise. libnoise can generate Perlin noise, ridged multifractal noise, and other types of coherent-noise.

Coherent noise is often used by graphics programmers to generate natural-looking textures, planetary terrain, and other things. The mountain scene shown above was rendered in Terragen with a terrain file generated by libnoise. You can also view some other examples of what libnoise can do.

In libnoise, coherent-noise generators are encapsulated in classes called noise modules. There are many different types of noise modules. Some noise modules can combine or modify the outputs of other noise modules in various ways; you can join these modules together to generate very complex coherent noise.

Fezter
  • 21,867
  • 11
  • 68
  • 123
KarlM
  • 131
  • 2