From 24ba7cbbd1b2fe8b30ac7d7f6fa1f17e0d4f8934 Mon Sep 17 00:00:00 2001 From: Shoghi Cervantes Date: Sat, 1 Jun 2013 00:32:23 +0200 Subject: [PATCH] New direct block method, better block placement sending --- src/API/BlockAPI.php | 11 ---- src/constants/GeneralConstants.php | 18 ++++-- src/material/block/FallableBlock.php | 10 ++- src/material/block/GenericBlock.php | 2 +- src/world/Entity.php | 2 +- src/world/Level.php | 73 ++++++++++++++-------- src/world/generator/SuperflatGenerator.php | 2 +- 7 files changed, 72 insertions(+), 46 deletions(-) diff --git a/src/API/BlockAPI.php b/src/API/BlockAPI.php index bb098a1b02..f3eac4a7a2 100644 --- a/src/API/BlockAPI.php +++ b/src/API/BlockAPI.php @@ -25,17 +25,6 @@ the Free Software Foundation, either version 3 of the License, or */ - -define("BLOCK_UPDATE_NORMAL", 0); -define("BLOCK_UPDATE_RANDOM", 1); -define("BLOCK_UPDATE_SCHEDULED", 2); -define("BLOCK_UPDATE_WEAK", 3); -define("BLOCK_UPDATE_TOUCH", 4); - - - - - class BlockAPI{ private $server; private $scheduledUpdates = array(); diff --git a/src/constants/GeneralConstants.php b/src/constants/GeneralConstants.php index 3ff2e2797d..4990d7788b 100644 --- a/src/constants/GeneralConstants.php +++ b/src/constants/GeneralConstants.php @@ -37,10 +37,18 @@ define("VIEWER", 3); define("PLAYER_RECOVERY_BUFFER", 2048); -//Entities -define("ENTITY_PLAYER", 0); +//Block Updates +define("BLOCK_UPDATE_NORMAL", 1); +define("BLOCK_UPDATE_RANDOM", 2); +define("BLOCK_UPDATE_SCHEDULED", 3); +define("BLOCK_UPDATE_WEAK", 4); +define("BLOCK_UPDATE_TOUCH", 5); -define("ENTITY_MOB", 1); + +//Entities +define("ENTITY_PLAYER", 1); + +define("ENTITY_MOB", 2); define("MOB_CHICKEN", 10); define("MOB_COW", 11); define("MOB_PIG", 12); @@ -52,10 +60,10 @@ define("ENTITY_MOB", 1); define("MOB_SPIDER", 35); define("MOB_PIGMAN", 36); -define("ENTITY_OBJECT", 2); +define("ENTITY_OBJECT", 3); define("OBJECT_PAINTING", 83); -define("ENTITY_ITEM", 3); +define("ENTITY_ITEM", 4); define("ENTITY_FALLING", 4); define("FALLING_SAND", 66); diff --git a/src/material/block/FallableBlock.php b/src/material/block/FallableBlock.php index 9df09ba046..90a8474fbe 100644 --- a/src/material/block/FallableBlock.php +++ b/src/material/block/FallableBlock.php @@ -31,6 +31,12 @@ class FallableBlock extends SolidBlock{ $this->hasPhysics = true; } + public function place(Item $item, Player $player, Block $block, Block $target, $face, $fx, $fy, $fz){ + $ret = $this->level->setBlock($this, $this, true, false, true); + ServerAPI::request()->api->block->blockUpdate($this, BLOCK_UPDATE_NORMAL); + return $ret; + } + public function onUpdate($type){ if($this->getSide(0)->getID() === AIR){ $data = array( @@ -40,9 +46,11 @@ class FallableBlock extends SolidBlock{ "Tile" => $this->id, ); $server = ServerAPI::request(); - $this->level->setBlock($this, new AirBlock()); + $this->level->setBlock($this, new AirBlock(), false, false, true); $e = $server->api->entity->add($this->level, ENTITY_FALLING, FALLING_SAND, $data); $server->api->entity->spawnToAll($this->level, $e->eid); + return BLOCK_UPDATE_NORMAL; } + return false; } } \ No newline at end of file diff --git a/src/material/block/GenericBlock.php b/src/material/block/GenericBlock.php index 4f7bd46da8..1f99f44657 100644 --- a/src/material/block/GenericBlock.php +++ b/src/material/block/GenericBlock.php @@ -31,7 +31,7 @@ class GenericBlock extends Block{ parent::__construct($id, $meta, $name); } public function place(Item $item, Player $player, Block $block, Block $target, $face, $fx, $fy, $fz){ - return $this->level->setBlock($block, $this); + return $this->level->setBlock($this, $this, true, false, true); } public function isBreakable(Item $item, Player $player){ diff --git a/src/world/Entity.php b/src/world/Entity.php index e07cafd86f..cde9da6e86 100644 --- a/src/world/Entity.php +++ b/src/world/Entity.php @@ -400,7 +400,7 @@ class Entity extends Position{ if($fall->isFullBlock === false or $down->isFullBlock === false){ $this->server->api->entity->drop($this, BlockAPI::getItem($this->data["Tile"] & 0xFFFF, 0, 1), true); }else{ - $this->level->setBlock($fall, BlockAPI::get($this->data["Tile"])); + $this->level->setBlock($fall, BlockAPI::get($this->data["Tile"]), true, false, true); } $this->server->api->handle("entity.motion", $this); $this->close(); diff --git a/src/world/Level.php b/src/world/Level.php index 95c8fbe748..288ae4b52a 100644 --- a/src/world/Level.php +++ b/src/world/Level.php @@ -26,7 +26,7 @@ the Free Software Foundation, either version 3 of the License, or */ class Level{ - public $entities, $tileEntities, $nextSave; + public $entities, $tileEntities, $nextSave, $players = array(); private $level, $time, $startCheck, $startTime, $server, $name, $usedChunks, $changedBlocks, $changedCount; public function __construct(PMFLevel $level, Config $entities, Config $tileEntities, $name){ @@ -63,12 +63,12 @@ class Level{ } public function checkThings(){ - $players = $this->server->api->player->getAll($this); + $this->players = $this->server->api->player->getAll($this); $now = microtime(true); $time = $this->startTime + ($now - $this->startCheck) * 20; if($this->server->api->dhandle("time.change", array("level" => $this, "time" => $time)) !== false){ $this->time = $time; - $this->server->api->player->broadcastPacket($players, MC_SET_TIME, array( + $this->server->api->player->broadcastPacket($this->players, MC_SET_TIME, array( "time" => $this->time, )); } @@ -80,7 +80,7 @@ class Level{ if($count < 582){//Optimal value, calculated using the relation between minichunks and single packets break; } - foreach($players as $p){ + foreach($this->players as $p){ unset($p->chunksLoaded[$index]); } unset($this->changedBlocks[$index]); @@ -90,7 +90,7 @@ class Level{ if(count($this->changedBlocks) > 0){ foreach($this->changedBlocks as $blocks){ foreach($blocks as $b){ - $this->server->api->player->broadcastPacket($players, MC_UPDATE_BLOCK, array( + $this->server->api->player->broadcastPacket($this->players, MC_UPDATE_BLOCK, array( "x" => $b->x, "y" => $b->y, "z" => $b->z, @@ -205,20 +205,33 @@ class Level{ return BlockAPI::get($b[0], $b[1], new Position($pos->x, $pos->y, $pos->z, $this)); } - public function setBlockRaw(Vector3 $pos, Block $block){ + public function setBlockRaw(Vector3 $pos, Block $block, $direct = true){ if(($ret = $this->level->setBlock($pos->x, $pos->y, $pos->z, $block->getID(), $block->getMetadata())) === true){ - $i = ($pos->x >> 4).":".($pos->y >> 4).":".($pos->z >> 4); - if(!isset($this->changedBlocks[$i])){ - $this->changedBlocks[$i] = array(); - $this->changedCount[$i] = 0; + if($direct === true){ + $this->server->api->player->broadcastPacket($this->players, MC_UPDATE_BLOCK, array( + "x" => $pos->x, + "y" => $pos->y, + "z" => $pos->z, + "block" => $block->getID(), + "meta" => $block->getMetadata(), + )); + }elseif($direct === false){ + if(!($block->level instanceof Level)){ + $block->position($pos); + } + $i = ($pos->x >> 4).":".($pos->y >> 4).":".($pos->z >> 4); + if(!isset($this->changedBlocks[$i])){ + $this->changedBlocks[$i] = array(); + $this->changedCount[$i] = 0; + } + $this->changedBlocks[$i][] = $block; + ++$this->changedCount[$i]; } - $this->changedBlocks[$i][] = $block; - ++$this->changedCount[$i]; } return $ret; } - public function setBlock(Vector3 $pos, Block $block, $update = true, $tiles = false){ + public function setBlock(Vector3 $pos, Block $block, $update = true, $tiles = false, $direct = false){ if((($pos instanceof Position) and $pos->level !== $this) or $pos->x < 0 or $pos->y < 0 or $pos->z < 0){ return false; } @@ -228,21 +241,29 @@ class Level{ if(!($pos instanceof Position)){ $pos = new Position($pos->x, $pos->y, $pos->z, $this); } - $block = $this->getBlock($pos); - - $i = ($pos->x >> 4).":".($pos->y >> 4).":".($pos->z >> 4); - if(!isset($this->changedBlocks[$i])){ - $this->changedBlocks[$i] = array(); - $this->changedCount[$i] = 0; + if(!($block->level instanceof Level)){ + $block->position($pos); } - $this->changedBlocks[$i][] = $block; - ++$this->changedCount[$i]; - /*$this->server->trigger("block.change", array( - "position" => $pos, - "block" => $block, - ));*/ + if($direct === true){ + $this->server->api->player->broadcastPacket($this->players, MC_UPDATE_BLOCK, array( + "x" => $pos->x, + "y" => $pos->y, + "z" => $pos->z, + "block" => $block->getID(), + "meta" => $block->getMetadata(), + )); + }else{ + $i = ($pos->x >> 4).":".($pos->y >> 4).":".($pos->z >> 4); + if(!isset($this->changedBlocks[$i])){ + $this->changedBlocks[$i] = array(); + $this->changedCount[$i] = 0; + } + $this->changedBlocks[$i][] = $block; + ++$this->changedCount[$i]; + } + if($update === true){ - $this->server->api->block->scheduleBlockUpdate($block, 1, BLOCK_UPDATE_NORMAL); //????? water? + $this->server->api->block->blockUpdateAround($pos, BLOCK_UPDATE_NORMAL, 1); } if($tiles === true){ diff --git a/src/world/generator/SuperflatGenerator.php b/src/world/generator/SuperflatGenerator.php index 88c4c13f87..3308138d00 100644 --- a/src/world/generator/SuperflatGenerator.php +++ b/src/world/generator/SuperflatGenerator.php @@ -134,7 +134,7 @@ class SuperflatGenerator implements LevelGenerator{ for($x = $start; $x <= $end; ++$x){ for($z = $start; $z <= $end; ++$z){ if(floor(sqrt(pow($x - 128, 2) + pow($z - 128, 2))) <= $spawn[0]){ - $this->level->setBlockRaw(new Vector3($x, $this->floorLevel - 1, $z), $spawn[1]); + $this->level->setBlockRaw(new Vector3($x, $this->floorLevel - 1, $z), $spawn[1], null); } } }