Merge branch 'stable'

This commit is contained in:
Dylan K. Taylor 2019-04-25 15:27:13 +01:00
commit c5ca623124
20 changed files with 722 additions and 307 deletions

File diff suppressed because it is too large Load Diff

File diff suppressed because one or more lines are too long

@ -1 +1 @@
Subproject commit 33566f555fc720b3d4a5af1acf7c744a98e37170 Subproject commit 44366c633f31ab19ecb916b451ca1aeacd4972c2

View File

@ -36,10 +36,7 @@ namespace pocketmine {
use pocketmine\utils\VersionString; use pocketmine\utils\VersionString;
use pocketmine\wizard\SetupWizard; use pocketmine\wizard\SetupWizard;
const NAME = "PocketMine-MP"; require_once __DIR__ . '/VersionInfo.php';
const BASE_VERSION = "4.0.0";
const IS_DEVELOPMENT_BUILD = true;
const BUILD_NUMBER = 0;
const MIN_PHP_VERSION = "7.2.0"; const MIN_PHP_VERSION = "7.2.0";

View File

@ -0,0 +1,27 @@
<?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/
*
*
*/
namespace pocketmine;
const NAME = "PocketMine-MP";
const BASE_VERSION = "4.0.0";
const IS_DEVELOPMENT_BUILD = true;
const BUILD_NUMBER = 0;

View File

@ -141,68 +141,70 @@ abstract class Entity extends Location implements Metadatable, EntityIds{
public const DATA_LEAD_HOLDER_EID = 37; //long public const DATA_LEAD_HOLDER_EID = 37; //long
public const DATA_SCALE = 38; //float public const DATA_SCALE = 38; //float
public const DATA_HAS_NPC_COMPONENT = 39; //byte (???) public const DATA_HAS_NPC_COMPONENT = 39; //byte (???)
public const DATA_NPC_SKIN_ID = 40; //string public const DATA_SKIN_ID = 40; //string
public const DATA_URL_TAG = 41; //string public const DATA_NPC_SKIN_ID = 41; //string
public const DATA_MAX_AIR = 42; //short public const DATA_URL_TAG = 42; //string
public const DATA_MARK_VARIANT = 43; //int public const DATA_MAX_AIR = 43; //short
public const DATA_CONTAINER_TYPE = 44; //byte (ContainerComponent) public const DATA_MARK_VARIANT = 44; //int
public const DATA_CONTAINER_BASE_SIZE = 45; //int (ContainerComponent) public const DATA_CONTAINER_TYPE = 45; //byte (ContainerComponent)
public const DATA_CONTAINER_EXTRA_SLOTS_PER_STRENGTH = 46; //int (used for llamas, inventory size is baseSize + thisProp * strength) public const DATA_CONTAINER_BASE_SIZE = 46; //int (ContainerComponent)
public const DATA_BLOCK_TARGET = 47; //block coords (ender crystal) public const DATA_CONTAINER_EXTRA_SLOTS_PER_STRENGTH = 47; //int (used for llamas, inventory size is baseSize + thisProp * strength)
public const DATA_WITHER_INVULNERABLE_TICKS = 48; //int public const DATA_BLOCK_TARGET = 48; //block coords (ender crystal)
public const DATA_WITHER_TARGET_1 = 49; //long public const DATA_WITHER_INVULNERABLE_TICKS = 49; //int
public const DATA_WITHER_TARGET_2 = 50; //long public const DATA_WITHER_TARGET_1 = 50; //long
public const DATA_WITHER_TARGET_3 = 51; //long public const DATA_WITHER_TARGET_2 = 51; //long
/* 52 (short) */ public const DATA_WITHER_TARGET_3 = 52; //long
public const DATA_BOUNDING_BOX_WIDTH = 53; //float /* 53 (short) */
public const DATA_BOUNDING_BOX_HEIGHT = 54; //float public const DATA_BOUNDING_BOX_WIDTH = 54; //float
public const DATA_FUSE_LENGTH = 55; //int public const DATA_BOUNDING_BOX_HEIGHT = 55; //float
public const DATA_RIDER_SEAT_POSITION = 56; //vector3f public const DATA_FUSE_LENGTH = 56; //int
public const DATA_RIDER_ROTATION_LOCKED = 57; //byte public const DATA_RIDER_SEAT_POSITION = 57; //vector3f
public const DATA_RIDER_MAX_ROTATION = 58; //float public const DATA_RIDER_ROTATION_LOCKED = 58; //byte
public const DATA_RIDER_MIN_ROTATION = 59; //float public const DATA_RIDER_MAX_ROTATION = 59; //float
public const DATA_AREA_EFFECT_CLOUD_RADIUS = 60; //float public const DATA_RIDER_MIN_ROTATION = 60; //float
public const DATA_AREA_EFFECT_CLOUD_WAITING = 61; //int public const DATA_AREA_EFFECT_CLOUD_RADIUS = 61; //float
public const DATA_AREA_EFFECT_CLOUD_PARTICLE_ID = 62; //int public const DATA_AREA_EFFECT_CLOUD_WAITING = 62; //int
/* 63 (int) shulker-related */ public const DATA_AREA_EFFECT_CLOUD_PARTICLE_ID = 63; //int
public const DATA_SHULKER_ATTACH_FACE = 64; //byte /* 64 (int) shulker-related */
/* 65 (short) shulker-related */ public const DATA_SHULKER_ATTACH_FACE = 65; //byte
public const DATA_SHULKER_ATTACH_POS = 66; //block coords /* 66 (short) shulker-related */
public const DATA_TRADING_PLAYER_EID = 67; //long public const DATA_SHULKER_ATTACH_POS = 67; //block coords
public const DATA_TRADING_PLAYER_EID = 68; //long
/* 69 (byte) command-block */ /* 70 (byte) command-block */
public const DATA_COMMAND_BLOCK_COMMAND = 70; //string public const DATA_COMMAND_BLOCK_COMMAND = 71; //string
public const DATA_COMMAND_BLOCK_LAST_OUTPUT = 71; //string public const DATA_COMMAND_BLOCK_LAST_OUTPUT = 72; //string
public const DATA_COMMAND_BLOCK_TRACK_OUTPUT = 72; //byte public const DATA_COMMAND_BLOCK_TRACK_OUTPUT = 73; //byte
public const DATA_CONTROLLING_RIDER_SEAT_NUMBER = 73; //byte public const DATA_CONTROLLING_RIDER_SEAT_NUMBER = 74; //byte
public const DATA_STRENGTH = 74; //int public const DATA_STRENGTH = 75; //int
public const DATA_MAX_STRENGTH = 75; //int public const DATA_MAX_STRENGTH = 76; //int
/* 76 (int) */ /* 77 (int) */
public const DATA_LIMITED_LIFE = 77; public const DATA_LIMITED_LIFE = 78;
public const DATA_ARMOR_STAND_POSE_INDEX = 78; //int public const DATA_ARMOR_STAND_POSE_INDEX = 79; //int
public const DATA_ENDER_CRYSTAL_TIME_OFFSET = 79; //int public const DATA_ENDER_CRYSTAL_TIME_OFFSET = 80; //int
public const DATA_ALWAYS_SHOW_NAMETAG = 80; //byte: -1 = default, 0 = only when looked at, 1 = always public const DATA_ALWAYS_SHOW_NAMETAG = 81; //byte: -1 = default, 0 = only when looked at, 1 = always
public const DATA_COLOR_2 = 81; //byte public const DATA_COLOR_2 = 82; //byte
/* 82 (unknown) */ /* 83 (unknown) */
public const DATA_SCORE_TAG = 83; //string public const DATA_SCORE_TAG = 84; //string
public const DATA_BALLOON_ATTACHED_ENTITY = 84; //int64, entity unique ID of owner public const DATA_BALLOON_ATTACHED_ENTITY = 85; //int64, entity unique ID of owner
public const DATA_PUFFERFISH_SIZE = 85; //byte public const DATA_PUFFERFISH_SIZE = 86; //byte
public const DATA_BOAT_BUBBLE_TIME = 86; //int (time in bubble column) public const DATA_BOAT_BUBBLE_TIME = 87; //int (time in bubble column)
public const DATA_PLAYER_AGENT_EID = 87; //long public const DATA_PLAYER_AGENT_EID = 88; //long
/* 88 (float) related to panda sitting /* 89 (float) related to panda sitting
* 89 (float) related to panda sitting */ * 90 (float) related to panda sitting */
public const DATA_EAT_COUNTER = 90; //int (used by pandas) public const DATA_EAT_COUNTER = 91; //int (used by pandas)
public const DATA_FLAGS2 = 91; //long (extended data flags) public const DATA_FLAGS2 = 92; //long (extended data flags)
/* 92 (float) related to panda lying down /* 93 (float) related to panda lying down
* 93 (float) related to panda lying down */ * 94 (float) related to panda lying down */
public const DATA_AREA_EFFECT_CLOUD_DURATION = 94; //int public const DATA_AREA_EFFECT_CLOUD_DURATION = 95; //int
public const DATA_AREA_EFFECT_CLOUD_SPAWN_TIME = 95; //int public const DATA_AREA_EFFECT_CLOUD_SPAWN_TIME = 96; //int
public const DATA_AREA_EFFECT_CLOUD_RADIUS_PER_TICK = 96; //float, usually negative public const DATA_AREA_EFFECT_CLOUD_RADIUS_PER_TICK = 97; //float, usually negative
public const DATA_AREA_EFFECT_CLOUD_RADIUS_CHANGE_ON_PICKUP = 97; //float public const DATA_AREA_EFFECT_CLOUD_RADIUS_CHANGE_ON_PICKUP = 98; //float
public const DATA_AREA_EFFECT_CLOUD_PICKUP_COUNT = 98; //int public const DATA_AREA_EFFECT_CLOUD_PICKUP_COUNT = 99; //int
public const DATA_INTERACTIVE_TAG = 99; //string (button text) public const DATA_INTERACTIVE_TAG = 100; //string (button text)
public const DATA_TRADE_TIER = 100; //int public const DATA_TRADE_TIER = 101; //int
public const DATA_MAX_TRADE_TIER = 101; //int public const DATA_MAX_TRADE_TIER = 102; //int
public const DATA_TRADE_XP = 103; //int
public const DATA_FLAG_ONFIRE = 0; public const DATA_FLAG_ONFIRE = 0;
public const DATA_FLAG_SNEAKING = 1; public const DATA_FLAG_SNEAKING = 1;
@ -278,12 +280,20 @@ abstract class Entity extends Location implements Metadatable, EntityIds{
public const DATA_FLAG_BLOCKING = 71; //shield public const DATA_FLAG_BLOCKING = 71; //shield
public const DATA_FLAG_DISABLE_BLOCKING = 72; public const DATA_FLAG_DISABLE_BLOCKING = 72;
//73 is set when a player is attacked while using shield, unclear on purpose //73 is set when a player is attacked while using shield, unclear on purpose
public const DATA_FLAG_SLEEPING = 74; //74 related to shield usage, needs further investigation
//75 related to sleeping, unclear usage public const DATA_FLAG_SLEEPING = 75;
public const DATA_FLAG_TRADE_INTEREST = 76; //76 related to sleeping, unclear usage
public const DATA_FLAG_DOOR_BREAKER = 77; //... public const DATA_FLAG_TRADE_INTEREST = 77;
public const DATA_FLAG_BREAKING_OBSTRUCTION = 78; public const DATA_FLAG_DOOR_BREAKER = 78; //...
public const DATA_FLAG_DOOR_OPENER = 79; //... public const DATA_FLAG_BREAKING_OBSTRUCTION = 79;
public const DATA_FLAG_DOOR_OPENER = 80; //...
public const DATA_FLAG_ILLAGER_CAPTAIN = 81;
public const DATA_FLAG_STUNNED = 82;
public const DATA_FLAG_ROARING = 83;
public const DATA_FLAG_DELAYED_ATTACKING = 84;
public const DATA_FLAG_AVOIDING_MOBS = 85;
//86 used by RangedAttackGoal
//87 used by NearestAttackableTargetGoal
public const DATA_PLAYER_FLAG_SLEEP = 1; public const DATA_PLAYER_FLAG_SLEEP = 1;
public const DATA_PLAYER_FLAG_DEAD = 2; //TODO: CHECK public const DATA_PLAYER_FLAG_DEAD = 2; //TODO: CHECK

View File

@ -58,12 +58,18 @@ class CraftingManager{
foreach($recipes as $recipe){ foreach($recipes as $recipe){
switch($recipe["type"]){ switch($recipe["type"]){
case 0: case 0:
if($recipe["block"] !== "crafting_table"){ //TODO: filter others out for now to avoid breaking economics
break;
}
$this->registerShapelessRecipe(new ShapelessRecipe( $this->registerShapelessRecipe(new ShapelessRecipe(
array_map(function(array $data) : Item{ return Item::jsonDeserialize($data); }, $recipe["input"]), array_map(function(array $data) : Item{ return Item::jsonDeserialize($data); }, $recipe["input"]),
array_map(function(array $data) : Item{ return Item::jsonDeserialize($data); }, $recipe["output"]) array_map(function(array $data) : Item{ return Item::jsonDeserialize($data); }, $recipe["output"])
)); ));
break; break;
case 1: case 1:
if($recipe["block"] !== "crafting_table"){ //TODO: filter others out for now to avoid breaking economics
break;
}
$this->registerShapedRecipe(new ShapedRecipe( $this->registerShapedRecipe(new ShapedRecipe(
$recipe["shape"], $recipe["shape"],
array_map(function(array $data) : Item{ return Item::jsonDeserialize($data); }, $recipe["input"]), array_map(function(array $data) : Item{ return Item::jsonDeserialize($data); }, $recipe["input"]),
@ -72,6 +78,9 @@ class CraftingManager{
break; break;
case 2: case 2:
case 3: case 3:
if($recipe["block"] !== "furnace"){ //TODO: filter others out for now to avoid breaking economics
break;
}
$result = $recipe["output"]; $result = $recipe["output"];
$resultItem = Item::jsonDeserialize($result); $resultItem = Item::jsonDeserialize($result);
$this->registerFurnaceRecipe(new FurnaceRecipe($resultItem, ItemFactory::get($recipe["inputId"], $recipe["inputDamage"] ?? -1, 1))); $this->registerFurnaceRecipe(new FurnaceRecipe($resultItem, ItemFactory::get($recipe["inputId"], $recipe["inputDamage"] ?? -1, 1)));

View File

@ -74,6 +74,7 @@ use pocketmine\network\mcpe\protocol\LevelSoundEventPacket;
use pocketmine\network\mcpe\protocol\LevelSoundEventPacketV1; use pocketmine\network\mcpe\protocol\LevelSoundEventPacketV1;
use pocketmine\network\mcpe\protocol\LevelSoundEventPacketV2; use pocketmine\network\mcpe\protocol\LevelSoundEventPacketV2;
use pocketmine\network\mcpe\protocol\LoginPacket; use pocketmine\network\mcpe\protocol\LoginPacket;
use pocketmine\network\mcpe\protocol\MapCreateLockedCopyPacket;
use pocketmine\network\mcpe\protocol\MapInfoRequestPacket; use pocketmine\network\mcpe\protocol\MapInfoRequestPacket;
use pocketmine\network\mcpe\protocol\MobArmorEquipmentPacket; use pocketmine\network\mcpe\protocol\MobArmorEquipmentPacket;
use pocketmine\network\mcpe\protocol\MobEffectPacket; use pocketmine\network\mcpe\protocol\MobEffectPacket;
@ -86,6 +87,7 @@ use pocketmine\network\mcpe\protocol\MovePlayerPacket;
use pocketmine\network\mcpe\protocol\NetworkChunkPublisherUpdatePacket; use pocketmine\network\mcpe\protocol\NetworkChunkPublisherUpdatePacket;
use pocketmine\network\mcpe\protocol\NetworkStackLatencyPacket; use pocketmine\network\mcpe\protocol\NetworkStackLatencyPacket;
use pocketmine\network\mcpe\protocol\NpcRequestPacket; use pocketmine\network\mcpe\protocol\NpcRequestPacket;
use pocketmine\network\mcpe\protocol\OnScreenTextureAnimationPacket;
use pocketmine\network\mcpe\protocol\PhotoTransferPacket; use pocketmine\network\mcpe\protocol\PhotoTransferPacket;
use pocketmine\network\mcpe\protocol\PlayerActionPacket; use pocketmine\network\mcpe\protocol\PlayerActionPacket;
use pocketmine\network\mcpe\protocol\PlayerHotbarPacket; use pocketmine\network\mcpe\protocol\PlayerHotbarPacket;
@ -650,4 +652,12 @@ abstract class SessionHandler{
public function handleVideoStreamConnect(VideoStreamConnectPacket $packet) : bool{ public function handleVideoStreamConnect(VideoStreamConnectPacket $packet) : bool{
return false; return false;
} }
public function handleMapCreateLockedCopy(MapCreateLockedCopyPacket $packet) : bool{
return false;
}
public function handleOnScreenTextureAnimation(OnScreenTextureAnimationPacket $packet) : bool{
return false;
}
} }

File diff suppressed because one or more lines are too long

View File

@ -50,6 +50,8 @@ class ClientboundMapItemDataPacket extends DataPacket implements ClientboundPack
public $type; public $type;
/** @var int */ /** @var int */
public $dimensionId = DimensionIds::OVERWORLD; public $dimensionId = DimensionIds::OVERWORLD;
/** @var bool */
public $isLocked = false;
/** @var int[] */ /** @var int[] */
public $eids = []; public $eids = [];
@ -76,6 +78,7 @@ class ClientboundMapItemDataPacket extends DataPacket implements ClientboundPack
$this->mapId = $this->getEntityUniqueId(); $this->mapId = $this->getEntityUniqueId();
$this->type = $this->getUnsignedVarInt(); $this->type = $this->getUnsignedVarInt();
$this->dimensionId = $this->getByte(); $this->dimensionId = $this->getByte();
$this->isLocked = $this->getBool();
if(($this->type & 0x08) !== 0){ if(($this->type & 0x08) !== 0){
$count = $this->getUnsignedVarInt(); $count = $this->getUnsignedVarInt();
@ -148,6 +151,7 @@ class ClientboundMapItemDataPacket extends DataPacket implements ClientboundPack
$this->putUnsignedVarInt($type); $this->putUnsignedVarInt($type);
$this->putByte($this->dimensionId); $this->putByte($this->dimensionId);
$this->putBool($this->isLocked);
if(($type & 0x08) !== 0){ //TODO: find out what these are for if(($type & 0x08) !== 0){ //TODO: find out what these are for
$this->putUnsignedVarInt($eidsCount); $this->putUnsignedVarInt($eidsCount);

View File

@ -78,6 +78,7 @@ class CraftingDataPacket extends DataPacket implements ClientboundPacket{
$entry["output"][] = $this->getSlot(); $entry["output"][] = $this->getSlot();
} }
$entry["uuid"] = $this->getUUID()->toString(); $entry["uuid"] = $this->getUUID()->toString();
$entry["block"] = $this->getString();
break; break;
case self::ENTRY_SHAPED: case self::ENTRY_SHAPED:
@ -95,6 +96,8 @@ class CraftingDataPacket extends DataPacket implements ClientboundPacket{
$entry["output"][] = $this->getSlot(); $entry["output"][] = $this->getSlot();
} }
$entry["uuid"] = $this->getUUID()->toString(); $entry["uuid"] = $this->getUUID()->toString();
$entry["block"] = $this->getString();
break; break;
case self::ENTRY_FURNACE: case self::ENTRY_FURNACE:
case self::ENTRY_FURNACE_DATA: case self::ENTRY_FURNACE_DATA:
@ -103,6 +106,8 @@ class CraftingDataPacket extends DataPacket implements ClientboundPacket{
$entry["inputDamage"] = $this->getVarInt(); $entry["inputDamage"] = $this->getVarInt();
} }
$entry["output"] = $this->getSlot(); $entry["output"] = $this->getSlot();
$entry["block"] = $this->getString();
break; break;
case self::ENTRY_MULTI: case self::ENTRY_MULTI:
$entry["uuid"] = $this->getUUID()->toString(); $entry["uuid"] = $this->getUUID()->toString();
@ -141,6 +146,7 @@ class CraftingDataPacket extends DataPacket implements ClientboundPacket{
} }
$stream->put(str_repeat("\x00", 16)); //Null UUID $stream->put(str_repeat("\x00", 16)); //Null UUID
$stream->putString("crafting_table"); //TODO: blocktype (no prefix) (this might require internal API breaks)
return CraftingDataPacket::ENTRY_SHAPELESS; return CraftingDataPacket::ENTRY_SHAPELESS;
} }
@ -162,23 +168,21 @@ class CraftingDataPacket extends DataPacket implements ClientboundPacket{
} }
$stream->put(str_repeat("\x00", 16)); //Null UUID $stream->put(str_repeat("\x00", 16)); //Null UUID
$stream->putString("crafting_table"); //TODO: blocktype (no prefix) (this might require internal API breaks)
return CraftingDataPacket::ENTRY_SHAPED; return CraftingDataPacket::ENTRY_SHAPED;
} }
private static function writeFurnaceRecipe(FurnaceRecipe $recipe, NetworkBinaryStream $stream) : int{ private static function writeFurnaceRecipe(FurnaceRecipe $recipe, NetworkBinaryStream $stream){
$stream->putVarInt($recipe->getInput()->getId());
$result = CraftingDataPacket::ENTRY_FURNACE;
if(!$recipe->getInput()->hasAnyDamageValue()){ //Data recipe if(!$recipe->getInput()->hasAnyDamageValue()){ //Data recipe
$stream->putVarInt($recipe->getInput()->getId());
$stream->putVarInt($recipe->getInput()->getMeta()); $stream->putVarInt($recipe->getInput()->getMeta());
$stream->putSlot($recipe->getResult()); $result = CraftingDataPacket::ENTRY_FURNACE_DATA;
return CraftingDataPacket::ENTRY_FURNACE_DATA;
}else{
$stream->putVarInt($recipe->getInput()->getId());
$stream->putSlot($recipe->getResult());
return CraftingDataPacket::ENTRY_FURNACE;
} }
$stream->putSlot($recipe->getResult());
$stream->putString("furnace"); //TODO: blocktype (no prefix) (this might require internal API breaks)
return $result;
} }
public function addShapelessRecipe(ShapelessRecipe $recipe) : void{ public function addShapelessRecipe(ShapelessRecipe $recipe) : void{

View File

@ -33,6 +33,8 @@ class LecternUpdatePacket extends DataPacket implements ServerboundPacket{
/** @var int */ /** @var int */
public $page; public $page;
/** @var int */ /** @var int */
public $totalPages;
/** @var int */
public $x; public $x;
/** @var int */ /** @var int */
public $y; public $y;
@ -43,12 +45,14 @@ class LecternUpdatePacket extends DataPacket implements ServerboundPacket{
protected function decodePayload() : void{ protected function decodePayload() : void{
$this->page = $this->getByte(); $this->page = $this->getByte();
$this->totalPages = $this->getByte();
$this->getBlockPosition($this->x, $this->y, $this->z); $this->getBlockPosition($this->x, $this->y, $this->z);
$this->dropBook = $this->getBool(); $this->dropBook = $this->getBool();
} }
protected function encodePayload() : void{ protected function encodePayload() : void{
$this->putByte($this->page); $this->putByte($this->page);
$this->putByte($this->totalPages);
$this->putBlockPosition($this->x, $this->y, $this->z); $this->putBlockPosition($this->x, $this->y, $this->z);
$this->putBool($this->dropBook); $this->putBool($this->dropBook);
} }

View File

@ -218,7 +218,7 @@ class LevelSoundEventPacket extends DataPacket implements ClientboundPacket, Ser
public const SOUND_ITEM_TRIDENT_THUNDER = 184; public const SOUND_ITEM_TRIDENT_THUNDER = 184;
public const SOUND_ITEM_TRIDENT_HIT_GROUND = 185; public const SOUND_ITEM_TRIDENT_HIT_GROUND = 185;
public const SOUND_DEFAULT = 186; public const SOUND_DEFAULT = 186;
public const SOUND_BLOCK_FLETCHING_TABLE_USE = 187;
public const SOUND_ELEMCONSTRUCT_OPEN = 188; public const SOUND_ELEMCONSTRUCT_OPEN = 188;
public const SOUND_ICEBOMB_HIT = 189; public const SOUND_ICEBOMB_HIT = 189;
public const SOUND_BALLOONPOP = 190; public const SOUND_BALLOONPOP = 190;
@ -283,7 +283,26 @@ class LevelSoundEventPacket extends DataPacket implements ClientboundPacket, Ser
public const SOUND_AMBIENT_AGGRESSIVE = 252; public const SOUND_AMBIENT_AGGRESSIVE = 252;
public const SOUND_AMBIENT_WORRIED = 253; public const SOUND_AMBIENT_WORRIED = 253;
public const SOUND_CANT_BREED = 254; public const SOUND_CANT_BREED = 254;
public const SOUND_UNDEFINED = 255; public const SOUND_ITEM_SHIELD_BLOCK = 255;
public const SOUND_ITEM_BOOK_PUT = 256;
public const SOUND_BLOCK_GRINDSTONE_USE = 257;
public const SOUND_BLOCK_BELL_HIT = 258;
public const SOUND_BLOCK_CAMPFIRE_CRACKLE = 259;
public const SOUND_ROAR = 260;
public const SOUND_STUN = 261;
public const SOUND_BLOCK_SWEET_BERRY_BUSH_HURT = 262;
public const SOUND_BLOCK_SWEET_BERRY_BUSH_PICK = 263;
public const SOUND_UI_CARTOGRAPHY_TABLE_TAKE_RESULT = 264;
public const SOUND_UI_STONECUTTER_TAKE_RESULT = 265;
public const SOUND_BLOCK_COMPOSTER_EMPTY = 266;
public const SOUND_BLOCK_COMPOSTER_FILL = 267;
public const SOUND_BLOCK_COMPOSTER_FILL_SUCCESS = 268;
public const SOUND_BLOCK_COMPOSTER_READY = 269;
public const SOUND_BLOCK_BARREL_OPEN = 270;
public const SOUND_BLOCK_BARREL_CLOSE = 271;
public const SOUND_RAID_HORN = 272;
public const SOUND_BLOCK_LOOM_USE = 273;
public const SOUND_UNDEFINED = 274;
public static function create(int $sound, ?Vector3 $pos, int $extraData = -1, string $entityType = ":", bool $isBabyMob = false) : self{ public static function create(int $sound, ?Vector3 $pos, int $extraData = -1, string $entityType = ":", bool $isBabyMob = false) : self{
$result = new self; $result = new self;

View File

@ -0,0 +1,51 @@
<?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/
*
*
*/
declare(strict_types=1);
namespace pocketmine\network\mcpe\protocol;
#include <rules/DataPacket.h>
use pocketmine\network\mcpe\handler\SessionHandler;
class MapCreateLockedCopyPacket extends DataPacket{
public const NETWORK_ID = ProtocolInfo::MAP_CREATE_LOCKED_COPY_PACKET;
/** @var int */
public $originalMapId;
/** @var int */
public $newMapId;
protected function decodePayload() : void{
$this->originalMapId = $this->getEntityUniqueId();
$this->newMapId = $this->getEntityUniqueId();
}
protected function encodePayload() : void{
$this->putEntityUniqueId($this->originalMapId);
$this->putEntityUniqueId($this->newMapId);
}
public function handle(SessionHandler $handler) : bool{
return $handler->handleMapCreateLockedCopy($this);
}
}

View File

@ -0,0 +1,47 @@
<?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/
*
*
*/
declare(strict_types=1);
namespace pocketmine\network\mcpe\protocol;
#include <rules/DataPacket.h>
use pocketmine\network\mcpe\handler\SessionHandler;
class OnScreenTextureAnimationPacket extends DataPacket{
public const NETWORK_ID = ProtocolInfo::ON_SCREEN_TEXTURE_ANIMATION_PACKET;
/** @var int */
public $effectId;
protected function decodePayload() : void{
$this->effectId = $this->getLInt(); //unsigned
}
protected function encodePayload() : void{
$this->putLInt($this->effectId);
}
public function handle(SessionHandler $handler) : bool{
return $handler->handleOnScreenTextureAnimation($this);
}
}

View File

@ -156,6 +156,8 @@ class PacketPool{
static::registerPacket(new LevelSoundEventPacket()); static::registerPacket(new LevelSoundEventPacket());
static::registerPacket(new LecternUpdatePacket()); static::registerPacket(new LecternUpdatePacket());
static::registerPacket(new VideoStreamConnectPacket()); static::registerPacket(new VideoStreamConnectPacket());
static::registerPacket(new MapCreateLockedCopyPacket());
static::registerPacket(new OnScreenTextureAnimationPacket());
} }
/** /**

View File

@ -39,15 +39,15 @@ interface ProtocolInfo{
/** /**
* Actual Minecraft: PE protocol version * Actual Minecraft: PE protocol version
*/ */
public const CURRENT_PROTOCOL = 340; public const CURRENT_PROTOCOL = 354;
/** /**
* Current Minecraft PE version reported by the server. This is usually the earliest currently supported version. * Current Minecraft PE version reported by the server. This is usually the earliest currently supported version.
*/ */
public const MINECRAFT_VERSION = 'v1.10.0'; public const MINECRAFT_VERSION = 'v1.11.0';
/** /**
* Version number sent to clients in ping responses. * Version number sent to clients in ping responses.
*/ */
public const MINECRAFT_VERSION_NETWORK = '1.10.0'; public const MINECRAFT_VERSION_NETWORK = '1.11.0';
public const LOGIN_PACKET = 0x01; public const LOGIN_PACKET = 0x01;
public const PLAY_STATUS_PACKET = 0x02; public const PLAY_STATUS_PACKET = 0x02;
@ -174,5 +174,7 @@ interface ProtocolInfo{
public const LEVEL_SOUND_EVENT_PACKET = 0x7b; public const LEVEL_SOUND_EVENT_PACKET = 0x7b;
public const LECTERN_UPDATE_PACKET = 0x7c; public const LECTERN_UPDATE_PACKET = 0x7c;
public const VIDEO_STREAM_CONNECT_PACKET = 0x7d; public const VIDEO_STREAM_CONNECT_PACKET = 0x7d;
public const MAP_CREATE_LOCKED_COPY_PACKET = 0x7e;
public const ON_SCREEN_TEXTURE_ANIMATION_PACKET = 0x7f;
} }

View File

@ -37,7 +37,7 @@ class StartGamePacket extends DataPacket implements ClientboundPacket{
public const NETWORK_ID = ProtocolInfo::START_GAME_PACKET; public const NETWORK_ID = ProtocolInfo::START_GAME_PACKET;
/** @var string|null */ /** @var string|null */
private static $runtimeIdTable; private static $runtimeIdTableCache;
/** @var int */ /** @var int */
public $entityUniqueId; public $entityUniqueId;
@ -138,6 +138,9 @@ class StartGamePacket extends DataPacket implements ClientboundPacket{
/** @var string */ /** @var string */
public $multiplayerCorrelationId = ""; //TODO: this should be filled with a UUID of some sort public $multiplayerCorrelationId = ""; //TODO: this should be filled with a UUID of some sort
/** @var array|null each entry must have a "name" (string) and "data" (int16) element */
public $runtimeIdTable = null;
protected function decodePayload() : void{ protected function decodePayload() : void{
$this->entityUniqueId = $this->getEntityUniqueId(); $this->entityUniqueId = $this->getEntityUniqueId();
$this->entityRuntimeId = $this->getEntityRuntimeId(); $this->entityRuntimeId = $this->getEntityRuntimeId();
@ -189,10 +192,14 @@ class StartGamePacket extends DataPacket implements ClientboundPacket{
$this->enchantmentSeed = $this->getVarInt(); $this->enchantmentSeed = $this->getVarInt();
$count = $this->getUnsignedVarInt(); $count = $this->getUnsignedVarInt();
$table = [];
for($i = 0; $i < $count; ++$i){ for($i = 0; $i < $count; ++$i){
$this->getString(); $id = $this->getString();
$this->getLShort(); $data = $this->getLShort();
$table[$i] = ["name" => $id, "data" => $data];
} }
$this->runtimeIdTable = $table;
$this->multiplayerCorrelationId = $this->getString(); $this->multiplayerCorrelationId = $this->getString();
} }
@ -247,20 +254,27 @@ class StartGamePacket extends DataPacket implements ClientboundPacket{
$this->putVarInt($this->enchantmentSeed); $this->putVarInt($this->enchantmentSeed);
if(self::$runtimeIdTable === null){ if($this->runtimeIdTable === null){
if(self::$runtimeIdTableCache === null){
//this is a really nasty hack, but it'll do for now //this is a really nasty hack, but it'll do for now
self::$runtimeIdTableCache = self::serializeBlockTable(RuntimeBlockMapping::getBedrockKnownStates());
}
$this->put(self::$runtimeIdTableCache);
}else{
$this->put(self::serializeBlockTable($this->runtimeIdTable));
}
$this->putString($this->multiplayerCorrelationId);
}
private static function serializeBlockTable(array $table) : string{
$stream = new NetworkBinaryStream(); $stream = new NetworkBinaryStream();
$data = RuntimeBlockMapping::getBedrockKnownStates(); $stream->putUnsignedVarInt(count($table));
$stream->putUnsignedVarInt(count($data)); foreach($table as $v){
foreach($data as $v){
$stream->putString($v["name"]); $stream->putString($v["name"]);
$stream->putLShort($v["data"]); $stream->putLShort($v["data"]);
} }
self::$runtimeIdTable = $stream->getBuffer(); return $stream->getBuffer();
}
$this->put(self::$runtimeIdTable);
$this->putString($this->multiplayerCorrelationId);
} }
public function handle(SessionHandler $handler) : bool{ public function handle(SessionHandler $handler) : bool{

View File

@ -40,45 +40,45 @@ class UpdateTradePacket extends DataPacket implements ClientboundPacket{
/** @var int */ /** @var int */
public $windowType = WindowTypes::TRADING; //Mojang hardcoded this -_- public $windowType = WindowTypes::TRADING; //Mojang hardcoded this -_-
/** @var int */ /** @var int */
public $varint1; public $thisIsAlwaysZero = 0; //hardcoded to 0
/** @var int */ /** @var int */
public $varint2; public $tradeTier;
/** @var int */
public $varint3;
/** @var bool */
public $isWilling;
/** @var int */ /** @var int */
public $traderEid; public $traderEid;
/** @var int */ /** @var int */
public $playerEid; public $playerEid;
/** @var string */ /** @var string */
public $displayName; public $displayName;
/** @var bool */
public $isWilling;
/** @var bool */
public $isV2Trading;
/** @var string */ /** @var string */
public $offers; public $offers;
protected function decodePayload() : void{ protected function decodePayload() : void{
$this->windowId = $this->getByte(); $this->windowId = $this->getByte();
$this->windowType = $this->getByte(); $this->windowType = $this->getByte();
$this->varint1 = $this->getVarInt(); $this->thisIsAlwaysZero = $this->getVarInt();
$this->varint2 = $this->getVarInt(); $this->tradeTier = $this->getVarInt();
$this->varint3 = $this->getVarInt();
$this->isWilling = $this->getBool();
$this->traderEid = $this->getEntityUniqueId(); $this->traderEid = $this->getEntityUniqueId();
$this->playerEid = $this->getEntityUniqueId(); $this->playerEid = $this->getEntityUniqueId();
$this->displayName = $this->getString(); $this->displayName = $this->getString();
$this->isWilling = $this->getBool();
$this->isV2Trading = $this->getBool();
$this->offers = $this->getRemaining(); $this->offers = $this->getRemaining();
} }
protected function encodePayload() : void{ protected function encodePayload() : void{
$this->putByte($this->windowId); $this->putByte($this->windowId);
$this->putByte($this->windowType); $this->putByte($this->windowType);
$this->putVarInt($this->varint1); $this->putVarInt($this->thisIsAlwaysZero);
$this->putVarInt($this->varint2); $this->putVarInt($this->tradeTier);
$this->putVarInt($this->varint3);
$this->putBool($this->isWilling);
$this->putEntityUniqueId($this->traderEid); $this->putEntityUniqueId($this->traderEid);
$this->putEntityUniqueId($this->playerEid); $this->putEntityUniqueId($this->playerEid);
$this->putString($this->displayName); $this->putString($this->displayName);
$this->putBool($this->isWilling);
$this->putBool($this->isV2Trading);
$this->put($this->offers); $this->put($this->offers);
} }

View File

@ -27,6 +27,8 @@ namespace pocketmine\network\mcpe\protocol\types;
interface WindowTypes{ interface WindowTypes{
public const NONE = -9;
public const INVENTORY = -1; public const INVENTORY = -1;
public const CONTAINER = 0; public const CONTAINER = 0;
public const WORKBENCH = 1; public const WORKBENCH = 1;
@ -47,4 +49,13 @@ interface WindowTypes{
public const COMMAND_BLOCK = 16; public const COMMAND_BLOCK = 16;
public const JUKEBOX = 17; public const JUKEBOX = 17;
public const COMPOUND_CREATOR = 20;
public const ELEMENT_CONSTRUCTOR = 21;
public const MATERIAL_REDUCER = 22;
public const LAB_TABLE = 23;
public const BLAST_FURNACE = 27;
public const SMOKER = 28;
public const STONECUTTER = 29;
} }