#include "quakedef.h"
-void fractalnoise(byte *noise, int size, int startgrid)
+void fractalnoise(unsigned char *noise, int size, int startgrid)
{
int x, y, g, g2, amplitude, min, max, size1 = size - 1, sizepower, gridpower;
int *noisebuf;
for (sizepower = 0;(1 << sizepower) < size;sizepower++);
if (size != (1 << sizepower))
- Sys_Error("fractalnoise: size must be power of 2\n");
+ {
+ Con_Printf("fractalnoise: size must be power of 2\n");
+ return;
+ }
for (gridpower = 0;(1 << gridpower) < startgrid;gridpower++);
if (startgrid != (1 << gridpower))
- Sys_Error("fractalnoise: grid must be power of 2\n");
+ {
+ Con_Printf("fractalnoise: grid must be power of 2\n");
+ return;
+ }
startgrid = bound(0, startgrid, size);
amplitude = 0xFFFF; // this gets halved before use
- noisebuf = Mem_Alloc(tempmempool, size*size*sizeof(int));
+ noisebuf = (int *)Mem_Alloc(tempmempool, size*size*sizeof(int));
memset(noisebuf, 0, size*size*sizeof(int));
for (g2 = startgrid;g2;g2 >>= 1)
g = g2 >> 1;
if (g)
{
- // subdivide, diamond-square algorythm (really this has little to do with squares)
+ // subdivide, diamond-square algorithm (really this has little to do with squares)
// diamond
for (y = 0;y < size;y += g2)
for (x = 0;x < size;x += g2)
// normalize noise and copy to output
for (y = 0;y < size;y++)
for (x = 0;x < size;x++)
- *noise++ = (byte) (((n(x,y) - min) * 256) / max);
+ *noise++ = (unsigned char) (((n(x,y) - min) * 256) / max);
Mem_Free(noisebuf);
#undef n
}
+
+// unnormalized, used for explosions mainly, does not allocate/free memory (hence the name quick)
+void fractalnoisequick(unsigned char *noise, int size, int startgrid)
+{
+ int x, y, g, g2, amplitude, size1 = size - 1, sizepower, gridpower;
+#define n(x,y) noise[((y)&size1)*size+((x)&size1)]
+
+ for (sizepower = 0;(1 << sizepower) < size;sizepower++);
+ if (size != (1 << sizepower))
+ {
+ Con_Printf("fractalnoise: size must be power of 2\n");
+ return;
+ }
+
+ for (gridpower = 0;(1 << gridpower) < startgrid;gridpower++);
+ if (startgrid != (1 << gridpower))
+ {
+ Con_Printf("fractalnoise: grid must be power of 2\n");
+ return;
+ }
+
+ startgrid = bound(0, startgrid, size);
+
+ amplitude = 255; // this gets halved before use
+ memset(noise, 0, size*size);
+
+ for (g2 = startgrid;g2;g2 >>= 1)
+ {
+ // brownian motion (at every smaller level there is random behavior)
+ amplitude >>= 1;
+ for (y = 0;y < size;y += g2)
+ for (x = 0;x < size;x += g2)
+ n(x,y) += (rand()&litude);
+
+ g = g2 >> 1;
+ if (g)
+ {
+ // subdivide, diamond-square algorithm (really this has little to do with squares)
+ // diamond
+ for (y = 0;y < size;y += g2)
+ for (x = 0;x < size;x += g2)
+ n(x+g,y+g) = (unsigned char) (((int) n(x,y) + (int) n(x+g2,y) + (int) n(x,y+g2) + (int) n(x+g2,y+g2)) >> 2);
+ // square
+ for (y = 0;y < size;y += g2)
+ for (x = 0;x < size;x += g2)
+ {
+ n(x+g,y) = (unsigned char) (((int) n(x,y) + (int) n(x+g2,y) + (int) n(x+g,y-g) + (int) n(x+g,y+g)) >> 2);
+ n(x,y+g) = (unsigned char) (((int) n(x,y) + (int) n(x,y+g2) + (int) n(x-g,y+g) + (int) n(x+g,y+g)) >> 2);
+ }
+ }
+ }
+#undef n
+}
+