2014-09-03 7 views
1

我想创建一个效果,如this article中的效果,从在'逼真地形的130行'处理端口找到的代码开始。我修改了代码,因此它只能在Processing中生成灰度高度图,而不是3D地形。但是,我的代码不会生成岛状高度图,并且还会留下不寻常的方形图案,如图所示here我的中点位移生成岛的实现不会创建所需的模式?

我的代码如下:

int size = 512; 

Terrain t; 

float rough = 0.7; 
void setup() { 

    t = new Terrain(8, size); 
    doit(); 
} 

void doit() { 

    t.generate(rough); 
    size(513, 513); 
    loadPixels(); 
    for (int a=0;a<t.tMap.length;a++) { 
    float val = ((t.tMap[a]+24)/48)*255; 
    pixels[a] = color(floor(val)); 
    } 
    updatePixels(); 
} 

void mousePressed() { 
    doit(); 
} 

class Terrain { 
    public final int tSize, tMax; 
    public float[] tMap; 
    public float tRoughness; 

    Terrain(int detail, int size) { 
    tSize = size+1; 
    tMax = tSize-1; 
    tMap = new float[tSize*tSize]; 
    } 

    private float getp(int x, int y) { 
    if (x < 0) x= tMax + x; 
    if (x > tMax) x= x % tMax; 
    if (y < 0) y= tMax + y; 
    if (y > tMax) y= y % tMax; 

    return tMap[x + tSize * y]; 
    } 

    private void setp(int x, int y, float val) { 

    tMap[x + tSize * y] = val; 
    } 

    public void generate(float roughness) { 
    tRoughness = roughness; 
    //set edges and corners 0 
    for (int x=0;x<tSize;x++) { 
     setp(x, 0, 0); 
     setp(x, tMax, 0); 
    } 
    for (int y=0;y<tSize;y++) { 
     setp(y, 0, 0); 
     setp(y, tMax, 0); 
    } 
    //seed random numbers every 16 
    for (int x=0;x<tSize;x+=16) { 
     for (int y=0;y<tSize;y+=16) { 
     setp(x, y, random(-(roughness*16), roughness*16)); 
     } 
    } 
    //divide each 16x16 square 
    for (int x=0;x<tSize;x+=16) { 
     for (int y=0;y<tSize;y+=16) { 
     divide(16, x, y); 
     } 
    } 
    } 

    private void divide(int size, int smallestX, int smallestY) { 
    int x, y, half = size/2; 
    float scale = tRoughness * size; 
    if (half < 1) return; 

    for (y = smallestY + half; y < tMax; y += size) { 
     for (x = smallestX + half; x < tMax; x += size) { 
     square(x, y, half, random(-scale, scale)); 
     } 
    } 
    for (y = smallestY; y <= tMax; y += half) { 
     for (x = (y + half + smallestY) % size; x <= tMax; x += size) { 
     diamond(x, y, half, random(-scale, scale)); 
     } 
    } 
    divide(size/2, smallestX, smallestY); 
    } 

    private float average(float[] values) { 
    int valid = 0; 
    float total = 0; 
    for (int i=0; i<values.length; i++) { 
     if (values[i] != -1) { 
     valid++; 
     total += values[i]; 
     } 
    } 
    return valid == 0 ? 0 : total/valid; 
    } 

    private void square(int x, int y, int size, float offset) { 
    float ave = average(new float[] { 
     getp(x - size, y - size), // upper left 
     getp(x + size, y - size), // upper right 
     getp(x + size, y + size), // lower right 
     getp(x - size, y + size) // lower left 
    } 
    ); 
    setp(x, y, ave + offset); 
    } 

    private void diamond(int x, int y, int size, float offset) { 
    float ave = average(new float[] { 
     getp(x, y - size), // top 
     getp(x + size, y), // right 
     getp(x, y + size), // bottom 
     getp(x - size, y) // left 
    } 
    ); 
    setp(x, y, ave + offset); 
    } 
} 

感谢您的帮助!

回答

1

您首先在16x16块中分解地形。在输出中,这些边界非常明显。这是为什么?那么,因为边界上的数值比每个数据块中的数值有很大差异。

块之间的差异由初始generate值确定,与块的差异由divide引起。在divide中,您需要generate或更少的更多变体。

即使在所有块生成后,在整个图像上应用平滑算子也是值得的。这会降低粗糙度,但它会进一步降低特定边界的可见性(特别是对人眼;统计测试仍然可能证明该图像是由轴对齐过程生成的)

+0

这有助于相当位,谢谢! – Zarpar 2014-09-03 13:35:14

相关问题