Проблемы реализации Java Perlin Noise - PullRequest
1 голос
/ 03 марта 2012

Эй, сообщество stackoverflow! Последние 2 недели я читал о перлиновом шуме и пытался реализовать его самостоятельно самым простым способом. Несмотря на это, моя программа не работает. Он выдает почти одинаковые результаты, и постоянство, похоже, ничего не меняет. Вот мой код:

import java.awt.Color;
import java.awt.Graphics;
import java.util.Random;
import javax.swing.JFrame;
import javax.swing.JPanel;

@SuppressWarnings("serial")
public class Noise extends JPanel{

public static int octaves = 4;
public static int size =  128;
public static float[][][] noise = new float[size][size][octaves];
public static float[][] perlinnoise = new float[size][size];

public static float p = (float) 1/4;

public static Random gen = new Random();

public static float GenerateNoise() {
    return gen.nextFloat();
}

public static float SmoothNoise(int x, int y, int z) {
    try{
        float corners = (noise[x - 1][y - 1][z] + noise[x + 1][y - 1][z] + noise[x - 1][y + 1][z] + noise[x + 1][y + 1][z]) / 16;
        float sides = (noise[x - 1][y][z] + noise[x + 1][y][z] + noise[x][y - 1][z] + noise[x][y + 1][z]) / 8;
        float center = noise[x][y][z] / 4;
        return corners + sides + center;
    }catch(Exception e) {
        return 0;
    }
}

public static float InterpolatedNoise(float x, float y, int pX, int pY, int pZ) {
    int intX = (int) x;
    int intY = (int) y;
    float fracX = x - intX;
    float fracY = y - intY;
    float v1 = SmoothNoise(pX, pY, pZ);
    float v2 = SmoothNoise(pX + 1, pY, pZ);
    float v3 = SmoothNoise(pX, pY + 1, pZ);
    float v4 = SmoothNoise(pX + 1, pY + 1, pZ);
    float i1 = Interpolate(v1, v2, fracX);
    float i2 = Interpolate(v3, v4, fracX);
    return Interpolate(i1, i2, fracY);
}

public static float Interpolate(float a, float b, float x) {
    float ft = (float) (x * 3.1415927);
    float f = (float) ((1 - Math.cos(ft)) * 0.5);
    return (float) (a * (1 - f) + b * f);
}

public static float Perlin2D(float x, float y, int posX, int posY, int posZ) {
    float total = 0;
    for(int i = 0; i < octaves; i++) {
        double f = Math.pow(2, i);
        double a = Math.pow(p, i);
        total = (float) (total + InterpolatedNoise((float)(x * f), (float)(y * f), posX, posY, posZ) * a);
    }
    return total;
}

public static void main(String [] args) {
    for(int z = 0; z < octaves; z++) {
        for(int y = 0; y < size; y++) {
            for(int x = 0; x < size; x++) {
                noise[x][y][z] = GenerateNoise();
            }
        }
    }

    for(int z = 0; z < octaves; z++) {
        for(int y = 0; y < size; y++) {
            for(int x = 0; x < size; x++) {
                perlinnoise[x][y] = Perlin2D(x / (size - 1), y / (size - 1), x, y, z) / octaves;
            }
        }
    }

    JFrame f = new JFrame("Perlin Noise");
    f.setSize(400, 400);
    f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    f.add(new Noise());
    f.setVisible(true);
}

public void paintComponent(Graphics g) {
    super.paintComponent(g);
    for(int y = 0; y < size; y++) {
        for(int x = 0; x < size; x++) {
            g.setColor(new Color(perlinnoise[x][y], perlinnoise[x][y], perlinnoise[x][y]));
            g.fillRect(x * 2, y * 2, 2, 2);
        }
    }
    repaint();
}
}

Я не понимаю, почему он не работает, потому что он точно такой же, как псевдокод в этой статье , в которой это сказано. Может ли кто-нибудь помочь мне разобраться в этом? Спасибо.

РЕДАКТИРОВАТЬ: Хорошо, пожалуйста, кто-то может просто объяснить процесс, необходимый для этого, ПОЖАЛУЙСТА, я схожу с ума, пытаясь понять это. Я пытался понять это в течение прошлых 2 недель, и никто не помогает мне с этим. Пожалуйста, если вы знаете, как это сделать, просто объясните мне, я был бы очень признателен. Спасибо.

...