curv3d / curv

a language for making art using mathematics
Apache License 2.0
1.14k stars 73 forks source link

Noise Library #46

Open doug-moen opened 6 years ago

doug-moen commented 6 years ago

A noise function is a math function that hashes one or more numbers onto a random number or random vector with certain properties that create a desired visual effect. The simplest noise function gives us white noise. Cellular noise is the basis for stochastic Voronoi patterns, which can be used for "biological" looking patterns and lattices. Fractal noise is useful for creating procedural textures like smoke and marble, or for creating fractal landscapes.

Many of the examples in the examples directory contain noise functions. It would be good to have a standard noise library (lib.noise), as a base for defining libraries of procedural textures and much more.

To start with, we can port http://github.com/ashima/webgl-noise from GLSL to Curv.

Other resources:

Cewein commented 5 years ago

should it be written in curv direcly ? I will look into, procedural is really cool. Any update on the subjet ? It has been almost a year since original post.

doug-moen commented 5 years ago

My current idea to implement a random function that takes a number, or a vector of between 2 and 4 numbers, and hashes the input into a uniformly distributed random number between 0 and 1. This random function will initially not be implemented in Curv. Instead, it will be implemented as a primitive function, in C++ and in GLSL. The rest of the noise library can be implemented in Curv using this random function.

The best available algorithms for hashing floating point numbers use features that aren't currently in Curv. The algorithms that I have in mind extract the IEEE floating point representation (an array of bits) from a number, and represent that array of bits as an integer, and then perform bitwise and arithmetic operations on the integer, and then convert into a float between 0 and 1. It's rather complicated to add the necessary language features for doing this directly, so in order to make progress without getting hung up on a side issue, we will just implement random as a primitive function.

Here are my current notes on how to implement the random function: https://github.com/curv3d/curv/blob/master/ideas/lib/Noise

There are multiple algorithms referenced by the above notes, so I'd like to try implementing the most promising algorithms, and compare them for performance and randomness. Then pick the best one.

If you are interested in implementing this, you can start by looking in the libcurv directory for the function named fhash in builtin.cc and glsl.cc. This is just junk code, part of an experiment that I never finished implementing. You can replace the implementation of fhash with a proper random function, then use it to run tests. Note that fhash has two implementations: one written in C++, used by the interpreter that runs on the CPU, and one written in GLSL, that runs on the GPU.

doug-moen commented 4 years ago

There is a new 'noise' library under construction in lib/curv/lib/noise.curv. I just checked in the first code for this. See examples/noise.curv for a white noise pattern.