Godot: Simplex Noise functions (2D, 3D, and 4D)

Created on 19 Jan 2015  Â·  58Comments  Â·  Source: godotengine/godot

Simplex Noise (also known as improved Perlin Noise) has many uses in modern game development, as it lies at the heart of procedural generation. Infinite terrain, voxel worlds, clouds, and just about any texture with realistic, natural patterns can be generated using Simplex Noise. It's commonplace in modern game engines.

Simple examples of simplex noise use:

Fortunately, it's also pretty easy to implement.

The ideal implementation would involve allowing the user to set the RNG's seed somehow (whether it's set using a separate function in advance or passed as a parameter to the noise functions), and exposing the noise functions in "@GDScript", which might look something like this:

float simplex2d(x, y)
float simplex3d(x, y, z)
feature proposal core

Most helpful comment

Until its supported natively by godot, there is a 2D/3D simplex implementation in gdscript: https://github.com/OvermindDL1/Godot-Helpers/blob/master/Simplex/Simplex.gd

All 58 comments

You would want 4d noise too, so you can get noise in 3d + time. That said, it makes considerably more sense to find and use existing glsl code yourself in shaders rather than use in gdscript (where it would be running in c++ underneath). The parallelism of the video card would make the calculations manythousands of times faster to be real time.

@Spooner Great point with the 4d noise and using shaders whenever possible. Rethinking this, I can't really come up with any real use case where it would be favourable to use simplex noise in CPU time over GPU. It might still be favourable for light one-off things, but even for stuff like voxel engines, generating initial block placement would probably best be done with fragment shaders..

I'd like to also suggest the addition of Voronoi/Worley noise and Musgrave noise. Both are useful for procedural generation, especially when used in combination with one another.

Okay, apparently simplex noise is covered by a patent for implementations using three or more dimensions. There is, however, an alternative implementation called OpenSimplex that skirts the patent issues, though afaik it is only implemented in Java.

Found an implementation of opensimplex written in C: https://github.com/smcameron/open-simplex-noise-in-c

The problem with simplex noise is that its patent protected. One would have to chose an implementation that avoids to be covered by the patent's claims.

@est31 Which is why I suggested OpenSimplex, which (despite the name) is NOT based off of the patented implementation of Simplex.

Coming from 2d game dev, I've used noise functions extensively in my games, and never in shaders. So I would have to vote to keep it out of the shader-related stuff :)

Until its supported natively by godot, there is a 2D/3D simplex implementation in gdscript: https://github.com/OvermindDL1/Godot-Helpers/blob/master/Simplex/Simplex.gd

Someone wrote a C version of simplex noise. I think will be of much help with implementing it in the core game engine. https://github.com/smcameron/open-simplex-noise-in-c. If I get time I'll try to make a module for it meanwhile (if no one else beats me to it :d)

@razvanc-r It is worth noting that it is Open Simplex, not Simplex. The implementation is different than that of Simplex, and (importantly) is not encumbered by patents.

It would be nice to have noise functionality in godot :+1:

I'm playing with terrain generation and noise functions would be very useful to speed up GDScript implementations. I tried with shaders but in Godot it feels too limited yet and I don't know if it can multi-thread well (maybe with Vulkan compute shaders in the future?).

I also found this library, FastNoise, which is MIT-licensed: https://github.com/Auburns/FastNoise.
It's very small and suited for real-time, so it could be integrated easily I think :)

I would also point out that not only a noise3d(x,y,z) is good to have, but also noise3d(x,y,z, grid) so we can ask C++ to generate a whole grid of values at once, in various formats (floats, bytes, flags...).
Then I think noise should not be just functions, but objects, so we can set their seed, offsets, storage format, parameters, add, multiply, compose them etc. without the need to iterate all values one by one in GDScript.

Side note: composing arrays of 1D, 2D, 3D numbers could be implemented outside the scope of noise generation. It sounds like something a GPU does with textures already, but would still be of use on multi-thread CPUs for non-graphic number crunching, if the GPU is already used a lot of lacks features.

I've just got FastNoise to work in Godot as a module. World generation is blazing fast now :)

# A glimpse of the usage
var noise = Noise.new()
noise.set_seed(666)
noise.set_frequency(32)
noise.set_octaves(3)
...
var h = noise.get_noise_3d(x, y, t)

But I read about the patent issues with Simplex noise so I also started to integrate OpenSimplex, following the same kind of GDScript interface.

A notable difference is that by design, OpenSimplex allocates memory for permutations _per noise instance_, which FastNoise doesn't. It shouldn't be a serious issue because it's uncommon to have many instances of noise generators, but might be worth mentionning.

I finished an OpenSimplex Godot integration :)
https://github.com/Zylann/godot_opensimplex

Thank you for your work @Zylann , I took a look and it looks like a great implementation. The native inclusion of the fractal noise class seems epecially good, since it covers probably the most common use pattern.
If the whole repository is MIT licensed, you may want to consider moving the LICENSE file up to the root of the repo and including the license or a link to the license at the bottom of the readme.

Edit: Oops, I just realized the license in the lib directory is not MIT. Either way, whatever license the rest of the code is, it might be a good idea to place it in the readme.

The license of the OpenSimplex C library is public domain.
I added a LICENSE file for the rest of the code :)

Oh!!! I can't wait to check your wrapper, thanks Zylann!!

Just in case, here is my FastNoise integration I was talking about earlier: https://github.com/Zylann/godot_fastnoise
It has more features and usage is a bit simpler, but it has the Simplex noise patent issue.

Apparently the patent on Simplex noise (referred as Perlin Noise) covers its use for image generation: "A method for generating images"
So using it for terrain generation should be fine, isn't it? Or can the resulting terrain be considered an "image" when drawn on the screen?

I am no lawyer, but isn't the terrain displayed on the screen via images (aka "frames")?

So its probably fine if you don't display the generated terrain on an image.

Why isn't this bundled with the engine already? :)

Why isn't this bundled with the engine already? :)

Because nobody sent any PR...

Lets wait until we can supply binary modules for 3.0, then we bundle this
On Jun 24, 2016 14:47, "George Marques" [email protected] wrote:

Why isn't this bundled with the engine already? :)

Because nobody sent any PR...

—
You are receiving this because you are subscribed to this thread.
Reply to this email directly, view it on GitHub
https://github.com/godotengine/godot/issues/1268#issuecomment-228413384,
or mute the thread
https://github.com/notifications/unsubscribe/AF-Z24NfsQYJdm8guxDIBVsavj-N29Ttks5qPBhHgaJpZM4DUCsT
.

Oh, didn't know there's plan to add binary modules. That would be great cause to recompile it every time... well, that's why I don't use these modules now :). Probably not only me either.

Hey guys,

Do you think the noise module implementation is usable to generate animated 4d textures?

Would ne awesome...

My two modules (OpenSimplex and FastNoise for Godot) both provide a 4d simplex noise generator so you can at most animate a 3D texture (the 4th dimension being time).

The way would be call the function for every pixel and fill a pixel buffer set it as texture? Is gd script fast enough for this?

If you need to do it only once or bake the animated images, GDScript can do the job with a native module (or even a pure script implementation, which will be much slower: https://github.com/OvermindDL1/Godot-Helpers/blob/master/Simplex/Simplex.gd). If you need to do that every frame... you have to forget about native modules, and do that with a shader. However I'm not sure if the current Godot shader language has enough features to make it simple :') (also, note that the patent on Simplex noise targets this usage).

All we really need is to be able to do iteration in shaders/shadergraphs and we will be able to implement our own cell/noises in shaders, I mean besides just the basic hash noise which is possible already now.

I made a comment much earlier (around the time when I made this issue) about how I couldn't think of non image/hightmap-related use cases for simplex noise, but really there are many. For instance, if you want to make your camera shake a certain way using simplex noise, or you want to simulate the smooth random direction change of an insect as it's moving.

This isn't just about shaders, simplex noise (as other types of random functions) can be used for an infinite other purposes, not just visuals. Coherent noise can be done with http://libnoise.sourceforge.net/ for example (which is just another name for something like simplex noise, but doesn't come attached with patent issues etc.)

Yeah I've been eyeing that libnoise myself, and I do agree that noise is useful in more way's than just the one. :)

However my point still stands, as far as shaders are concerned all we need is to be able to do iteration in shaders to generate our own noise, and I'm inclined to say that noise can already be generated in GDScript.
This in no way is meant to say that we couldn't make good use of something like libnoise implementation, though(it would be fantastic, alas no MIT License there - it's LGPL).

Personally, for some game projects I often need more than shaders (in which I actually sample textures, which is faster), and when I do for other purposes it's usually a huge CPU bottleneck when done in GDScript. My requirements are usually the ability to setup seeds and query any point in 1, 2, 3 or 4D infinite seamless space, with preferably as less memory allocations as possible.
I was pretty amazed by FastNoise for this, as it allocates zero memory, is lightweight, provides a few different noises which are not limited in space and generation is very fast.
On the other hand I keep hearing about libnoise but I wonder if it can fulfill the same requirements in game development?

Oh, yeah, fastnoise is a compatible license so a definite +1 to that. :)

@reduz OpenSimplexNoise would be a DLScript?
I have no problem with that, if it were about libnoise or complete frameworks...
But how about having the basics in core? It covers lots of use cases by itself. If more complex stuff is needed on more advanced projects, then custom modules or DLScript are better suited for it due to the size it adds.

Or when you said "bundle", did you mean Godot will be bundled with some modules that will be supported in official export templates rather than being 3rd party?

Also, the fact OpenSimplexNoise would be a DLScript implies that C++ code making use of it without overhead would also have to be a DLScript...

@Zylann are we thinking your noise module would be integrated for the 3.1 release, or is this something that would have to be a GDNative submodule for some reason (would prefer a module implementation)?

Given how widespread the usage is, a module would be great. I made an OpenSimplex implementation as a module, feel free to check it out

I thought you used FastNoise too though? @Zylann

Would be fine too (might even be better) if you don't mind patents

@Zylann How would patents get involved? FastNoise is MIT-licensed, so there shouldn't be any issue in integrating a Noise Reference-type into Godot (I would think).

It's not about the implementation license, but the patent on the method itself. I think it was mentionned earlier in this thread

@Zylann Ohhhh, I get it now. So you were wanting to substitute the portions of FastNoise that would infringe on the patent for 2D content with Open Simplex implementations? Or are we just doing Open Simplex all the way?

Put shortly, I prefer FastNoise because it is faster, lighter in memory and has more features. But due to patents I also ported an OpenSimplex module, which is slower, has less features and allocates more memory. I didn't write the libs, and I didn't work on mixing them because I use my free time for other things at the moment :p

So due to that, I proposed OpenSimplex all the way despite my preference, but feem free to tweak the module.

I suppose this patent is active only in empire of evil(USA) :) Because in Russia and Europe patents for program methods are not exist. I wonder if someone decided to push game with patented FastNoise algo to Steam the problems could happens ? However its not easy provably...

However its not easy provably...

This is not the right way to think. And probably false, if they know the game is made in Godot, which has the source available, it's easy to connect the dots.

Patent for software and algorithms does not exist AFAIK, but this case falls into a sort of grey area, since it's described as an "apparatus" which includes a computer and a display. Nevertheless, I'm not a lawyer and don't know all the implications of it, therefore I would be on the safe side. If someone with proper knowledge of the USA law explain why this would be okay, then fine, otherwise I prefer the status quo.

In any case, the patent only covers image generation. The problem is if some user unknowingly uses it to create images in the game, which could cause them trouble and such trouble likely would fall into Godot's lap since they were just using the engine.

Ah, then having it as separate library is the only option. Pushing slow unpatented version to Godot does not firstly seems like a good idea, but if someone would prefer to use faster version instead slower for image generation, this fact will be hidden(if not open source) by slow version and hardly proven(I guess Godot binary is not easy for decompile). Am I on the right way to think ? :)

Well, I'm trying to create a unified implementation that uses FastNoise in most cases, but suddenly switches over to OpenSimplex any time you want to do a 2D simplex noise operation.

@Chaosus technically, OpenSimplex should still be faster than PerlinNoise, only slower than Simplex.

And maybe performance is not so critical for this, because it called usually several times at level creation step and not in process function.. Not much games uses noise for generate level chunks on fly. And for graphical part of shaders there is already existed assets in Asset library...

Any progress on this so far?

If we add 4D noise, it may be worthwhile to add 4D math types first (such as Vector4).

For note, 5D and higher noise has immense uses as well, don't just constrain it to lower dimensions. It is not hard to create an N-Dimension version of the algorithm (though I did that via C++ templates long long ago so the usages got optimized extremely well, and I think I was using perlin then...).

For 5+ D noise, it would make sense to add it since it is useful, but I would suggest only as a generic-ish function. For example, a function accepts float arrays, and passing an array of 7 floats = 7D noise.

For example, a function accepts float arrays, and passing an array of 7 floats = 7D noise.

That's what I did in C++, if it could statically know the size of the array then it generated optimized code, else it fell back to recursion (which depending on what was being done could be about the same speed or a lot slower, depending on how well SSE could be used).

I went ahead and added open-simplex-noise as a Godot module in #21569. Just commenting here in case someone wants to improve on it (maybe add 5+D noise?) since I won't be working on it in the near future. If anyone wants to work on it I'm open to answering questions.

Simplex noise was implemented in #21569, so this issue can now be closed.

Thanks for your contribution @JFonS! :tada:

Was this page helpful?
0 / 5 - 0 ratings

Related issues

gonzo191 picture gonzo191  Â·  3Comments

mefihl picture mefihl  Â·  3Comments

testman42 picture testman42  Â·  3Comments

nunodonato picture nunodonato  Â·  3Comments

ducdetronquito picture ducdetronquito  Â·  3Comments