Tuesday, 5 November 2013

Hi guys! ^_^

Due to popular demand, I have decided to do a tutorial on how to use noise to create interesting terrain for games. This is Part A, and in Part B I will be covering how to use the noise for terrain.

Part 0: Preface

In this section, I’m just pointing out a few facts that may be interesting to note. You can skip it if you want :P

The most commonly used form of noise in computing is Perlin Noise. It was created by Ken Perlin, back in 1982 for use with the Tron movie. A very innovative use of technology that has now become the bread and butter for many effects ad textures. Perlin Noise is pretty good, but has a few flaws, and in 2001 Ken developed Simplex Noise. The two look extremely similar, and so for our purposes we can pretty much use them interchangeably. For example, one of the more annoying flaws of Perlin Noise is that it greys out at integer values, so you have to rotate your inputs in order to avoid this. I am using Simplex Noise, because it’s a bit nicer and also a bit faster. Also, it totally sounds cooler.

Thanks for a few games like Worms, Minecraft and Terraria, the concept of using noise to generate terrain for games has become quite popular. I love it – now let’s do it! :D

Part 1: Getting Set up!

Ok, so first thing’s first! Grab the code here!.

Now, I’ve set this library up in a really simple(x) way (lol, I’m terrible for puns). The only thing you need to care about is the object “NoiseGen”. It has 3 constructors…

  1. NoiseGen() – this will set it up with the default values.
  2. NoiseGen(double pScale, byte pOctaves) – this is the one you’ll probably use the most. It sets the X and Y scales to the specified value, and sets the number of octaves you want in your noise – I’ll cover what this means in a second.
  3. NoiseGen(double pXScale, double pYScale, byte pOctaves) – this is handy if you want separate X and Y scales… ie. terrain that is “taller”, for high mountains or some such…

So inside the object there are 4 values…

  1. double XScale = 0.02 – sets the scale for the X component of the noise pattern
  2. double YScale = 0.02 – sets the scale for the Y component of the noise pattern
  3. double ZScale = 1 – sets the scale for the Z component of the noise pattern, which is primarily used for animation or seed values (time / random)
  4. byte Octaves = 1 – sets the number of octaves you want the noise to show

That’s it! I kept it really simple so it would be less confusing, but it still does pretty much everything you would want. Now to set up some code to actually produce some noise! Woo!

So let’s start with a new XNA project (XNA Game Studio 4.0 – Windows Game 4.0). I’m calling mine NoiseTest, because I love creative and interesting names.

Alright, F6, F5 – nice blank CornflowerBlue screen. Nice. Ok, now let’s add in the Noise.cs file. And we’re ready to start using it! Oooooh yea!

Part 2: Let’s Make Some Noise! :D

Now, of course, in your actual game project you’ll want some infrastructure, but for the purposes of this tutorial, I’m going to do it with nothing but what we start with, as everyone will have different infrastructure. For demonstration purposes, we’re just going to display the noise on a texture.

So, right after the class declaration:
const int textureSize = 200; // the size of the texture we'll be playing with, I chose 200 at random, and 300 ran a bit slowly
Texture2D noiseTexture; // the actual texture we'll be using to display some noise
Noise.NoiseGen noiseGen = new Noise.NoiseGen(); // the magical noise generator, yay!

Somewhere in Initialize:
IsFixedTimeStep = false; // sadly Fixed Time Step is very buggy in XNA - I won't go into the reasons here

At the end of LoadContent:
noiseTexture = new Texture2D(GraphicsDevice, textureSize, textureSize); // create the texture

In Update:
GraphicsDevice.Textures[0] = null; // this is a nice trick to prevent XNA complaining that we're trying to edit a texture that's currently in use

Color[,] colors2D = new Color[textureSize, textureSize]; // a nice 2d array for our texture
for(int x = 0; x < textureSize; x++) {     for(int y = 0; y < textureSize; y++)     {         double noise = noiseGen.GetNoise(x, y, 0); // get the noise at the current position (a value from 0.0 - 1.0)         byte value = (byte)(255 * noise); // turn that value into a byte (0 - 255)         colors2D[x, y] = new Color(value, value, value); // turn that value into a color     } } Color[] colors1D = new Color[textureSize * textureSize]; // convert the 2d array into a 1d array - this code will normally be in your infrastructure for(int x = 0; x < textureSize; x++)     for(int y = 0; y < textureSize; y++)         colors1D[x + y * textureSize] = colors2D[x, y]; noiseTexture.SetData(colors1D); // update the texture with our new values

In Draw:
spriteBatch.Draw(noiseTexture, new Vector2(0, 0), Color.White); // render it!

And that will spit out this little sucker (picture at size 300):

So this is using the default scale and octave values in NoiseGen – namely a scale of 0.02 and a single octave. Now, don’t be surprised if it runs a little sluggishly, noise is relatively “computationally expensive” to generate! That’s why Minecraft and Terraria take so long to generate terrain, even though the blocks are so relatively large (compared to pixels).

Part 3: Octave Noise

So the scale values obviously affect the “size” or “zoom level” of the noise pattern, but what about the octave value? Well, the octave value controls how many levels of noise are layered on top of one another. For example, if set to 2 octaves, it will create one layer of noise at 100% scale just like normal, but then it will layer on another level of noise that’s twice as “fine grained”. An octave value of 3 will then add a 3rd layer of extra detail into the noise.

Feel free to have a play with these values. You can make some nice looking noise. For example, scale 0.01 and 5 octaves will produce this:

Nice smokey looking noise :)

Note that increasing the octaves up past 5 for this scale won’t really have any visible effect. Also it will be really slow and unresponsive :)

Part 4: Animated Noise

Just for fun, here is how you can animate the noise :)

Now I recommend setting your NoiseGen object to default values at first – mainly because you want to start with only 1 octave… or you’ll probably suffer form terrible performance.

After your initial declarations at the top of the class, add this in:
float timer = 0;

Somewhere at the start of Update, add this in:
timer += 0.01f;

And then find the line where you call noiseGen.GetNoise and add in the Z value of timer:
double noise = noiseGen.GetNoise(x, y, timer); // get the noise at the current position (a value from 0.0 - 1.0)

Run that and you’ll get some trippy animating noise, yay! Now, if your computer can handle it, add in some extra octaves, maybe set it to 3, and see how it goes :)

So as you can see, you can get an unlimited amount of 2d noise patterns, using different Z values – this is extremely useful, as not only can you animate noise, but you can also use the Z value as a seed to generate different worlds.

Alright, that concludes Part A of the noise tutorial! Within the next few days I’m hoping to create the second part, which will focus on actually using this noise to generate usable terrain in games! This will include how to separate the ground from the sky, etc. Stay tuned!

Categories: Dev — NightCabbage @ 4:15 pm
Cabbynode Games
Sunday, 10 June 2012

So a while back I was checking out different noise methods for procedural and art generation, and I decided to look into Simplex Noise.

Simplex Noise is basically Ken Perlin’s replacement for classic Perlin Noise. It produces better results, and is a bit faster, too.

I found a really good paper called “Simplex noise demystified”, by Stefan Gustavson, Link√∂ping University (2005).

In it was an algorithm written in Java for 2d, 3d and 4d noise. I ported it to C# for 2d and 3d noise. I didn’t bother porting the 4d noise over, because I’d never use it.

The method signature is as follows:
public static float GetNoise(double pX, double pY, double pZ)

So, you’d call it like this (note that I’ve encapsulated it in a static class called Noise):
float noiseValue = Noise.GetNoise(x, y, z);

It takes doubles for input, as the extra accuracy over floats is needed (floats suck for positional data!), and it returns a single float (between 0 and 1) for the value of the noise at the specified point.

This method is extra handy because you can use it in the following ways…

* Simple 2d noise
Noise.GetNoise(x, y, 0);
and you can replace the z value of 0 with any number you want, giving you a different 2d noise pattern each time (just be sure to use the same Z value for the entire “block” of noise!)
or you could keep z as 0 and modify the x and/or y values to get a different noise pattern, eg. Noise.GetNoise(x + 100, y + 100, 0);

* Animated 2d noise
Noise.GetNoise(x, y, timer);
where timer is a value that changes over time, and you can modify the x, y and/or timer values as above to produce different patterns

* Simple 3d noise
Noise.GetNoise(x, y, z);
full 3d noise, and if you want a different pattern, all you need to do is modify any/all of the values, eg. Noise.GetNoise(x + 100, y + 100, z + 100);

Hope you enjoy the code! :)


Have added in a more up to date version of the code, yay! Modified the link for the new code…

Categories: Dev — NightCabbage @ 10:53 pm
Cabbynode Games
Friday, 2 September 2011

I’m currently working on procedural terrain generation for Crystal Haven.

For the moment I just need it to generate some basic terrain so I can use it for testing. I plan to set up a basic player movement system (with gravity), and the ability to add and remove blocks. After that will come the netcode :)

Here’s a picture of how the terrain is currently generated. I shrank the image 50% to fit on the blog better, but if it were full size, each pixel would represent one 16×16 pixel block. It’s using noise algorithms to generate the shape of the landscape, and also to generate the caves and details. It’s very basic currently, and just has 1 type of block, but that’s all I need for now.

The system has a maximum map size of about 268 million x 268 million blocks (I think Terraria’s largest map has 8400 x 2400 blocks), but I’m not sure if I’ll want to limit it for the actual game (too epic? lol imagine the harddrive space that would take up!). The terrain is generated in realtime so when the player moves a bit to the left, blocks on the right are un-loaded, and blocks on the left are added in (well, a bit more optimized than this, but the theory is the same). So currently there is no load time when a player starts a new map, etc.

Over the coming weeks I’ll slowly start to leak more information about the actual game itself – but this is a development post :)

Categories: Dev — NightCabbage @ 5:04 pm
Cabbynode Games

Powered by WordPress