GeezerVisonThe World Wide Web, restored to 800 pixels of glory. |
| Home|About|Gaming cabinet|Archives|How it works|Starter sites |
GeezerVison is showing github.com — Java/Others/PerlinNoise.java at master · feiteng/Java Expand file tree/ Copy pathPerlinNoise.javaMore file actions 166 lines (135 loc) · 5.63 KB / Copy pathPerlinNoise.javaFile metadata and controls166 lines (135 loc) · 5.63 KB 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 package Others; import java.util.Random; import java.util.Scanner; /** * For detailed info and implementation see: <a href="http://devmag.org.za/2009/04/25/perlin-noise/">Perlin-Noise</a> */ public class PerlinNoise { /** * @param width width of noise array * @param height height of noise array * @param octaveCount numbers of layers used for blending noise * @param persistence value of impact each layer get while blending * @param seed used for randomizer * @return float array containing calculated "Perlin-Noise" values */ static float[][] generatePerlinNoise(int width, int height, int octaveCount, float persistence, long seed) { final float[][] base = new float[width][height]; final float[][] perlinNoise = new float[width][height]; final float[][][] noiseLayers = new float[octaveCount][][]; Random random = new Random(seed); //fill base array with random values as base for noise for (int x = 0; x < width; x++) { for (int y = 0; y < height; y++) { base[x][y] = random.nextFloat(); } } //calculate octaves with different roughness for (int octave = 0; octave < octaveCount; octave++) { noiseLayers[octave] = generatePerlinNoiseLayer(base, width, height, octave); } float amplitude = 1f; float totalAmplitude = 0f; //calculate perlin noise by blending each layer together with specific persistence for (int octave = octaveCount - 1; octave >= 0; octave--) { amplitude *= persistence; totalAmplitude += amplitude; for (int x = 0; x < width; x++) { for (int y = 0; y < height; y++) { //adding each value of the noise layer to the noise //by increasing amplitude the rougher noises will have more impact perlinNoise[x][y] += noiseLayers[octave][x][y] * amplitude; } } } //normalize values so that they stay between 0..1 for (int x = 0; x < width; x++) { for (int y = 0; y < height; y++) { perlinNoise[x][y] /= totalAmplitude; } } return perlinNoise; } /** * @param base base random float array * @param width width of noise array * @param height height of noise array * @param octave current layer * @return float array containing calculated "Perlin-Noise-Layer" values */ static float[][] generatePerlinNoiseLayer(float[][] base, int width, int height, int octave) { float[][] perlinNoiseLayer = new float[width][height]; //calculate period (wavelength) for different shapes int period = 1 << octave; //2^k float frequency = 1f / period; // 1/2^k for (int x = 0; x < width; x++) { //calculates the horizontal sampling indices int x0 = (x / period) * period; int x1 = (x0 + period) % width; float horizintalBlend = (x - x0) * frequency; for (int y = 0; y < height; y++) { //calculates the vertical sampling indices int y0 = (y / period) * period; int y1 = (y0 + period) % height; float verticalBlend = (y - y0) * frequency; //blend top corners float top = interpolate(base[x0][y0], base[x1][y0], horizintalBlend); //blend bottom corners float bottom = interpolate(base[x0][y1], base[x1][y1], horizintalBlend); //blend top and bottom interpolation to get the final blend value for this cell perlinNoiseLayer[x][y] = interpolate(top, bottom, verticalBlend); } } return perlinNoiseLayer; } /** * @param a value of point a * @param b value of point b * @param alpha determine which value has more impact (closer to 0 -> a, closer to 1 -> b) * @return interpolated value */ static float interpolate(float a, float b, float alpha) { return a * (1 - alpha) + alpha * b; } public static void main(String[] args) { Scanner in = new Scanner(System.in); final int width; final int height; final int octaveCount; final float persistence; final long seed; final String charset; final float[][] perlinNoise; System.out.println("Width (int): "); width = in.nextInt(); System.out.println("Height (int): "); height = in.nextInt(); System.out.println("Octave count (int): "); octaveCount = in.nextInt(); System.out.println("Persistence (float): "); persistence = in.nextFloat(); System.out.println("Seed (long): "); seed = in.nextLong(); System.out.println("Charset (String): "); charset = in.next(); perlinNoise = generatePerlinNoise(width, height, octaveCount, persistence, seed); final char[] chars = charset.toCharArray(); final int length = chars.length; final float step = 1f / length; //output based on charset for (int x = 0; x < width; x++) { for (int y = 0; y < height; y++) { float value = step; float noiseValue = perlinNoise[x][y]; for (char c : chars) { if (noiseValue <= value) { System.out.print(c); break; } value += step; } } System.out.println(); } } } |
| You are visitor 01402520 — GeezerVison does not store the pages you look up. Best viewed with Netscape Navigator 4.7 or Internet Explorer 6 at 800×600. No cookies required. |