mirror of
https://github.com/pmmp/PocketMine-MP.git
synced 2025-05-17 11:18:52 +00:00
Such noise
This commit is contained in:
parent
26772082da
commit
1bc54dbc44
@ -94,7 +94,7 @@ class LevelAPI{
|
||||
if(strtoupper($this->server->api->getProperty("level-type")) == "FLAT"){
|
||||
$generator = new SuperflatGenerator($options);
|
||||
}else{
|
||||
$generator = new TemporalGenerator($options);
|
||||
$generator = new NormalGenerator($options);
|
||||
}
|
||||
}
|
||||
$gen = new WorldGenerator($generator, $name, $seed === false ? Utils::readInt(Utils::getRandomBytes(4, false)):(int) $seed);
|
||||
|
@ -22,25 +22,15 @@
|
||||
|
||||
//Unsecure, not used for "Real Randomness"
|
||||
class Random{
|
||||
private $x, $y, $z, $w;
|
||||
private $z, $w;
|
||||
public function __construct($seed = false){
|
||||
$this->setSeed($seed);
|
||||
}
|
||||
|
||||
public function setSeed($seed = false){
|
||||
$seed = $seed !== false ? Utils::writeInt((int) $seed):Utils::getRandomBytes(4, false);
|
||||
$state = array();
|
||||
for($i = 0; $i < 256; ++$i){
|
||||
$state[] = $i;
|
||||
}
|
||||
for($i = $j = 0; $i < 256; ++$i){
|
||||
$j = ($j + ord($seed{$i & 0x03}) + $state[$i]) & 0xFF;
|
||||
$state[$i] ^= $state[$j];
|
||||
$state[$j] ^= $state[$i];
|
||||
$state[$i] ^= $state[$j];
|
||||
}
|
||||
$this->state = $state;
|
||||
$this->i = $this->j = 0;
|
||||
$seed = $seed !== false ? (int) $seed:Utils::readInt(Utils::getRandomBytes(4, false));
|
||||
$this->z = $seed ^ 0xdeadbeef;
|
||||
$this->w = $seed ^ 0xc0de1337;
|
||||
}
|
||||
|
||||
public function nextInt(){
|
||||
@ -61,19 +51,16 @@ class Random{
|
||||
|
||||
public function nextBytes($byteCount){
|
||||
$bytes = "";
|
||||
for($i = 0; $i < $byteCount; ++$i){
|
||||
$this->i = ($this->i + 1) & 0xFF;
|
||||
$this->j = ($this->j + $this->state[$this->i]) & 0xFF;
|
||||
$this->state[$this->i] ^= $this->state[$this->j];
|
||||
$this->state[$this->j] ^= $this->state[$this->i];
|
||||
$this->state[$this->i] ^= $this->state[$this->j];
|
||||
$bytes .= chr($this->state[($this->state[$this->i] + $this->state[$this->j]) & 0xFF]);
|
||||
while(strlen($bytes) < $byteCount){
|
||||
$this->z = 36969 * ($this->z & 65535) + ($this->z >> 16);
|
||||
$this->w = 18000 * ($this->w & 65535) + ($this->w >> 16);
|
||||
$bytes .= pack("N", ($this->z << 16) + $this->w);
|
||||
}
|
||||
return $bytes;
|
||||
return substr($bytes, 0, $byteCount);
|
||||
}
|
||||
|
||||
public function nextBoolean(){
|
||||
return ($this->nextBytes(1) & 0x01) == 0;
|
||||
return ($this->nextSignedInt() & 0x01) === 0;
|
||||
}
|
||||
|
||||
public function nextRange($start = 0, $end = PHP_INT_MAX){
|
||||
|
136
src/world/generator/NormalGenerator.php
Normal file
136
src/world/generator/NormalGenerator.php
Normal file
@ -0,0 +1,136 @@
|
||||
<?php
|
||||
|
||||
/**
|
||||
*
|
||||
* ____ _ _ __ __ _ __ __ ____
|
||||
* | _ \ ___ ___| | _____| |_| \/ (_)_ __ ___ | \/ | _ \
|
||||
* | |_) / _ \ / __| |/ / _ \ __| |\/| | | '_ \ / _ \_____| |\/| | |_) |
|
||||
* | __/ (_) | (__| < __/ |_| | | | | | | | __/_____| | | | __/
|
||||
* |_| \___/ \___|_|\_\___|\__|_| |_|_|_| |_|\___| |_| |_|_|
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* @author PocketMine Team
|
||||
* @link http://www.pocketmine.net/
|
||||
*
|
||||
*
|
||||
*/
|
||||
|
||||
/***REM_START***/
|
||||
require_once("LevelGenerator.php");
|
||||
/***REM_END***/
|
||||
|
||||
class NormalGenerator implements LevelGenerator{
|
||||
|
||||
private $populators = array();
|
||||
private $level;
|
||||
private $random;
|
||||
private $worldHeight = 64;
|
||||
private $waterHeight = 60;
|
||||
private $blockLevels = array();
|
||||
private $noiseGen1;
|
||||
private $noiseGen2;
|
||||
private $noiseGen3;
|
||||
private $noiseGen4;
|
||||
private $noiseGen5;
|
||||
private $noiseGen6;
|
||||
private $noiseArray = array();
|
||||
|
||||
public function __construct(array $options = array()){
|
||||
$this->noiseGen1 = new PerlinOctaveGenerator($rand, 16);
|
||||
$this->noiseGen2 = new PerlinOctaveGenerator($rand, 16);
|
||||
$this->noiseGen3 = new PerlinOctaveGenerator($rand, 8);
|
||||
$this->noiseGen4 = new PerlinOctaveGenerator($rand, 4);
|
||||
$this->noiseGen5 = new PerlinOctaveGenerator($rand, 10);
|
||||
$this->noiseGen6 = new PerlinOctaveGenerator($rand, 16);
|
||||
}
|
||||
|
||||
public function init(Level $level, Random $random){
|
||||
$this->level = $level;
|
||||
$this->random = $random;
|
||||
$this->random->setSeed($this->level->getSeed());
|
||||
$perlin = new PerlinNoiseGenerator($this->random, array(
|
||||
"frequency" => 1,
|
||||
"octaves" => 8,
|
||||
"persistence" => 0.3,
|
||||
"scale" => 1,
|
||||
));
|
||||
$this->deviations = $perlin->fillNoiseArray(256, 256);
|
||||
|
||||
$ores = new OrePopulator();
|
||||
$ores->setOreTypes(array(
|
||||
new OreType(new CoalOreBlock(), 20, 16, 0, 128),
|
||||
new OreType(New IronOreBlock(), 20, 8, 0, 64),
|
||||
new OreType(new RedstoneOreBlock(), 8, 7, 0, 16),
|
||||
new OreType(new LapisOreBlock(), 1, 6, 0, 32),
|
||||
new OreType(new GoldOreBlock(), 2, 8, 0, 32),
|
||||
new OreType(new DiamondOreBlock(), 1, 7, 0, 16),
|
||||
new OreType(new DirtBlock(), 20, 32, 0, 128),
|
||||
new OreType(new GravelBlock(), 10, 16, 0, 128),
|
||||
));
|
||||
$this->populators[] = $ores;
|
||||
}
|
||||
|
||||
public function generateChunk($chunkX, $chunkZ){
|
||||
//$this->random->setSeed(0xdeadbeef ^ ($chunkX << 8) ^ $chunkZ ^ $this->level->getSeed());
|
||||
$byte0 = 4;
|
||||
$this->noiseArray = $this->initializeNoiseArray($chunkX * $byte0, 0, $chunkZ * $byte0, $byte0 + 1, ($this->worldHeight / 8) + 1, $byte0 + 1);
|
||||
|
||||
$chunks = array();
|
||||
for($chunkY = 0; $chunkY < 8; ++$chunkY){
|
||||
$chunk = "";
|
||||
$startY = $chunkY << 4;
|
||||
$endY = $startY + 16;
|
||||
for($z = 0; $z < 16; ++$z){
|
||||
for($x = 0; $x < 16; ++$x){
|
||||
$height = (int) ($this->baseHeight + $this->deviations[$z + ($chunkZ << 4)][$x + ($chunkX << 4)]);
|
||||
for($y = $startY; $y < $endY; ++$y){
|
||||
$diff = $height - $y;
|
||||
if($y <= 4 and ($y === 0 or $this->random->nextFloat() < 0.75)){
|
||||
$chunk .= "\x07"; //bedrock
|
||||
}elseif($diff > 3){
|
||||
$chunk .= "\x01"; //stone
|
||||
}elseif($diff > 0){
|
||||
$chunk .= "\x03"; //dirt
|
||||
}elseif($y <= $this->waterHeight){
|
||||
$chunk .= "\x09"; //still_water
|
||||
}elseif($diff === 0){
|
||||
$chunk .= "\x02"; //grass
|
||||
}else{
|
||||
$chunk .= "\x00";
|
||||
}
|
||||
}
|
||||
$chunk .= "\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00";
|
||||
}
|
||||
}
|
||||
$this->level->setMiniChunk($chunkX, $chunkZ, $chunkY, $chunk);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private function initializeNoiseArray($x, $y, $z, $sizeX, $sizeY, $sizeZ){
|
||||
$noiseArray = array_fill(0, $sizeX * $sizeY * $sizeZ, 0.0);
|
||||
|
||||
$noise5 = $this->noiseGen5->generateNoiseOctaves($x, $y, $z);
|
||||
|
||||
}
|
||||
|
||||
public function populateChunk($chunkX, $chunkZ){
|
||||
foreach($this->populators as $populator){
|
||||
$this->random->setSeed(0xdeadbeef ^ ($chunkX << 8) ^ $chunkZ ^ $this->level->getSeed());
|
||||
$populator->populate($this->level, $chunkX, $chunkZ, $this->random);
|
||||
}
|
||||
}
|
||||
|
||||
public function populateLevel(){
|
||||
|
||||
}
|
||||
|
||||
public function getSpawn(){
|
||||
return $this->level->getSafeSpawn(new Vector3(127.5, 128, 127.5));
|
||||
}
|
||||
|
||||
}
|
@ -127,7 +127,7 @@ class SuperflatGenerator implements LevelGenerator{
|
||||
|
||||
public function populateChunk($chunkX, $chunkZ){
|
||||
foreach($this->populators as $populator){
|
||||
$this->random->setSeed((int) ($chunkX * 0xdead + $chunkZ * 0xbeef) ^ $this->level->getSeed());
|
||||
$this->random->setSeed(0xdeadbeef ^ ($chunkX << 8) ^ $chunkZ ^ $this->level->getSeed());
|
||||
$populator->populate($this->level, $chunkX, $chunkZ, $this->random);
|
||||
}
|
||||
}
|
||||
|
@ -19,6 +19,49 @@
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
abstract class NoiseGenerator{
|
||||
protected $perm = array();
|
||||
protected $offsetX;
|
||||
protected $offsetY;
|
||||
protected $offsetZ;
|
||||
|
||||
public static function floor($x){
|
||||
return $x >= 0 ? (int) $x : (int) $x - 1;
|
||||
}
|
||||
|
||||
public static function fade($x){
|
||||
return $x * $x * $x * ($x * ($x * 6 - 15) + 10);
|
||||
}
|
||||
|
||||
public static function lerp($x, $y, $z){
|
||||
return $y + $x * ($z - $y);
|
||||
}
|
||||
|
||||
public static function grad($hash, $x, $y, $z){
|
||||
$hash &= 15;
|
||||
$u = $hash < 8 ? $x : $y;
|
||||
$v = $hash < 4 ? $y : (($hash === 12 or $hash === 14) ? $x : $z);
|
||||
return (($hash & 1) === 0 ? $u : -$u) + (($hash & 2) === 0 ? $v : -$v);
|
||||
}
|
||||
|
||||
abstract public function noise($x, $y, $z);
|
||||
|
||||
public function noise3D($x, $y, $z, $octaves, $frequency, $amplitude, $normalized = false){
|
||||
$result = 0;
|
||||
$amp = 1;
|
||||
$freq = 1;
|
||||
$max = 0;
|
||||
|
||||
for($i = 0; $i < $octaves; ++$i){
|
||||
$result += $this->noise($x * $freq, $y * $freq, $z * $freq) * $amp;
|
||||
$max += $amp;
|
||||
$freq *= $frequency;
|
||||
$amp *= $amplitude;
|
||||
}
|
||||
if($normalized === true){
|
||||
$result /= $max;
|
||||
}
|
||||
|
||||
return $result;
|
||||
}
|
@ -1,68 +0,0 @@
|
||||
<?php
|
||||
|
||||
/**
|
||||
*
|
||||
* ____ _ _ __ __ _ __ __ ____
|
||||
* | _ \ ___ ___| | _____| |_| \/ (_)_ __ ___ | \/ | _ \
|
||||
* | |_) / _ \ / __| |/ / _ \ __| |\/| | | '_ \ / _ \_____| |\/| | |_) |
|
||||
* | __/ (_) | (__| < __/ |_| | | | | | | | __/_____| | | | __/
|
||||
* |_| \___/ \___|_|\_\___|\__|_| |_|_|_| |_|\___| |_| |_|_|
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* @author PocketMine Team
|
||||
* @link http://www.pocketmine.net/
|
||||
*
|
||||
*
|
||||
*/
|
||||
|
||||
/***REM_START***/
|
||||
require_once("NoiseGenerator.php");
|
||||
/***REM_END***/
|
||||
|
||||
class NoiseGeneratorOctaves extends NoiseGenerator{
|
||||
public $octaves;
|
||||
private $generatorCollection;
|
||||
public function __construct(Random $random, $octaves){
|
||||
$this->generatorCollection = array();
|
||||
$this->octaves = (int) $octaves;
|
||||
for($o = 0; $o < $this->octaves; ++$o){
|
||||
$this->generatorCollection[$o] = new NoiseGeneratorPerlin($random);
|
||||
}
|
||||
}
|
||||
|
||||
public function generateNoiseOctaves($int1, $int2, $int3, $int4, $int5, $int6, $par1 = false, $par2 = false, $par3 = false){
|
||||
if($par1 === false or $par2 === false or $par3 === false){
|
||||
return $this->generateNoiseOctaves($int1, 10, $int2, $int3, 1, $int4, $int5, 1, $int6);
|
||||
}
|
||||
|
||||
$floats = array();
|
||||
$cnt = $int4 * $int5 * $int6;
|
||||
for($i = 0; $i < $cnt; ++$i){
|
||||
$floats[$i] = 0;
|
||||
}
|
||||
|
||||
$d1 = 1;
|
||||
|
||||
for($j = 0; $j < $this->octaves; ++$j){
|
||||
$d2 = $int1 * $d1 * $par1;
|
||||
$d3 = $int2 * $d1 * $par2;
|
||||
$d4 = $int3 * $d1 * $par3;
|
||||
$l1 = floor($d2);
|
||||
$l2 = floor($d4);
|
||||
$d2 -= $l1;
|
||||
$d4 -= $l2;
|
||||
$l1 %= 16777216;
|
||||
$l2 %= 16777216;
|
||||
|
||||
$d2 += $l1;
|
||||
$d4 += $l2;
|
||||
$this->generatorCollection[$j]->populateNoiseArray($floats, $d2, $d3, $d4, $int4, $int5, $int6, $par1 * $d1, $par2 * $d1, $par3 * $d1, $d1);
|
||||
$d1 /= 2;
|
||||
}
|
||||
return $floats;
|
||||
}
|
||||
}
|
@ -1,169 +0,0 @@
|
||||
<?php
|
||||
|
||||
/**
|
||||
*
|
||||
* ____ _ _ __ __ _ __ __ ____
|
||||
* | _ \ ___ ___| | _____| |_| \/ (_)_ __ ___ | \/ | _ \
|
||||
* | |_) / _ \ / __| |/ / _ \ __| |\/| | | '_ \ / _ \_____| |\/| | |_) |
|
||||
* | __/ (_) | (__| < __/ |_| | | | | | | | __/_____| | | | __/
|
||||
* |_| \___/ \___|_|\_\___|\__|_| |_|_|_| |_|\___| |_| |_|_|
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* @author PocketMine Team
|
||||
* @link http://www.pocketmine.net/
|
||||
*
|
||||
*
|
||||
*/
|
||||
|
||||
/***REM_START***/
|
||||
require_once("NoiseGenerator.php");
|
||||
/***REM_END***/
|
||||
|
||||
class NoiseGeneratorPerlin extends NoiseGenerator{
|
||||
private $permutations = array();
|
||||
public $xCoord, $yCoord, $zCoord;
|
||||
|
||||
public function __construct($random = false){
|
||||
if(!($random instanceof Random)){
|
||||
$random = new Random();
|
||||
}
|
||||
$this->xCoord = $random->nextFloat() * 256;
|
||||
$this->yCoord = $random->nextFloat() * 256;
|
||||
$this->zCoord = $random->nextFloat() * 256;
|
||||
|
||||
for($i = 0; $i < 512; ++$i){
|
||||
$this->permutations[$i] = 0;
|
||||
}
|
||||
for($i = 0; $i < 256; ++$i){
|
||||
$this->permutations[$i] = $i;
|
||||
}
|
||||
|
||||
for($i = 0; $i < 256; ++$i){
|
||||
$j = $random->nextRange(0, 256 - $i) + $i;
|
||||
$k = $this->permutations[$i];
|
||||
$this->permutations[$i] = $this->permutations[$j];
|
||||
$this->permutations[$j] = $k;
|
||||
$this->permutations[$i + 256] = $this->permutations[$i];
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public final function curve($par1, $par2, $par3){
|
||||
return $par2 + $par1 * ($par3 - $par2);
|
||||
}
|
||||
|
||||
public function grad2D($int, $par1, $par2){
|
||||
$i = $int & 0x0F;
|
||||
$d1 = (1 - (($i & 0x08) >> 3)) * $par1;
|
||||
$d2 = ($i === 12 or $i === 14) ? $par1:($i < 4 ? 0:$par2);
|
||||
|
||||
return (($i & 0x01) === 0 ? $d1:-$d1) + (($i & 0x02) === 0 ? $d2:-$d2);
|
||||
}
|
||||
|
||||
public function grad3D($int, $par1, $par2, $par3){
|
||||
$i = $int & 0x0F;
|
||||
$d1 = $i < 8 ? $par1 : $par2;
|
||||
$d2 = ($i === 12 or $i === 14) ? $par1:($i < 4 ? $par2:$par3);
|
||||
|
||||
return (($i & 0x01) === 0 ? $d1:-$d1) + (($i & 0x02) === 0 ? $d2:-$d2);
|
||||
}
|
||||
|
||||
public function populateNoiseArray(&$floats, $par1, $par2, $par3, $int1, $int2, $int3, $par4, $par5, $par6, $par7){
|
||||
if($int2 === 1){
|
||||
$n = 0;
|
||||
$d3 = 1 / $par7;
|
||||
for($i1 = 0; $i1 < $int1; ++$i1){
|
||||
$d4 = $par1 + $i1 * $par4 + $this->xCoord;
|
||||
$i2 = (int) $d4;
|
||||
if($d4 < $i2){
|
||||
--$i2;
|
||||
}
|
||||
$i3 = $i2 & 0xFF;
|
||||
$d4 -= $i2;
|
||||
$d5 = $d4 * $d4 * $d4 * ($d4 * ($d4 * 6 - 15) + 10);
|
||||
|
||||
for($i4 = 0; $i4 < $int3; ++$i4){
|
||||
$d6 = $par3 + $i4 * $par6 + $this->zCoord;
|
||||
$i5 = (int) $d6;
|
||||
if($d6 < $i5){
|
||||
--$i5;
|
||||
}
|
||||
$i6 = $i5 & 0xFF;
|
||||
$d6 -= $i5;
|
||||
$d7 = $d6 * $d6 * $d6 * ($d6 * ($d6 * 6 - 15) + 10);
|
||||
|
||||
$i = $this->permutations[$i3];
|
||||
$j = $this->permutations[$i] + $i6;
|
||||
$k = $this->permutations[$i3 + 1];
|
||||
$m = $this->permutations[$k] + $i6;
|
||||
$d1 = $this->curve($d5, $this->grad2D($this->permutations[$j], $d4, $d6), $this->grad3D($this->permutations[$m], $d4 - 1, 0, $d6));
|
||||
$d2 = $this->curve($d5, $this->grad3D($this->permutations[$j + 1], $d4, 0, $d6 - 1), $this->grad3D($this->permutations[$m + 1], $d4 - 1, 0, $d6 - 1));
|
||||
|
||||
$d8 = $this->curve($d7, $d1, $d2);
|
||||
$floats[$n++] += $d8 * $d3;
|
||||
}
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
$d9 = 1 / $par7;
|
||||
$m = -1;
|
||||
$n = 0;
|
||||
$i = 0;
|
||||
|
||||
for($i4 = 0; $i4 < $int1; ++$i4){
|
||||
$d6 = $par1 + $i4 * $par4 + $this->xCoord;
|
||||
$i5 = (int) $d6;
|
||||
if($d6 < $i5){
|
||||
--$i5;
|
||||
}
|
||||
$i6 = $i5 & 0xFF;
|
||||
$d6 -= $i5;
|
||||
$d7 = $d6 * $d6 * $d6 * ($d6 * ($d6 * 6 - 15) + 10);
|
||||
|
||||
for($i12 = 0; $i12 < $int3; ++$i12){
|
||||
$d12 = $par3 + $i12 * $par6 + $this->zCoord;
|
||||
$i13 = (int) $d12;
|
||||
if($d12 < $i13){
|
||||
--$i13;
|
||||
}
|
||||
$i14 = $i13 & 0xFF;
|
||||
$d12 -= $i13;
|
||||
$d13 = $d12 * $d12 * $d12 * ($d12 * ($d12 * 6 - 15) + 10);
|
||||
|
||||
for($i15 = 0; $i15 < $int2; ++$i15){
|
||||
$d14 = $par2 + $i15 * $par5 + $this->yCoord;
|
||||
$i16 = (int) $d14;
|
||||
if($d14 < $i16){
|
||||
--$i16;
|
||||
}
|
||||
$d14 -= $i16;
|
||||
$d15 = $d14 * $d14 * $d14 * ($d14 * ($d14 * 6 - 15) + 10);
|
||||
|
||||
if($i15 === 0 or $i17 !== $m){
|
||||
$m = $i17;
|
||||
$i7 = $this->permutations[$i6] + $i17;
|
||||
$i8 = $this->permutations[$i7] + $i14;
|
||||
$i9 = $this->permutations[$i7 + 1] + $i14;
|
||||
$i10 = $this->permutations[$i6 + 1] + $i17;
|
||||
$n = $this->permutations[$i10] + $i14;
|
||||
$i11 = $this->permutations[$i10 + 1] + $i14;
|
||||
$d10 = $this->curve($d7, $this->grad3D($this->permutations[$i8], $d6, $d14, $d12), $this->grad3D($this->permutations[$n], $d6 - 1, $d14, $d12));
|
||||
$d4 = $this->curve($d7, $this->grad3D($this->permutations[$i9], $d6, $d14 - 1, $d12), $this->grad3D($this->permutations[$i11], $d6 - 1, $d14 - 1, $d12));
|
||||
$d11 = $this->curve($d7, $this->grad3D($this->permutations[$i8 + 1], $d6, $d14, $d12 - 1), $this->grad3D($this->permutations[$n + 1], $d6 - 1, $d14, $d12 - 1));
|
||||
$d5 = $this->curve($d7, $this->grad3D($this->permutations[$i9 + 1], $d6, $d14 - 1, $d12 - 1), $this->grad3D($this->permutations[$i11 + 1], $d6 - 1, $d14 - 1, $d12 - 1));
|
||||
}
|
||||
|
||||
$d16 = $this->curve($d15, $d10, $d4);
|
||||
$d17 = $this->curve($d15, $d11, $d5);
|
||||
$d18 = $this->curve($d13, $d16, $d17);
|
||||
$floats[$i++] += $d18 * $d9;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
108
src/world/generator/noise/OctaveGenerator.php
Normal file
108
src/world/generator/noise/OctaveGenerator.php
Normal file
@ -0,0 +1,108 @@
|
||||
<?php
|
||||
|
||||
/**
|
||||
*
|
||||
* ____ _ _ __ __ _ __ __ ____
|
||||
* | _ \ ___ ___| | _____| |_| \/ (_)_ __ ___ | \/ | _ \
|
||||
* | |_) / _ \ / __| |/ / _ \ __| |\/| | | '_ \ / _ \_____| |\/| | |_) |
|
||||
* | __/ (_) | (__| < __/ |_| | | | | | | | __/_____| | | | __/
|
||||
* |_| \___/ \___|_|\_\___|\__|_| |_|_|_| |_|\___| |_| |_|_|
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* @author PocketMine Team
|
||||
* @link http://www.pocketmine.net/
|
||||
*
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
abstract class OctaveGenerator{
|
||||
protected $octaves;
|
||||
protected $xScale = 1;
|
||||
protected $yScale = 1;
|
||||
protected $zScale = 1;
|
||||
|
||||
public function __construct(array $octaves){
|
||||
$this->octaves = $octaves;
|
||||
}
|
||||
|
||||
public function setScale($scale){
|
||||
$this->setXScale($scale);
|
||||
$this->setYScale($scale);
|
||||
$this->setZScale($scale);
|
||||
}
|
||||
|
||||
public function getXScale(){
|
||||
return $this->xScale;
|
||||
}
|
||||
|
||||
public function setXScale($scale){
|
||||
$this->xScale = $scale;
|
||||
}
|
||||
|
||||
public function getYScale(){
|
||||
return $this->yScale;
|
||||
}
|
||||
|
||||
public function setYScale($scale){
|
||||
$this->yScale = $scale;
|
||||
}
|
||||
|
||||
public function getZScale(){
|
||||
return $this->zScale;
|
||||
}
|
||||
|
||||
public function setZScale($scale){
|
||||
$this->zScale = $scale;
|
||||
}
|
||||
|
||||
public function getOctaves(){
|
||||
$array = array();
|
||||
foreach($this->octaves as $index => $value){
|
||||
$array[$index] = clone $value;
|
||||
}
|
||||
return $array;
|
||||
}
|
||||
|
||||
//1D-noise
|
||||
public function noise1D($x, $frequency, $amplitude, $normalized = false){
|
||||
return $this->noise3D($x, 0, 0, $frequency, $amplitude, $normalized);
|
||||
}
|
||||
|
||||
//2D-noise
|
||||
public function noise2D($x, $y, $frequency, $amplitude, $normalized = false){
|
||||
return $this->noise3D($x, $y, 0, $frequency, $amplitude, $normalized);
|
||||
}
|
||||
|
||||
//3D-noise
|
||||
public function noise3D($x, $y, $z, $frequency, $amplitude, $normalized = false){
|
||||
$result = 0;
|
||||
$amp = 1;
|
||||
$freq = 1;
|
||||
$max = 0;
|
||||
|
||||
$x *= $this->xScale;
|
||||
$y *= $this->yScale;
|
||||
$z *= $this->zScale;
|
||||
|
||||
foreach($this->octaves as $noiseGenerator){
|
||||
$result += $octave->noise($x * $freq, $y * $freq, $z * $freq) * $amp;
|
||||
$max += $amp;
|
||||
$freq *= $frequency;
|
||||
$amp *= $amplitude;
|
||||
}
|
||||
if($normalized === true){
|
||||
$result /= $max;
|
||||
}
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
||||
public function generateNoiseOctaves($x, $y, $z, $frequency, $amplitude){
|
||||
|
||||
}
|
||||
}
|
96
src/world/generator/noise/PerlinNoiseGenerator.php
Normal file
96
src/world/generator/noise/PerlinNoiseGenerator.php
Normal file
@ -0,0 +1,96 @@
|
||||
<?php
|
||||
|
||||
/**
|
||||
*
|
||||
* ____ _ _ __ __ _ __ __ ____
|
||||
* | _ \ ___ ___| | _____| |_| \/ (_)_ __ ___ | \/ | _ \
|
||||
* | |_) / _ \ / __| |/ / _ \ __| |\/| | | '_ \ / _ \_____| |\/| | |_) |
|
||||
* | __/ (_) | (__| < __/ |_| | | | | | | | __/_____| | | | __/
|
||||
* |_| \___/ \___|_|\_\___|\__|_| |_|_|_| |_|\___| |_| |_|_|
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* @author PocketMine Team
|
||||
* @link http://www.pocketmine.net/
|
||||
*
|
||||
*
|
||||
*/
|
||||
|
||||
/***REM_START***/
|
||||
require_once("NoiseGenerator.php");
|
||||
/***REM_END***/
|
||||
|
||||
class NoiseGeneratorPerlin extends NoiseGenerator[
|
||||
public static $grad3 = [
|
||||
[1, 1, 0], [-1, 1, 0], [1, -1, 0], [-1, -1, 0],
|
||||
[1, 0, 1], [-1, 0, 1], [1, 0, -1], [-1, 0, -1],
|
||||
[0, 1, 1], [0, -1, 1], [0, 1, -1], [0, -1, -1]
|
||||
];
|
||||
|
||||
|
||||
public function __construct(Random $random){
|
||||
$this->offsetX = $random->nextFloat() * 256;
|
||||
$this->offsetY = $random->nextFloat() * 256;
|
||||
$this->offsetZ = $random->nextFloat() * 256;
|
||||
|
||||
for($i = 0; $i < 512; ++$i){
|
||||
$this->perm[$i} = 0;
|
||||
}
|
||||
|
||||
for($i = 0; $i < 256; ++$i){
|
||||
$this->perm[$i} = $random->nextRange(0, 255);
|
||||
}
|
||||
for($i = 0; $i < 256; ++$i)[
|
||||
$pos = $random->nextRange(0, 255 - $i) + $i;
|
||||
$old = $this->perm[$i};
|
||||
|
||||
$this->perm[$i} = $this->perm[$pos};
|
||||
$this->perm[$pos} = $old;
|
||||
$this->perm[$i + 256} = $this->perm[$i};
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public function noise($x, $y, $z){
|
||||
$x += $this->offsetX;
|
||||
$y += $this->offsetY;
|
||||
$z += $this->offsetZ;
|
||||
|
||||
$floorX = self::floor($x);
|
||||
$floorY = self::floor($y);
|
||||
$floorZ = self::floor($z);
|
||||
|
||||
$X = $floorX & 0xFF;
|
||||
$Y = $floorY & 0xFF;
|
||||
$Z = $floorZ & 0xFF;
|
||||
|
||||
$x -= $floorX;
|
||||
$y -= $floorY;
|
||||
$z -= $floorZ;
|
||||
|
||||
//Fade curves
|
||||
$fX = self::fade($x);
|
||||
$fY = self::fade($y);
|
||||
$fZ = self::fade($z);
|
||||
|
||||
//Cube corners
|
||||
$A = $this->perm[$X] + $Y;
|
||||
$AA = $this->perm[$A] + $Z;
|
||||
$AB = $this->perm[$A + 1] + $Z;
|
||||
$B = $this->perm[$X + 1] + $Y;
|
||||
$BA = $this->perm[$B] + $Z;
|
||||
$BB = $this->perm[$B + 1] + $Z;
|
||||
|
||||
return self::lerp($fZ, self::lerp($fY, self::lerp($fX, self::grad($this->perm[$AA]), $x, $y, $z),
|
||||
self::grad($this->perm[$BA], $x - 1, $y, $z),
|
||||
self::lerp($fX, self::grad($this->perm[$AB], $x, $y - 1, $z),
|
||||
self::grad($this->perm[$BB], $x - 1, $y - 1, $z))),
|
||||
self::lerp($fY, self::lerp($fX, self::grad($this->perm[$AA + 1], $x, $y, $z - 1),
|
||||
self::grad($this->perm[$BA + 1], $x - 1, $y, $z - 1)),
|
||||
self::lerp($fX, self::grad($this->perm[$AB + 1], $x, $y - 1, $z - 1),
|
||||
self::grad($this->perm[$BB + 1], $x - 1, $y - 1, $z - 1))));
|
||||
}
|
||||
}
|
35
src/world/generator/noise/PerlinOctaveGenerator.php
Normal file
35
src/world/generator/noise/PerlinOctaveGenerator.php
Normal file
@ -0,0 +1,35 @@
|
||||
<?php
|
||||
|
||||
/**
|
||||
*
|
||||
* ____ _ _ __ __ _ __ __ ____
|
||||
* | _ \ ___ ___| | _____| |_| \/ (_)_ __ ___ | \/ | _ \
|
||||
* | |_) / _ \ / __| |/ / _ \ __| |\/| | | '_ \ / _ \_____| |\/| | |_) |
|
||||
* | __/ (_) | (__| < __/ |_| | | | | | | | __/_____| | | | __/
|
||||
* |_| \___/ \___|_|\_\___|\__|_| |_|_|_| |_|\___| |_| |_|_|
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* @author PocketMine Team
|
||||
* @link http://www.pocketmine.net/
|
||||
*
|
||||
*
|
||||
*/
|
||||
|
||||
/***REM_START***/
|
||||
require_once("OctaveGenerator.php");
|
||||
/***REM_END***/
|
||||
|
||||
class PerlinOctaveGenerator extends OctaveGenerator{
|
||||
public function __construct(Random $random, $octaves){
|
||||
$this->octaves = array();
|
||||
for($o = 0; $o < $octaves; ++$o){
|
||||
$this->octaves[$o] = new NoiseGeneratorPerlin($random);
|
||||
}
|
||||
}
|
||||
|
||||
public function
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user