Clean up extern functions, update noise_diamondsquare to match LordHavoc's fractalnoise.

This commit is contained in:
Ragnvald Maartmann-Moe IV 2001-10-06 00:39:22 +00:00
parent 8afd4a870e
commit d657a590b5
3 changed files with 91 additions and 41 deletions

View file

@ -0,0 +1,36 @@
/*
noisetextures.h
Noise texture generator exports.
Copyright (C) 1996-1997 Id Software, Inc.
This program is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 2
of the License, or (at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
See the GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to:
Free Software Foundation, Inc.
59 Temple Place - Suite 330
Boston, MA 02111-1307, USA
$Id$
*/
#ifndef __QF_GL_noisetextures_h
#define __QF_GL_noisetextures_h
extern void noise_diamondsquare (unsigned char *noise, unsigned int size,
unsigned int startgrid);
extern void noise_plasma (unsigned char *noise, int size);
#endif // __QF_GL_noisetextures_h

View file

@ -36,15 +36,13 @@ static const char rcsid[] =
#include "QF/qtypes.h"
#include "QF/GL/defines.h"
#include "QF/GL/funcs.h"
#include "QF/GL/qf_noisetextures.h"
#include "QF/GL/qf_vid.h"
int part_tex_dot;
int part_tex_smoke;
int part_tex_spark;
extern void noise_diamondsquare(unsigned char *noise, int size);
extern void noise_plasma(unsigned char *noise, int size);
static void
GDT_InitDotParticleTexture (void)
@ -58,7 +56,7 @@ GDT_InitDotParticleTexture (void)
for (y = 0; y < 16; y++) {
dy = y - 8;
d = 255 - 4 * (dx2 + (dy * dy));
if (d<=0) {
if (d <= 0) {
d = 0;
data[y][x][0] = 0;
} else
@ -82,14 +80,14 @@ GDT_InitSparkParticleTexture (void)
int x, y, dx2, dy, d;
for (x = 0; x < 16; x++) {
dx2 = 8 - abs(x - 8);
dx2 = 8 - abs (x - 8);
dx2 *= dx2;
for (y = 0; y < 16; y++) {
dy = 8 - abs(y - 8);
dy = 8 - abs (y - 8);
d = 3 * (dx2 + dy * dy) - 100;
if (d>255)
if (d > 255)
d = 255;
if (d<1) {
if (d < 1) {
d = 0;
data[y][x][0] = 0;
} else
@ -115,20 +113,20 @@ GDT_InitSmokeParticleTexture (void)
int x, y, c;
noise_plasma (&noise1[0][0], 32);
noise_diamondsquare (&noise2[0][0], 32);
noise_diamondsquare (&noise2[0][0], 32, 4);
for (y = 0; y < 32; y++)
{
dy2 = y - 16;
dy2 *= dy2;
for (x = 0; x < 32; x++) {
dx = x - 16;
c = 255 - (dx*dx + dy2);
c = 255 - (dx * dx + dy2);
if (c < 1)
c = 0;
d = (noise1[y][x] + noise2[y][x]) / 2;
if (d > 0) {
data[y][x][0] = 255;
data[y][x][1] = (d * c)/255;
data[y][x][1] = (d * c) / 255;
} else {
data[y][x][0] = 255;
data[y][x][1] = 0;

View file

@ -44,45 +44,60 @@ static const char rcsid[] =
#include <stdlib.h>
#include "QF/mathlib.h"
#include "QF/sys.h"
#include "compat.h"
void
noise_diamondsquare (unsigned char *noise, int size)
noise_diamondsquare (unsigned char *noise, unsigned int size,
unsigned int startgrid)
{
int amplitude, max, min, g, g2, x, y;
int size1 = size - 1;
int amplitude, max, min;
int size1 = size - 1;
int *noisebuf;
unsigned int gridpower, sizepower, g, g2, x, y;
#define n(x, y) noisebuf[((y) & size1) * size + ((x) & size1)]
noisebuf = calloc (size * size, sizeof (int));
amplitude = 32767;
g2 = size;
n (0, 0) = 0;
for (; (g = g2 >> 1) >= 1; g2 >>= 1) {
// subdivide, diamond-square algorythm (really this has little
// to do with squares)
// diamond
for (sizepower = 0;(1 << sizepower) < size;sizepower++);
if (size != (1 << sizepower))
Sys_Error("fractalnoise: size must be power of 2\n");
for (gridpower = 0;(1 << gridpower) < startgrid;gridpower++);
if (startgrid != (1 << gridpower))
Sys_Error("fractalnoise: grid must be power of 2\n");
startgrid = bound(0, startgrid, size);
amplitude = 0xFFFF; // this gets halved before use
noisebuf = calloc (size * size, sizeof (int));
memset(noisebuf, 0, size * size * sizeof(int));
for (g2 = startgrid; g2; g2 >>= 1) {
// Brownian Motion
amplitude >>= 1;
for (y = 0; y < size; y += g2)
for (x = 0; x < size; x += g2)
n (x + g, y + g) =
(n (x, y) + n (x + g2, y) + n (x, y + g2) +
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) =
(n (x, y) + n (x + g2, y) + n (x + g, y - g) +
n (x + g, y + g)) >> 2;
n (x, y + g) =
(n (x, y) + n (x, y + g2) + n (x - g, y + g) +
n (x + g, y + g)) >> 2;
n (x,y) += (rand () & amplitude);
g = g2 >> 1;
if (g) {
// subdivide, diamond-square algorithm
// diamond
for (y = 0; y < size; y += g2)
for (x = 0; x < size; x += g2)
n (x + g, y + g) =
(n (x, y) + n (x + g2, y) + n (x, y + g2) +
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) = (n (x, y) + n (x + g2, y) +
n (x + g, y - g) + n (x + g, y + g)) >> 2;
n (x, y + g) = (n (x, y) + n (x, y + g2) +
n (x - g, y + g) + n (x + g, y + g)) >> 2;
}
// Brownian motion ( at every smaller level, random behavior )
amplitude >>= 1;
for (y = 0; y < size; y += g)
for (x = 0; x < size; x += g)
n (x, y) += (rand () & amplitude);
}
}
// find range of noise values
min = max = 0;
@ -94,10 +109,11 @@ noise_diamondsquare (unsigned char *noise, int size)
max = n (x, y);
}
max -= min;
max++;
// normalize noise and copy to output
for (y = 0; y < size; y++)
for (x = 0; x < size; x++)
*noise++ = (n (x, y) - min) * 255 / max;
*noise++ = (unsigned char) (((n (x, y) - min) * 256) / max);
free (noisebuf);
#undef n
}
@ -105,7 +121,7 @@ noise_diamondsquare (unsigned char *noise, int size)
void
noise_plasma (unsigned char *noise, int size)
{
int a, b, c, d, i, j, k;
unsigned int a, b, c, d, i, j, k;
if (128 >= size)
d = 64 / size;