mirror of
https://github.com/pmmp/PocketMine-MP.git
synced 2025-04-21 08:17:34 +00:00
Merge branch 'minor-next' of github.com:pmmp/PocketMine-MP into feat/async-events
This commit is contained in:
commit
86fb041a65
1
.github/CODEOWNERS
vendored
Normal file
1
.github/CODEOWNERS
vendored
Normal file
@ -0,0 +1 @@
|
||||
* @pmmp/server-developers
|
16
.github/dependabot.yml
vendored
16
.github/dependabot.yml
vendored
@ -12,6 +12,22 @@ updates:
|
||||
update-types:
|
||||
- "version-update:semver-major"
|
||||
- "version-update:semver-minor"
|
||||
groups:
|
||||
production-patch-updates:
|
||||
dependency-type: production
|
||||
patterns:
|
||||
- "*"
|
||||
update-types:
|
||||
- "patch"
|
||||
development-patch-updates:
|
||||
dependency-type: development
|
||||
patterns:
|
||||
- "*"
|
||||
update-types:
|
||||
- "patch"
|
||||
phpstan:
|
||||
patterns:
|
||||
- "phpstan/*"
|
||||
|
||||
- package-ecosystem: gitsubmodule
|
||||
directory: "/"
|
||||
|
8
.github/workflows/build-docker-image.yml
vendored
8
.github/workflows/build-docker-image.yml
vendored
@ -53,7 +53,7 @@ jobs:
|
||||
run: echo NAME=$(echo "${GITHUB_REPOSITORY,,}") >> $GITHUB_OUTPUT
|
||||
|
||||
- name: Build image for tag
|
||||
uses: docker/build-push-action@v5.3.0
|
||||
uses: docker/build-push-action@v6.9.0
|
||||
with:
|
||||
push: true
|
||||
context: ./pocketmine-mp
|
||||
@ -66,7 +66,7 @@ jobs:
|
||||
|
||||
- name: Build image for major tag
|
||||
if: steps.channel.outputs.CHANNEL == 'stable'
|
||||
uses: docker/build-push-action@v5.3.0
|
||||
uses: docker/build-push-action@v6.9.0
|
||||
with:
|
||||
push: true
|
||||
context: ./pocketmine-mp
|
||||
@ -79,7 +79,7 @@ jobs:
|
||||
|
||||
- name: Build image for minor tag
|
||||
if: steps.channel.outputs.CHANNEL == 'stable'
|
||||
uses: docker/build-push-action@v5.3.0
|
||||
uses: docker/build-push-action@v6.9.0
|
||||
with:
|
||||
push: true
|
||||
context: ./pocketmine-mp
|
||||
@ -92,7 +92,7 @@ jobs:
|
||||
|
||||
- name: Build image for latest tag
|
||||
if: steps.channel.outputs.CHANNEL == 'stable'
|
||||
uses: docker/build-push-action@v5.3.0
|
||||
uses: docker/build-push-action@v6.9.0
|
||||
with:
|
||||
push: true
|
||||
context: ./pocketmine-mp
|
||||
|
2
.github/workflows/discord-release-notify.yml
vendored
2
.github/workflows/discord-release-notify.yml
vendored
@ -13,7 +13,7 @@ jobs:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Setup PHP and tools
|
||||
uses: shivammathur/setup-php@2.30.4
|
||||
uses: shivammathur/setup-php@2.31.1
|
||||
with:
|
||||
php-version: 8.2
|
||||
|
||||
|
65
.github/workflows/draft-release-from-pr.yml
vendored
Normal file
65
.github/workflows/draft-release-from-pr.yml
vendored
Normal file
@ -0,0 +1,65 @@
|
||||
name: Draft release from PR
|
||||
|
||||
on:
|
||||
#presume that pull_request_target is safe at this point, since the PR was approved and merged
|
||||
#we need write access to prepare the release & create comments
|
||||
pull_request_target:
|
||||
types:
|
||||
- closed
|
||||
branches:
|
||||
- stable
|
||||
- minor-next
|
||||
- major-next
|
||||
- "legacy/*"
|
||||
paths:
|
||||
- "src/VersionInfo.php"
|
||||
|
||||
jobs:
|
||||
check:
|
||||
name: Check release
|
||||
uses: ./.github/workflows/draft-release-pr-check.yml
|
||||
|
||||
draft:
|
||||
name: Create GitHub draft release
|
||||
needs: [check]
|
||||
if: needs.check.outputs.valid == 'true'
|
||||
|
||||
uses: ./.github/workflows/draft-release.yml
|
||||
|
||||
post-draft-url-comment:
|
||||
name: Post draft release URL as comment
|
||||
needs: [draft]
|
||||
|
||||
runs-on: ubuntu-20.04
|
||||
|
||||
steps:
|
||||
- name: Post draft release URL on PR
|
||||
uses: thollander/actions-comment-pull-request@v3
|
||||
with:
|
||||
message: "[Draft release ${{ needs.draft.outputs.version }}](${{ needs.draft.outputs.draft-url }}) has been created for commit ${{ github.sha }}. Please review and publish it."
|
||||
|
||||
trigger-post-release-workflow:
|
||||
name: Trigger post-release RestrictedActions workflow
|
||||
# Not sure if needs is actually needed here
|
||||
needs: [check]
|
||||
if: needs.check.outputs.valid == 'true'
|
||||
|
||||
runs-on: ubuntu-20.04
|
||||
|
||||
steps:
|
||||
- name: Generate access token
|
||||
id: generate-token
|
||||
uses: actions/create-github-app-token@v1
|
||||
with:
|
||||
app-id: ${{ vars.RESTRICTED_ACTIONS_DISPATCH_ID }}
|
||||
private-key: ${{ secrets.RESTRICTED_ACTIONS_DISPATCH_KEY }}
|
||||
owner: ${{ github.repository_owner }}
|
||||
repositories: RestrictedActions
|
||||
|
||||
- name: Dispatch post-release restricted action
|
||||
uses: peter-evans/repository-dispatch@v3
|
||||
with:
|
||||
token: ${{ steps.generate-token.outputs.token }}
|
||||
repository: ${{ github.repository_owner }}/RestrictedActions
|
||||
event-type: pocketmine_mp_post_release
|
||||
client-payload: '{"branch": "${{ github.ref }}"}'
|
13
.github/workflows/draft-release-from-tag.yml
vendored
Normal file
13
.github/workflows/draft-release-from-tag.yml
vendored
Normal file
@ -0,0 +1,13 @@
|
||||
#Allows creating a release by pushing a tag
|
||||
#This might be useful for retroactive releases
|
||||
name: Draft release from git tag
|
||||
|
||||
on:
|
||||
push:
|
||||
tags: "*"
|
||||
|
||||
jobs:
|
||||
draft:
|
||||
name: Create GitHub draft release
|
||||
if: "startsWith(github.event.head_commit.message, 'Release ')"
|
||||
uses: ./.github/workflows/draft-release.yml
|
111
.github/workflows/draft-release-pr-check.yml
vendored
Normal file
111
.github/workflows/draft-release-pr-check.yml
vendored
Normal file
@ -0,0 +1,111 @@
|
||||
name: Release PR checks
|
||||
|
||||
on:
|
||||
#do checks on every PR update
|
||||
pull_request:
|
||||
branches:
|
||||
- stable
|
||||
- minor-next
|
||||
- major-next
|
||||
- "legacy/*"
|
||||
paths:
|
||||
- "src/VersionInfo.php"
|
||||
|
||||
#allow this workflow to be invoked on PR merge, prior to creating the release
|
||||
workflow_call:
|
||||
outputs:
|
||||
valid:
|
||||
description: Whether this commit is valid for release
|
||||
value: ${{ jobs.check-intent.outputs.valid && jobs.check-validity.result == 'success' }}
|
||||
|
||||
permissions:
|
||||
contents: read #for user access check
|
||||
|
||||
jobs:
|
||||
check-intent:
|
||||
name: Check release trigger
|
||||
runs-on: ubuntu-20.04
|
||||
|
||||
outputs:
|
||||
valid: ${{ steps.validate.outputs.DEV_BUILD == 'false' }}
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Check IS_DEVELOPMENT_BUILD flag
|
||||
id: validate
|
||||
run: |
|
||||
echo DEV_BUILD=$(sed -n "s/^\s*public const IS_DEVELOPMENT_BUILD = \(true\|false\);$/\1/p" src/VersionInfo.php) >> $GITHUB_OUTPUT
|
||||
|
||||
check-validity:
|
||||
name: Validate release info
|
||||
needs: [check-intent]
|
||||
#don't do these checks if this isn't a release - we don't want to generate unnecessary failed statuses
|
||||
if: needs.check-intent.outputs.valid == 'true'
|
||||
|
||||
runs-on: ubuntu-20.04
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Setup PHP
|
||||
uses: shivammathur/setup-php@2.31.1
|
||||
with:
|
||||
php-version: 8.2
|
||||
|
||||
- name: Restore Composer package cache
|
||||
uses: actions/cache@v4
|
||||
with:
|
||||
path: |
|
||||
~/.cache/composer/files
|
||||
~/.cache/composer/vcs
|
||||
key: "composer-v2-cache-${{ hashFiles('./composer.lock') }}"
|
||||
restore-keys: |
|
||||
composer-v2-cache-
|
||||
|
||||
- name: Install Composer dependencies
|
||||
run: composer install --no-dev --prefer-dist --no-interaction --ignore-platform-reqs
|
||||
|
||||
- name: Check author permissions
|
||||
id: check-permission
|
||||
uses: actions-cool/check-user-permission@v2
|
||||
with:
|
||||
token: ${{ secrets.GITHUB_TOKEN }}
|
||||
require: write
|
||||
username: ${{ github.event.pull_request.user.login }}
|
||||
#technically this would be fine for dependabot but generally bots don't count as team members
|
||||
check-bot: true
|
||||
|
||||
- name: Abort if user permissions are insufficient
|
||||
#user doesn't have permission or is a bot
|
||||
if: steps.check-permission.outputs.require-result != 'true' || steps.check-permission.outputs.check-result != 'false'
|
||||
run: |
|
||||
echo "::error::This user is not authorized to trigger releases"
|
||||
exit 1
|
||||
|
||||
- name: Check changelog file is present
|
||||
id: file-presence
|
||||
run: |
|
||||
CHANGELOG_FILE="changelogs/$(php build/dump-version-info.php changelog_file_name)"
|
||||
if [ ! -f "${{ github.workspace }}/$CHANGELOG_FILE" ]; then
|
||||
echo "::error::$CHANGELOG_FILE does not exist"
|
||||
exit 1
|
||||
fi
|
||||
echo FILE="$CHANGELOG_FILE" >> $GITHUB_OUTPUT
|
||||
|
||||
- name: Check header is present in changelog file
|
||||
run: |
|
||||
FILE="${{ steps.file-presence.outputs.FILE }}"
|
||||
VERSION="$(php build/dump-version-info.php base_version)"
|
||||
if ! grep -Fqx "# $VERSION" "${{ github.workspace }}/$FILE"; then
|
||||
echo "::error::Header for $VERSION not found in $FILE"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
- name: Check version is valid for the selected channel
|
||||
run: |
|
||||
CHANNEL="$(php build/dump-version-info.php channel)"
|
||||
if [ "$(php build/dump-version-info.php suffix_valid)" != "true" ]; then
|
||||
echo "::error::Version $(php build/dump-version-info.php base_version) is not allowed on the $CHANNEL channel"
|
||||
exit 1
|
||||
fi
|
33
.github/workflows/draft-release.yml
vendored
33
.github/workflows/draft-release.yml
vendored
@ -1,26 +1,36 @@
|
||||
name: Draft release
|
||||
|
||||
on:
|
||||
push:
|
||||
tags: "*"
|
||||
workflow_call:
|
||||
outputs:
|
||||
draft-url:
|
||||
description: 'The URL of the draft release'
|
||||
value: ${{ jobs.draft.outputs.draft-url }}
|
||||
version:
|
||||
description: 'PocketMine-MP version'
|
||||
value: ${{ jobs.draft.outputs.version }}
|
||||
|
||||
jobs:
|
||||
draft:
|
||||
name: Create GitHub draft release
|
||||
if: "startsWith(github.event.head_commit.message, 'Release ')"
|
||||
|
||||
runs-on: ubuntu-20.04
|
||||
strategy:
|
||||
fail-fast: false
|
||||
matrix:
|
||||
php-version: [8.2]
|
||||
|
||||
outputs:
|
||||
draft-url: ${{ steps.create-draft.outputs.html_url }}
|
||||
version: ${{ steps.get-pm-version.outputs.PM_VERSION }}
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
with:
|
||||
submodules: true
|
||||
|
||||
- name: Setup PHP
|
||||
uses: shivammathur/setup-php@2.30.4
|
||||
uses: shivammathur/setup-php@2.31.1
|
||||
with:
|
||||
php-version: ${{ matrix.php-version }}
|
||||
|
||||
@ -53,12 +63,11 @@ jobs:
|
||||
- name: Get PocketMine-MP release version
|
||||
id: get-pm-version
|
||||
run: |
|
||||
echo PM_VERSION=$(php -r 'require "vendor/autoload.php"; echo \pocketmine\VersionInfo::BASE_VERSION;') >> $GITHUB_OUTPUT
|
||||
echo MCPE_VERSION=$(php -r 'require "vendor/autoload.php"; echo \pocketmine\network\mcpe\protocol\ProtocolInfo::MINECRAFT_VERSION_NETWORK;') >> $GITHUB_OUTPUT
|
||||
echo PM_VERSION_SHORT=$(php -r 'require "vendor/autoload.php"; $v = explode(".", \pocketmine\VersionInfo::BASE_VERSION); array_pop($v); echo implode(".", $v);') >> $GITHUB_OUTPUT
|
||||
echo PM_VERSION_MD=$(php -r 'require "vendor/autoload.php"; echo str_replace(".", "", \pocketmine\VersionInfo::BASE_VERSION);') >> $GITHUB_OUTPUT
|
||||
echo CHANGELOG_SUFFIX=$(php -r 'require "vendor/autoload.php"; echo \pocketmine\VersionInfo::BUILD_CHANNEL === "stable" ? "" : "-" . \pocketmine\VersionInfo::BUILD_CHANNEL;') >> $GITHUB_OUTPUT
|
||||
echo PRERELEASE=$(php -r 'require "vendor/autoload.php"; echo \pocketmine\VersionInfo::BUILD_CHANNEL === "stable" ? "false" : "true";') >> $GITHUB_OUTPUT
|
||||
echo PM_VERSION=$(php build/dump-version-info.php base_version) >> $GITHUB_OUTPUT
|
||||
echo MCPE_VERSION=$(php build/dump-version-info.php mcpe_version) >> $GITHUB_OUTPUT
|
||||
echo CHANGELOG_FILE_NAME=$(php build/dump-version-info.php changelog_file_name) >> $GITHUB_OUTPUT
|
||||
echo CHANGELOG_MD_HEADER=$(php build/dump-version-info.php changelog_md_header) >> $GITHUB_OUTPUT
|
||||
echo PRERELEASE=$(php build/dump-version-info.php prerelease) >> $GITHUB_OUTPUT
|
||||
|
||||
- name: Generate PHP binary download URL
|
||||
id: php-binary-url
|
||||
@ -91,6 +100,7 @@ jobs:
|
||||
|
||||
- name: Create draft release
|
||||
uses: ncipollo/release-action@v1.14.0
|
||||
id: create-draft
|
||||
with:
|
||||
artifacts: ${{ github.workspace }}/PocketMine-MP.phar,${{ github.workspace }}/start.*,${{ github.workspace }}/build_info.json,${{ github.workspace }}/core-permissions.rst
|
||||
commit: ${{ github.sha }}
|
||||
@ -99,9 +109,10 @@ jobs:
|
||||
name: PocketMine-MP ${{ steps.get-pm-version.outputs.PM_VERSION }}
|
||||
tag: ${{ steps.get-pm-version.outputs.PM_VERSION }}
|
||||
token: ${{ secrets.GITHUB_TOKEN }}
|
||||
skipIfReleaseExists: true #for release PRs, tags will be created on release publish and trigger the tag release workflow - don't create a second draft
|
||||
body: |
|
||||
**For Minecraft: Bedrock Edition ${{ steps.get-pm-version.outputs.MCPE_VERSION }}**
|
||||
|
||||
Please see the [changelogs](${{ github.server_url }}/${{ github.repository }}/blob/${{ steps.get-pm-version.outputs.PM_VERSION }}/changelogs/${{ steps.get-pm-version.outputs.PM_VERSION_SHORT }}${{ steps.get-pm-version.outputs.CHANGELOG_SUFFIX }}.md#${{ steps.get-pm-version.outputs.PM_VERSION_MD }}) for details.
|
||||
Please see the [changelogs](${{ github.server_url }}/${{ github.repository }}/blob/${{ steps.get-pm-version.outputs.PM_VERSION }}/changelogs/${{ steps.get-pm-version.outputs.CHANGELOG_FILE_NAME }}#${{ steps.get-pm-version.outputs.CHANGELOG_MD_HEADER }}) for details.
|
||||
|
||||
:information_source: Download the recommended PHP binary [here](${{ steps.php-binary-url.outputs.PHP_BINARY_URL }}).
|
||||
|
14
.github/workflows/main.yml
vendored
14
.github/workflows/main.yml
vendored
@ -28,7 +28,7 @@ jobs:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Setup PHP and tools
|
||||
uses: shivammathur/setup-php@2.30.4
|
||||
uses: shivammathur/setup-php@2.31.1
|
||||
with:
|
||||
php-version: 8.2
|
||||
tools: php-cs-fixer:3.49
|
||||
@ -37,3 +37,15 @@ jobs:
|
||||
|
||||
- name: Run PHP-CS-Fixer
|
||||
run: php-cs-fixer fix --dry-run --diff --ansi
|
||||
|
||||
shellcheck:
|
||||
name: ShellCheck
|
||||
runs-on: ubuntu-20.04
|
||||
strategy:
|
||||
fail-fast: false
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Run ShellCheck
|
||||
uses: ludeeus/action-shellcheck@2.0.0
|
||||
|
42
.github/workflows/team-pr-auto-approve.yml
vendored
Normal file
42
.github/workflows/team-pr-auto-approve.yml
vendored
Normal file
@ -0,0 +1,42 @@
|
||||
#Due to GitHub awkwardness, it's not easy to reduce the review requirement for collaborators.
|
||||
#Our policy is that 2 collaborators should be aware of every change.
|
||||
#For outside PRs, this means 2 collaborator reviews.
|
||||
#For PRs made by collaborators, this means 1 reviewer + the author.
|
||||
#We trust that collaborators don't need as much oversight.
|
||||
name: Auto approve collaborator PRs
|
||||
|
||||
on:
|
||||
pull_request_target:
|
||||
types:
|
||||
- opened
|
||||
- synchronize
|
||||
- reopened
|
||||
- ready_for_review
|
||||
|
||||
permissions:
|
||||
pull-requests: write
|
||||
|
||||
jobs:
|
||||
approve:
|
||||
name: Auto approve
|
||||
runs-on: ubuntu-latest
|
||||
|
||||
steps:
|
||||
- name: Check if PR author has write access
|
||||
id: check-permission
|
||||
uses: actions-cool/check-user-permission@v2
|
||||
with:
|
||||
token: ${{ secrets.GITHUB_TOKEN }}
|
||||
require: write
|
||||
username: ${{ github.event.pull_request.user.login }}
|
||||
#technically this would be fine for dependabot but generally bots don't count as team members
|
||||
check-bot: true
|
||||
|
||||
#TODO: Some way to avoid unnecessary repeated reviews would be nice here
|
||||
|
||||
- name: Approve PR if authorized
|
||||
if: steps.check-permission.outputs.require-result == 'true' && steps.check-permission.outputs.check-result == 'false'
|
||||
uses: juliangruber/approve-pull-request-action@v2
|
||||
with:
|
||||
github-token: ${{ secrets.GITHUB_TOKEN }}
|
||||
number: ${{ github.event.pull_request.number }}
|
86
build/dump-version-info.php
Normal file
86
build/dump-version-info.php
Normal file
@ -0,0 +1,86 @@
|
||||
<?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);
|
||||
|
||||
use pocketmine\network\mcpe\protocol\ProtocolInfo;
|
||||
use pocketmine\VersionInfo;
|
||||
|
||||
require dirname(__DIR__) . '/vendor/autoload.php';
|
||||
|
||||
/*
|
||||
* Dumps version info in a machine-readable format for use in GitHub Actions workflows
|
||||
*/
|
||||
|
||||
/**
|
||||
* @var string[]|\Closure[] $options
|
||||
* @phpstan-var array<string, string|\Closure() : string> $options
|
||||
*/
|
||||
$options = [
|
||||
"base_version" => VersionInfo::BASE_VERSION,
|
||||
"mcpe_version" => ProtocolInfo::MINECRAFT_VERSION_NETWORK,
|
||||
"is_dev" => VersionInfo::IS_DEVELOPMENT_BUILD,
|
||||
"changelog_file_name" => function() : string{
|
||||
$version = VersionInfo::VERSION();
|
||||
$result = $version->getMajor() . "." . $version->getMinor();
|
||||
$suffix = $version->getSuffix();
|
||||
if($suffix !== ""){
|
||||
if(preg_match('/^([A-Za-z]+)(\d+)$/', $suffix, $matches) !== 1){
|
||||
fwrite(STDERR, "error: invalid current version suffix \"$suffix\"; aborting" . PHP_EOL);
|
||||
exit(1);
|
||||
}
|
||||
$baseSuffix = $matches[1];
|
||||
$result .= "-" . strtolower($baseSuffix);
|
||||
}
|
||||
return $result . ".md";
|
||||
},
|
||||
"changelog_md_header" => fn() : string => str_replace(".", "", VersionInfo::BASE_VERSION),
|
||||
"prerelease" => fn() : bool => VersionInfo::VERSION()->getSuffix() !== "",
|
||||
"channel" => VersionInfo::BUILD_CHANNEL,
|
||||
"suffix_valid" => function() : bool{
|
||||
//TODO: maybe this should be put into its own script?
|
||||
$suffix = VersionInfo::VERSION()->getSuffix();
|
||||
if(VersionInfo::BUILD_CHANNEL === "stable"){
|
||||
//stable builds may not have suffixes
|
||||
return $suffix === "";
|
||||
}
|
||||
if(VersionInfo::BUILD_CHANNEL === "alpha" || VersionInfo::BUILD_CHANNEL === "beta"){
|
||||
$upperChannel = strtoupper(VersionInfo::BUILD_CHANNEL);
|
||||
$upperSuffix = strtoupper($suffix);
|
||||
return str_starts_with($upperSuffix, $upperChannel) && is_numeric(substr($upperSuffix, strlen($upperChannel)));
|
||||
}
|
||||
return true;
|
||||
}
|
||||
];
|
||||
if(count($argv) !== 2 || !isset($options[$argv[1]])){
|
||||
fwrite(STDERR, "Please provide an option (one of: " . implode(", ", array_keys($options)) . PHP_EOL);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
$result = $options[$argv[1]];
|
||||
if($result instanceof Closure){
|
||||
$result = $result();
|
||||
}
|
||||
if(is_bool($result)){
|
||||
echo $result ? "true" : "false";
|
||||
}else{
|
||||
echo $result;
|
||||
}
|
@ -86,7 +86,8 @@ function systemWrapper(string $command, string $errorMessage) : void{
|
||||
|
||||
function main() : void{
|
||||
$filteredOpts = [];
|
||||
foreach(Utils::stringifyKeys(getopt("", ["current:", "next:", "channel:", "help"])) as $optName => $optValue){
|
||||
$postCommitOnly = false;
|
||||
foreach(Utils::stringifyKeys(getopt("", ["current:", "next:", "channel:", "help", "post"])) as $optName => $optValue){
|
||||
if($optName === "help"){
|
||||
fwrite(STDOUT, "Options:\n");
|
||||
|
||||
@ -96,6 +97,10 @@ function main() : void{
|
||||
}
|
||||
exit(0);
|
||||
}
|
||||
if($optName === "post"){
|
||||
$postCommitOnly = true;
|
||||
continue;
|
||||
}
|
||||
if(!is_string($optValue)){
|
||||
fwrite(STDERR, "--$optName expects exactly 1 value\n");
|
||||
exit(1);
|
||||
@ -141,20 +146,25 @@ function main() : void{
|
||||
$channel ??= "stable";
|
||||
}
|
||||
|
||||
echo "About to tag version $currentVer. Next version will be $nextVer.\n";
|
||||
echo "$currentVer will be published on release channel \"$channel\".\n";
|
||||
echo "please add appropriate notes to the changelog and press enter...";
|
||||
fgets(STDIN);
|
||||
systemWrapper('git add "' . dirname(__DIR__) . '/changelogs"', "failed to stage changelog changes");
|
||||
system('git diff --cached --quiet "' . dirname(__DIR__) . '/changelogs"', $result);
|
||||
if($result === 0){
|
||||
echo "error: no changelog changes detected; aborting\n";
|
||||
exit(1);
|
||||
}
|
||||
$versionInfoPath = dirname(__DIR__) . '/src/VersionInfo.php';
|
||||
replaceVersion($versionInfoPath, $currentVer->getBaseVersion(), false, $channel);
|
||||
systemWrapper('git commit -m "Release ' . $currentVer->getBaseVersion() . '" --include "' . $versionInfoPath . '"', "failed to create release commit");
|
||||
systemWrapper('git tag ' . $currentVer->getBaseVersion(), "failed to create release tag");
|
||||
|
||||
if($postCommitOnly){
|
||||
echo "Skipping release commit & tag. Bumping to next version $nextVer directly.\n";
|
||||
}else{
|
||||
echo "About to tag version $currentVer. Next version will be $nextVer.\n";
|
||||
echo "$currentVer will be published on release channel \"$channel\".\n";
|
||||
echo "please add appropriate notes to the changelog and press enter...";
|
||||
fgets(STDIN);
|
||||
systemWrapper('git add "' . dirname(__DIR__) . '/changelogs"', "failed to stage changelog changes");
|
||||
system('git diff --cached --quiet "' . dirname(__DIR__) . '/changelogs"', $result);
|
||||
if($result === 0){
|
||||
echo "error: no changelog changes detected; aborting\n";
|
||||
exit(1);
|
||||
}
|
||||
replaceVersion($versionInfoPath, $currentVer->getBaseVersion(), false, $channel);
|
||||
systemWrapper('git commit -m "Release ' . $currentVer->getBaseVersion() . '" --include "' . $versionInfoPath . '"', "failed to create release commit");
|
||||
systemWrapper('git tag ' . $currentVer->getBaseVersion(), "failed to create release tag");
|
||||
}
|
||||
|
||||
replaceVersion($versionInfoPath, $nextVer->getBaseVersion(), true, $channel);
|
||||
systemWrapper('git add "' . $versionInfoPath . '"', "failed to stage changes for post-release commit");
|
||||
|
@ -1 +1 @@
|
||||
Subproject commit 084822aa9e381ca05591e902a2613fe971dff3fd
|
||||
Subproject commit a51259d7a6ea649d64f409fc0276baa59cf4f19a
|
38
changelogs/5.17.md
Normal file
38
changelogs/5.17.md
Normal file
@ -0,0 +1,38 @@
|
||||
# 5.17.0
|
||||
Released 10th July 2024.
|
||||
|
||||
**For Minecraft: Bedrock Edition 1.21.2**
|
||||
|
||||
This is a support release for Minecraft: Bedrock Edition 1.21.2.
|
||||
|
||||
**Plugin compatibility:** Plugins for previous 5.x versions will run unchanged on this release, unless they use internal APIs, reflection, or packages like the `pocketmine\network\mcpe` or `pocketmine\data` namespace.
|
||||
Do not update plugin minimum API versions unless you need new features added in this release.
|
||||
|
||||
**WARNING: If your plugin uses the `pocketmine\network\mcpe` namespace, you're not shielded by API change constraints.**
|
||||
Consider using the `mcpe-protocol` directive in `plugin.yml` as a constraint if you're using packets directly.
|
||||
|
||||
## General
|
||||
- Added support for Minecraft: Bedrock Edition 1.21.2.
|
||||
- Removed support for earlier versions.
|
||||
|
||||
## API
|
||||
### `pocketmine\player`
|
||||
- The following methods have been added:
|
||||
- `public function closeAllForms() : void` - closes the current viewing form and forms in queue.
|
||||
|
||||
## Fixes
|
||||
- Bowl can now be used as fuel.
|
||||
- Bells always drops themselves even when using an incompatible tool.
|
||||
|
||||
# 5.17.1
|
||||
Released 13th August 2024.
|
||||
|
||||
## Documentation
|
||||
- Added a note about `BlockStateData::CURRENT_VERSION`.
|
||||
|
||||
## Fixes
|
||||
- Fixed anvil placement rotation to match vanilla.
|
||||
- Fixed outdated `BedrockWorldData` version, this was preventing use newer worlds.
|
||||
|
||||
## Internals
|
||||
- Dependabot: PHPStan and patch updates are now grouped into a single PR.
|
30
changelogs/5.18.md
Normal file
30
changelogs/5.18.md
Normal file
@ -0,0 +1,30 @@
|
||||
# 5.18.0
|
||||
Released 16th August 2024.
|
||||
|
||||
**For Minecraft: Bedrock Edition 1.21.20**
|
||||
|
||||
This is a support release for Minecraft: Bedrock Edition 1.21.20.
|
||||
|
||||
**Plugin compatibility:** Plugins for previous 5.x versions will run unchanged on this release, unless they use internal APIs, reflection, or packages like the `pocketmine\network\mcpe` or `pocketmine\data` namespace.
|
||||
Do not update plugin minimum API versions unless you need new features added in this release.
|
||||
|
||||
**WARNING: If your plugin uses the `pocketmine\network\mcpe` namespace, you're not shielded by API change constraints.**
|
||||
Consider using the `mcpe-protocol` directive in `plugin.yml` as a constraint if you're using packets directly.
|
||||
|
||||
## General
|
||||
- Added support for Minecraft: Bedrock Edition 1.21.20.
|
||||
- Removed support for earlier versions.
|
||||
|
||||
## Fixes
|
||||
- Use `VISIBLE_MOB_EFFECTS` actor metadata property to send effect bubbles, this fixes effect bubbles not showing
|
||||
|
||||
# 5.18.1
|
||||
Released 3rd September 2024.
|
||||
|
||||
## Fixes
|
||||
- Fixed shift-crafting.
|
||||
- Blue Ice block no longer emits light & it's now dropped when mined with a tool with silk touch enchantment.
|
||||
|
||||
## Internals
|
||||
- Pull Requests from team members now get an approval automatically. This means that if a team member makes a PR, only one other approval should be needed.
|
||||
- Added [ShellCheck](https://github.com/koalaman/shellcheck) to the CI tests.
|
16
changelogs/5.19.md
Normal file
16
changelogs/5.19.md
Normal file
@ -0,0 +1,16 @@
|
||||
# 5.19.0
|
||||
Released 21st September 2024.
|
||||
|
||||
**For Minecraft: Bedrock Edition 1.21.30**
|
||||
|
||||
This is a support release for Minecraft: Bedrock Edition 1.21.30.
|
||||
|
||||
**Plugin compatibility:** Plugins for previous 5.x versions will run unchanged on this release, unless they use internal APIs, reflection, or packages like the `pocketmine\network\mcpe` or `pocketmine\data` namespace.
|
||||
Do not update plugin minimum API versions unless you need new features added in this release.
|
||||
|
||||
**WARNING: If your plugin uses the `pocketmine\network\mcpe` namespace, you're not shielded by API change constraints.**
|
||||
Consider using the `mcpe-protocol` directive in `plugin.yml` as a constraint if you're using packets directly.
|
||||
|
||||
## General
|
||||
- Added support for Minecraft: Bedrock Edition 1.21.30.
|
||||
- Removed support for earlier versions.
|
25
changelogs/5.20.md
Normal file
25
changelogs/5.20.md
Normal file
@ -0,0 +1,25 @@
|
||||
# 5.20.0
|
||||
Released 26th October 2024.
|
||||
|
||||
**For Minecraft: Bedrock Edition 1.21.40**
|
||||
|
||||
This is a support release for Minecraft: Bedrock Edition 1.21.40.
|
||||
|
||||
**Plugin compatibility:** Plugins for previous 5.x versions will run unchanged on this release, unless they use internal APIs, reflection, or packages like the `pocketmine\network\mcpe` or `pocketmine\data` namespace.
|
||||
Do not update plugin minimum API versions unless you need new features added in this release.
|
||||
|
||||
**WARNING: If your plugin uses the `pocketmine\network\mcpe` namespace, you're not shielded by API change constraints.**
|
||||
Consider using the `mcpe-protocol` directive in `plugin.yml` as a constraint if you're using packets directly.
|
||||
|
||||
## General
|
||||
- Added support for Minecraft: Bedrock Edition 1.21.40.
|
||||
- Removed support for earlier versions.
|
||||
|
||||
## Fixes
|
||||
- Fixed a bug in `tools/generate-blockstate-upgrade-schema.php` that caused it to fail on 1.21.40 with the new mushroom block changes.
|
||||
|
||||
# 5.20.1
|
||||
Released 31st October 2024.
|
||||
|
||||
## Fixes
|
||||
- Workaround old mob heads in world saves not being upgraded correctly and causing crashes.
|
112
changelogs/5.21.md
Normal file
112
changelogs/5.21.md
Normal file
@ -0,0 +1,112 @@
|
||||
# 5.21.0
|
||||
Released 3rd November 2024.
|
||||
|
||||
This is a minor feature release, including gameplay features and minor internals improvements.
|
||||
|
||||
**Plugin compatibility:** Plugins for previous 5.x versions will run unchanged on this release, unless they use internal APIs, reflection, or packages like the `pocketmine\network\mcpe` or `pocketmine\data` namespace.
|
||||
Do not update plugin minimum API versions unless you need new features added in this release.
|
||||
|
||||
**WARNING: If your plugin uses the `pocketmine\network\mcpe` namespace, you're not shielded by API change constraints.**
|
||||
Consider using the `mcpe-protocol` directive in `plugin.yml` as a constraint if you're using packets directly.
|
||||
|
||||
## Gameplay
|
||||
- Added the following new blocks:
|
||||
- Campfire
|
||||
- Chiseled Copper
|
||||
- Chiseled Tuff
|
||||
- Chiseled Tuff Bricks
|
||||
- Copper Bulb
|
||||
- Copper Door
|
||||
- Copper Grate
|
||||
- Copper Trapdoor
|
||||
- Polished Tuff, Slabs, Stairs and Walls
|
||||
- Soul Campfire
|
||||
- Tuff Bricks, Slabs, Stairs and Walls
|
||||
- Tuff Slab, Stairs and Walls
|
||||
- Added the following new types of painting:
|
||||
- backyard
|
||||
- baroque
|
||||
- bouquet
|
||||
- cavebird
|
||||
- changing
|
||||
- cotan
|
||||
- endboss
|
||||
- fern
|
||||
- finding
|
||||
- humble
|
||||
- lowmist
|
||||
- meditative
|
||||
- orb
|
||||
- owlemons
|
||||
- passage
|
||||
- pond
|
||||
- prairie_ride
|
||||
- sunflowers
|
||||
- tides
|
||||
- unpacked
|
||||
- Armor slots are now properly restricted (on the server side) to only contain the appropriate type of armor or headwear.
|
||||
- Implemented Aqua Affinity enchantment. Since the server doesn't currently enforce any movement restrictions in water, this enchantment works based on client-side behaviour only.
|
||||
|
||||
## API
|
||||
### `pocketmine\block`
|
||||
- The following new API methods have been added:
|
||||
- `public ChiseledBookshelf->getLastInteractedSlot() : ?ChiseledBookshelfSlot`
|
||||
- `public ChiseledBookshelf->setLastInteractedSlot(?ChiseledBookshelfSlot $lastInteractedSlot) : $this`
|
||||
- The following new classes have been added:
|
||||
- `utils\CopperMaterial` - interface implemented by all copper-like blocks with oxidation and waxed properties
|
||||
- `CopperBulb`
|
||||
- `CopperDoor`
|
||||
- `CopperGrate`
|
||||
- `CopperTrapdoor`
|
||||
- `SoulCampfire`
|
||||
- `Campfire`
|
||||
- The following enums have new cases:
|
||||
- `utils\BannerPatternType` has new cases `FLOW` and `GUSTER`
|
||||
|
||||
### `pocketmine\crafting`
|
||||
- The following enums have new cases:
|
||||
- `FurnaceType` has new cases `CAMPFIRE` and `SOUL_CAMPFIRE`
|
||||
|
||||
### `pocketmine\event`
|
||||
- The following new classes have been added:
|
||||
- `block\CampfireCookEvent` - called when a campfire finishes cooking an item
|
||||
|
||||
### `pocketmine\inventory`
|
||||
- Added support for slot validators, which permit restricting the types of items a player can put into an inventory slot.
|
||||
- The following new classes have been added:
|
||||
- `transaction\action\SlotValidator` - interface
|
||||
- `transaction\action\CallbackSlotValidator` - class allowing a closure to be used for slot content validation
|
||||
- `SlotValidatedInventory` - implemented by inventories which support the use of slot validators
|
||||
|
||||
### `pocketmine\item`
|
||||
- The following new API methods have been added:
|
||||
- `public Item->getCooldownTag() : ?string` - returns the cooldown group this item belongs to, used for ensuring that, for example, different types of goat horns all respect a general horn cooldown
|
||||
- The following new classes have been added:
|
||||
- `ItemCooldownTags` - list of cooldown group tags used by PocketMine-MP
|
||||
|
||||
### `pocketmine\world\sound`
|
||||
- The following new classes have been added
|
||||
- `CampfireSound` - sound made by campfires while lit
|
||||
|
||||
## Tools
|
||||
- `tools/blockstate-upgrade-schema-utils.php` (formerly `generate-blockstate-upgrade-schema.php`) has several improvements:
|
||||
- Support for generating `flattenedProperties` rules as per [BedrockBlockUpgradeSchema 5.0.0](https://github.com/pmmp/BedrockBlockUpgradeSchema/releases/tag/5.0.0)
|
||||
- Improved criteria for flattened property selection to minimize the amount of rules required
|
||||
- Several subcommands are now available:
|
||||
- `generate` - generates a schema from provided data
|
||||
- `update` - regenerates an existing schema in a newer format
|
||||
- `update-all` - regenerates a folder of existing schemas in a newer format (useful for updating `BedrockBlockUpgradeSchema` en masse)
|
||||
- `test` - verifies that a schema produces the results expected by provided data
|
||||
|
||||
## Internals
|
||||
- Fixed incorrect visibility of `createEntity` in spawn eggs.
|
||||
- Added support for newer `BedrockBlockUpgradeSchema` in `BlockStateUpgrader`.
|
||||
|
||||
# 5.21.1
|
||||
Released 12th November 2024.
|
||||
|
||||
## Fixes
|
||||
- Fixed server crash when applying a cooldown to an item with 1 count.
|
||||
- Fixed garbage collector cycle count increase on player disconnect.
|
||||
- Fixed weakness effect being applied to all attack types, causing damage splash potions to become weaker.
|
||||
- Fixed Enchanted Golden Apple regeneration effect amplifier to match vanilla.
|
@ -33,10 +33,10 @@
|
||||
"composer-runtime-api": "^2.0",
|
||||
"adhocore/json-comment": "~1.2.0",
|
||||
"pocketmine/netresearch-jsonmapper": "~v4.4.999",
|
||||
"pocketmine/bedrock-block-upgrade-schema": "~4.2.0+bedrock-1.21.0",
|
||||
"pocketmine/bedrock-data": "~2.11.0+bedrock-1.21.0",
|
||||
"pocketmine/bedrock-item-upgrade-schema": "~1.10.0+bedrock-1.21.0",
|
||||
"pocketmine/bedrock-protocol": "~31.0.0+bedrock-1.21.0",
|
||||
"pocketmine/bedrock-block-upgrade-schema": "~5.0.0+bedrock-1.21.40",
|
||||
"pocketmine/bedrock-data": "~2.14.0+bedrock-1.21.40",
|
||||
"pocketmine/bedrock-item-upgrade-schema": "~1.13.0+bedrock-1.21.40",
|
||||
"pocketmine/bedrock-protocol": "~35.0.0+bedrock-1.21.40",
|
||||
"pocketmine/binaryutils": "^0.2.1",
|
||||
"pocketmine/callback-validator": "^1.0.2",
|
||||
"pocketmine/color": "^0.3.0",
|
||||
@ -52,10 +52,10 @@
|
||||
"symfony/filesystem": "~6.4.0"
|
||||
},
|
||||
"require-dev": {
|
||||
"phpstan/phpstan": "1.11.2",
|
||||
"phpstan/phpstan": "1.11.11",
|
||||
"phpstan/phpstan-phpunit": "^1.1.0",
|
||||
"phpstan/phpstan-strict-rules": "^1.2.0",
|
||||
"phpunit/phpunit": "~10.3.0 || ~10.2.0 || ~10.1.0"
|
||||
"phpunit/phpunit": "^10.5.24"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
|
234
composer.lock
generated
234
composer.lock
generated
@ -4,7 +4,7 @@
|
||||
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
|
||||
"This file is @generated automatically"
|
||||
],
|
||||
"content-hash": "941b6d463cb044438aa7908b76f7a6bb",
|
||||
"content-hash": "b2fbf6e7a9d650341dc71fa4dd124681",
|
||||
"packages": [
|
||||
{
|
||||
"name": "adhocore/json-comment",
|
||||
@ -127,16 +127,16 @@
|
||||
},
|
||||
{
|
||||
"name": "pocketmine/bedrock-block-upgrade-schema",
|
||||
"version": "4.2.0",
|
||||
"version": "5.0.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/pmmp/BedrockBlockUpgradeSchema.git",
|
||||
"reference": "8a327197b3b462fa282f40f76b070ffe585a25d2"
|
||||
"reference": "20dd5c11e9915bacea4fe2cf649e1d23697a6e52"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/pmmp/BedrockBlockUpgradeSchema/zipball/8a327197b3b462fa282f40f76b070ffe585a25d2",
|
||||
"reference": "8a327197b3b462fa282f40f76b070ffe585a25d2",
|
||||
"url": "https://api.github.com/repos/pmmp/BedrockBlockUpgradeSchema/zipball/20dd5c11e9915bacea4fe2cf649e1d23697a6e52",
|
||||
"reference": "20dd5c11e9915bacea4fe2cf649e1d23697a6e52",
|
||||
"shasum": ""
|
||||
},
|
||||
"type": "library",
|
||||
@ -147,22 +147,22 @@
|
||||
"description": "Schemas describing how to upgrade saved block data in older Minecraft: Bedrock Edition world saves",
|
||||
"support": {
|
||||
"issues": "https://github.com/pmmp/BedrockBlockUpgradeSchema/issues",
|
||||
"source": "https://github.com/pmmp/BedrockBlockUpgradeSchema/tree/4.2.0"
|
||||
"source": "https://github.com/pmmp/BedrockBlockUpgradeSchema/tree/5.0.0"
|
||||
},
|
||||
"time": "2024-06-13T17:28:26+00:00"
|
||||
"time": "2024-11-03T14:13:50+00:00"
|
||||
},
|
||||
{
|
||||
"name": "pocketmine/bedrock-data",
|
||||
"version": "2.11.0+bedrock-1.21.0",
|
||||
"version": "2.14.0+bedrock-1.21.40",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/pmmp/BedrockData.git",
|
||||
"reference": "cae40bde98081b388c4d3ab59d45b8d1cf5d8761"
|
||||
"reference": "606d32ae426164b0615898b95d10e23293bed6ac"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/pmmp/BedrockData/zipball/cae40bde98081b388c4d3ab59d45b8d1cf5d8761",
|
||||
"reference": "cae40bde98081b388c4d3ab59d45b8d1cf5d8761",
|
||||
"url": "https://api.github.com/repos/pmmp/BedrockData/zipball/606d32ae426164b0615898b95d10e23293bed6ac",
|
||||
"reference": "606d32ae426164b0615898b95d10e23293bed6ac",
|
||||
"shasum": ""
|
||||
},
|
||||
"type": "library",
|
||||
@ -173,22 +173,22 @@
|
||||
"description": "Blobs of data generated from Minecraft: Bedrock Edition, used by PocketMine-MP",
|
||||
"support": {
|
||||
"issues": "https://github.com/pmmp/BedrockData/issues",
|
||||
"source": "https://github.com/pmmp/BedrockData/tree/bedrock-1.21.0"
|
||||
"source": "https://github.com/pmmp/BedrockData/tree/bedrock-1.21.40"
|
||||
},
|
||||
"time": "2024-06-13T17:17:55+00:00"
|
||||
"time": "2024-10-23T19:19:16+00:00"
|
||||
},
|
||||
{
|
||||
"name": "pocketmine/bedrock-item-upgrade-schema",
|
||||
"version": "1.10.0",
|
||||
"version": "1.13.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/pmmp/BedrockItemUpgradeSchema.git",
|
||||
"reference": "b4687afa19f91eacebd46c40d487f4cc515be504"
|
||||
"reference": "1dee9bbd0aaa65ed108b377b402746defe10b3b0"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/pmmp/BedrockItemUpgradeSchema/zipball/b4687afa19f91eacebd46c40d487f4cc515be504",
|
||||
"reference": "b4687afa19f91eacebd46c40d487f4cc515be504",
|
||||
"url": "https://api.github.com/repos/pmmp/BedrockItemUpgradeSchema/zipball/1dee9bbd0aaa65ed108b377b402746defe10b3b0",
|
||||
"reference": "1dee9bbd0aaa65ed108b377b402746defe10b3b0",
|
||||
"shasum": ""
|
||||
},
|
||||
"type": "library",
|
||||
@ -199,22 +199,22 @@
|
||||
"description": "JSON schemas for upgrading items found in older Minecraft: Bedrock world saves",
|
||||
"support": {
|
||||
"issues": "https://github.com/pmmp/BedrockItemUpgradeSchema/issues",
|
||||
"source": "https://github.com/pmmp/BedrockItemUpgradeSchema/tree/1.10.0"
|
||||
"source": "https://github.com/pmmp/BedrockItemUpgradeSchema/tree/1.13.0"
|
||||
},
|
||||
"time": "2024-05-15T15:15:55+00:00"
|
||||
"time": "2024-10-23T18:38:43+00:00"
|
||||
},
|
||||
{
|
||||
"name": "pocketmine/bedrock-protocol",
|
||||
"version": "31.0.0+bedrock-1.21.0",
|
||||
"version": "35.0.0+bedrock-1.21.40",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/pmmp/BedrockProtocol.git",
|
||||
"reference": "972373b6b8068963649f0a95163424eb5b645e29"
|
||||
"reference": "6aa7cbeb4a7ec6fa58f9024aeaddad7c5c65a459"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/pmmp/BedrockProtocol/zipball/972373b6b8068963649f0a95163424eb5b645e29",
|
||||
"reference": "972373b6b8068963649f0a95163424eb5b645e29",
|
||||
"url": "https://api.github.com/repos/pmmp/BedrockProtocol/zipball/6aa7cbeb4a7ec6fa58f9024aeaddad7c5c65a459",
|
||||
"reference": "6aa7cbeb4a7ec6fa58f9024aeaddad7c5c65a459",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@ -227,7 +227,7 @@
|
||||
"ramsey/uuid": "^4.1"
|
||||
},
|
||||
"require-dev": {
|
||||
"phpstan/phpstan": "1.11.2",
|
||||
"phpstan/phpstan": "1.11.9",
|
||||
"phpstan/phpstan-phpunit": "^1.0.0",
|
||||
"phpstan/phpstan-strict-rules": "^1.0.0",
|
||||
"phpunit/phpunit": "^9.5 || ^10.0"
|
||||
@ -245,9 +245,9 @@
|
||||
"description": "An implementation of the Minecraft: Bedrock Edition protocol in PHP",
|
||||
"support": {
|
||||
"issues": "https://github.com/pmmp/BedrockProtocol/issues",
|
||||
"source": "https://github.com/pmmp/BedrockProtocol/tree/31.0.0+bedrock-1.21.0"
|
||||
"source": "https://github.com/pmmp/BedrockProtocol/tree/35.0.0+bedrock-1.21.40"
|
||||
},
|
||||
"time": "2024-06-13T17:34:14+00:00"
|
||||
"time": "2024-10-24T15:45:43+00:00"
|
||||
},
|
||||
{
|
||||
"name": "pocketmine/binaryutils",
|
||||
@ -926,23 +926,25 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/filesystem",
|
||||
"version": "v6.4.7",
|
||||
"version": "v6.4.9",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/filesystem.git",
|
||||
"reference": "78dde75f8f6dbbca4ec436a4b0087f7af02076d4"
|
||||
"reference": "b51ef8059159330b74a4d52f68e671033c0fe463"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/filesystem/zipball/78dde75f8f6dbbca4ec436a4b0087f7af02076d4",
|
||||
"reference": "78dde75f8f6dbbca4ec436a4b0087f7af02076d4",
|
||||
"url": "https://api.github.com/repos/symfony/filesystem/zipball/b51ef8059159330b74a4d52f68e671033c0fe463",
|
||||
"reference": "b51ef8059159330b74a4d52f68e671033c0fe463",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=8.1",
|
||||
"symfony/polyfill-ctype": "~1.8",
|
||||
"symfony/polyfill-mbstring": "~1.8",
|
||||
"symfony/process": "^5.4|^6.4"
|
||||
"symfony/polyfill-mbstring": "~1.8"
|
||||
},
|
||||
"require-dev": {
|
||||
"symfony/process": "^5.4|^6.4|^7.0"
|
||||
},
|
||||
"type": "library",
|
||||
"autoload": {
|
||||
@ -970,7 +972,7 @@
|
||||
"description": "Provides basic utilities for the filesystem",
|
||||
"homepage": "https://symfony.com",
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/filesystem/tree/v6.4.7"
|
||||
"source": "https://github.com/symfony/filesystem/tree/v6.4.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@ -986,20 +988,20 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2024-04-18T09:22:46+00:00"
|
||||
"time": "2024-06-28T09:49:33+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-ctype",
|
||||
"version": "v1.29.0",
|
||||
"version": "v1.30.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-ctype.git",
|
||||
"reference": "ef4d7e442ca910c4764bce785146269b30cb5fc4"
|
||||
"reference": "0424dff1c58f028c451efff2045f5d92410bd540"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/ef4d7e442ca910c4764bce785146269b30cb5fc4",
|
||||
"reference": "ef4d7e442ca910c4764bce785146269b30cb5fc4",
|
||||
"url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/0424dff1c58f028c451efff2045f5d92410bd540",
|
||||
"reference": "0424dff1c58f028c451efff2045f5d92410bd540",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@ -1049,7 +1051,7 @@
|
||||
"portable"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-ctype/tree/v1.29.0"
|
||||
"source": "https://github.com/symfony/polyfill-ctype/tree/v1.30.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@ -1065,20 +1067,20 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2024-01-29T20:11:03+00:00"
|
||||
"time": "2024-05-31T15:07:36+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-mbstring",
|
||||
"version": "v1.29.0",
|
||||
"version": "v1.30.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-mbstring.git",
|
||||
"reference": "9773676c8a1bb1f8d4340a62efe641cf76eda7ec"
|
||||
"reference": "fd22ab50000ef01661e2a31d850ebaa297f8e03c"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/9773676c8a1bb1f8d4340a62efe641cf76eda7ec",
|
||||
"reference": "9773676c8a1bb1f8d4340a62efe641cf76eda7ec",
|
||||
"url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/fd22ab50000ef01661e2a31d850ebaa297f8e03c",
|
||||
"reference": "fd22ab50000ef01661e2a31d850ebaa297f8e03c",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@ -1129,7 +1131,7 @@
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-mbstring/tree/v1.29.0"
|
||||
"source": "https://github.com/symfony/polyfill-mbstring/tree/v1.30.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@ -1145,83 +1147,22 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2024-01-29T20:11:03+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/process",
|
||||
"version": "v6.4.7",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/process.git",
|
||||
"reference": "cdb1c81c145fd5aa9b0038bab694035020943381"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/process/zipball/cdb1c81c145fd5aa9b0038bab694035020943381",
|
||||
"reference": "cdb1c81c145fd5aa9b0038bab694035020943381",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=8.1"
|
||||
},
|
||||
"type": "library",
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"Symfony\\Component\\Process\\": ""
|
||||
},
|
||||
"exclude-from-classmap": [
|
||||
"/Tests/"
|
||||
]
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Fabien Potencier",
|
||||
"email": "fabien@symfony.com"
|
||||
},
|
||||
{
|
||||
"name": "Symfony Community",
|
||||
"homepage": "https://symfony.com/contributors"
|
||||
}
|
||||
],
|
||||
"description": "Executes commands in sub-processes",
|
||||
"homepage": "https://symfony.com",
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/process/tree/v6.4.7"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
"url": "https://symfony.com/sponsor",
|
||||
"type": "custom"
|
||||
},
|
||||
{
|
||||
"url": "https://github.com/fabpot",
|
||||
"type": "github"
|
||||
},
|
||||
{
|
||||
"url": "https://tidelift.com/funding/github/packagist/symfony/symfony",
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2024-04-18T09:22:46+00:00"
|
||||
"time": "2024-06-19T12:30:46+00:00"
|
||||
}
|
||||
],
|
||||
"packages-dev": [
|
||||
{
|
||||
"name": "myclabs/deep-copy",
|
||||
"version": "1.11.1",
|
||||
"version": "1.12.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/myclabs/DeepCopy.git",
|
||||
"reference": "7284c22080590fb39f2ffa3e9057f10a4ddd0e0c"
|
||||
"reference": "3a6b9a42cd8f8771bd4295d13e1423fa7f3d942c"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/myclabs/DeepCopy/zipball/7284c22080590fb39f2ffa3e9057f10a4ddd0e0c",
|
||||
"reference": "7284c22080590fb39f2ffa3e9057f10a4ddd0e0c",
|
||||
"url": "https://api.github.com/repos/myclabs/DeepCopy/zipball/3a6b9a42cd8f8771bd4295d13e1423fa7f3d942c",
|
||||
"reference": "3a6b9a42cd8f8771bd4295d13e1423fa7f3d942c",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@ -1229,11 +1170,12 @@
|
||||
},
|
||||
"conflict": {
|
||||
"doctrine/collections": "<1.6.8",
|
||||
"doctrine/common": "<2.13.3 || >=3,<3.2.2"
|
||||
"doctrine/common": "<2.13.3 || >=3 <3.2.2"
|
||||
},
|
||||
"require-dev": {
|
||||
"doctrine/collections": "^1.6.8",
|
||||
"doctrine/common": "^2.13.3 || ^3.2.2",
|
||||
"phpspec/prophecy": "^1.10",
|
||||
"phpunit/phpunit": "^7.5.20 || ^8.5.23 || ^9.5.13"
|
||||
},
|
||||
"type": "library",
|
||||
@ -1259,7 +1201,7 @@
|
||||
],
|
||||
"support": {
|
||||
"issues": "https://github.com/myclabs/DeepCopy/issues",
|
||||
"source": "https://github.com/myclabs/DeepCopy/tree/1.11.1"
|
||||
"source": "https://github.com/myclabs/DeepCopy/tree/1.12.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@ -1267,7 +1209,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2023-03-08T13:26:56+00:00"
|
||||
"time": "2024-06-12T14:39:25+00:00"
|
||||
},
|
||||
{
|
||||
"name": "nikic/php-parser",
|
||||
@ -1447,16 +1389,16 @@
|
||||
},
|
||||
{
|
||||
"name": "phpstan/phpstan",
|
||||
"version": "1.11.2",
|
||||
"version": "1.11.11",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/phpstan/phpstan.git",
|
||||
"reference": "0d5d4294a70deb7547db655c47685d680e39cfec"
|
||||
"reference": "707c2aed5d8d0075666e673a5e71440c1d01a5a3"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/phpstan/phpstan/zipball/0d5d4294a70deb7547db655c47685d680e39cfec",
|
||||
"reference": "0d5d4294a70deb7547db655c47685d680e39cfec",
|
||||
"url": "https://api.github.com/repos/phpstan/phpstan/zipball/707c2aed5d8d0075666e673a5e71440c1d01a5a3",
|
||||
"reference": "707c2aed5d8d0075666e673a5e71440c1d01a5a3",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@ -1501,25 +1443,25 @@
|
||||
"type": "github"
|
||||
}
|
||||
],
|
||||
"time": "2024-05-24T13:23:04+00:00"
|
||||
"time": "2024-08-19T14:37:29+00:00"
|
||||
},
|
||||
{
|
||||
"name": "phpstan/phpstan-phpunit",
|
||||
"version": "1.3.16",
|
||||
"version": "1.4.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/phpstan/phpstan-phpunit.git",
|
||||
"reference": "d5242a59d035e46774f2e634b374bc39ff62cb95"
|
||||
"reference": "f3ea021866f4263f07ca3636bf22c64be9610c11"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/phpstan/phpstan-phpunit/zipball/d5242a59d035e46774f2e634b374bc39ff62cb95",
|
||||
"reference": "d5242a59d035e46774f2e634b374bc39ff62cb95",
|
||||
"url": "https://api.github.com/repos/phpstan/phpstan-phpunit/zipball/f3ea021866f4263f07ca3636bf22c64be9610c11",
|
||||
"reference": "f3ea021866f4263f07ca3636bf22c64be9610c11",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": "^7.2 || ^8.0",
|
||||
"phpstan/phpstan": "^1.10"
|
||||
"phpstan/phpstan": "^1.11"
|
||||
},
|
||||
"conflict": {
|
||||
"phpunit/phpunit": "<7.0"
|
||||
@ -1551,27 +1493,27 @@
|
||||
"description": "PHPUnit extensions and rules for PHPStan",
|
||||
"support": {
|
||||
"issues": "https://github.com/phpstan/phpstan-phpunit/issues",
|
||||
"source": "https://github.com/phpstan/phpstan-phpunit/tree/1.3.16"
|
||||
"source": "https://github.com/phpstan/phpstan-phpunit/tree/1.4.0"
|
||||
},
|
||||
"time": "2024-02-23T09:51:20+00:00"
|
||||
"time": "2024-04-20T06:39:00+00:00"
|
||||
},
|
||||
{
|
||||
"name": "phpstan/phpstan-strict-rules",
|
||||
"version": "1.5.5",
|
||||
"version": "1.6.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/phpstan/phpstan-strict-rules.git",
|
||||
"reference": "2e193a07651a6f4be3baa44ddb21d822681f5918"
|
||||
"reference": "363f921dd8441777d4fc137deb99beb486c77df1"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/phpstan/phpstan-strict-rules/zipball/2e193a07651a6f4be3baa44ddb21d822681f5918",
|
||||
"reference": "2e193a07651a6f4be3baa44ddb21d822681f5918",
|
||||
"url": "https://api.github.com/repos/phpstan/phpstan-strict-rules/zipball/363f921dd8441777d4fc137deb99beb486c77df1",
|
||||
"reference": "363f921dd8441777d4fc137deb99beb486c77df1",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": "^7.2 || ^8.0",
|
||||
"phpstan/phpstan": "^1.10.60"
|
||||
"phpstan/phpstan": "^1.11"
|
||||
},
|
||||
"require-dev": {
|
||||
"nikic/php-parser": "^4.13.0",
|
||||
@ -1600,22 +1542,22 @@
|
||||
"description": "Extra strict and opinionated rules for PHPStan",
|
||||
"support": {
|
||||
"issues": "https://github.com/phpstan/phpstan-strict-rules/issues",
|
||||
"source": "https://github.com/phpstan/phpstan-strict-rules/tree/1.5.5"
|
||||
"source": "https://github.com/phpstan/phpstan-strict-rules/tree/1.6.0"
|
||||
},
|
||||
"time": "2024-04-19T15:12:26+00:00"
|
||||
"time": "2024-04-20T06:37:51+00:00"
|
||||
},
|
||||
{
|
||||
"name": "phpunit/php-code-coverage",
|
||||
"version": "10.1.14",
|
||||
"version": "10.1.15",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/sebastianbergmann/php-code-coverage.git",
|
||||
"reference": "e3f51450ebffe8e0efdf7346ae966a656f7d5e5b"
|
||||
"reference": "5da8b1728acd1e6ffdf2ff32ffbdfd04307f26ae"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/sebastianbergmann/php-code-coverage/zipball/e3f51450ebffe8e0efdf7346ae966a656f7d5e5b",
|
||||
"reference": "e3f51450ebffe8e0efdf7346ae966a656f7d5e5b",
|
||||
"url": "https://api.github.com/repos/sebastianbergmann/php-code-coverage/zipball/5da8b1728acd1e6ffdf2ff32ffbdfd04307f26ae",
|
||||
"reference": "5da8b1728acd1e6ffdf2ff32ffbdfd04307f26ae",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@ -1672,7 +1614,7 @@
|
||||
"support": {
|
||||
"issues": "https://github.com/sebastianbergmann/php-code-coverage/issues",
|
||||
"security": "https://github.com/sebastianbergmann/php-code-coverage/security/policy",
|
||||
"source": "https://github.com/sebastianbergmann/php-code-coverage/tree/10.1.14"
|
||||
"source": "https://github.com/sebastianbergmann/php-code-coverage/tree/10.1.15"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@ -1680,7 +1622,7 @@
|
||||
"type": "github"
|
||||
}
|
||||
],
|
||||
"time": "2024-03-12T15:33:41+00:00"
|
||||
"time": "2024-06-29T08:25:15+00:00"
|
||||
},
|
||||
{
|
||||
"name": "phpunit/php-file-iterator",
|
||||
@ -1927,16 +1869,16 @@
|
||||
},
|
||||
{
|
||||
"name": "phpunit/phpunit",
|
||||
"version": "10.3.5",
|
||||
"version": "10.5.24",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/sebastianbergmann/phpunit.git",
|
||||
"reference": "747c3b2038f1139e3dcd9886a3f5a948648b7503"
|
||||
"reference": "5f124e3e3e561006047b532fd0431bf5bb6b9015"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/sebastianbergmann/phpunit/zipball/747c3b2038f1139e3dcd9886a3f5a948648b7503",
|
||||
"reference": "747c3b2038f1139e3dcd9886a3f5a948648b7503",
|
||||
"url": "https://api.github.com/repos/sebastianbergmann/phpunit/zipball/5f124e3e3e561006047b532fd0431bf5bb6b9015",
|
||||
"reference": "5f124e3e3e561006047b532fd0431bf5bb6b9015",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@ -1976,7 +1918,7 @@
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"branch-alias": {
|
||||
"dev-main": "10.3-dev"
|
||||
"dev-main": "10.5-dev"
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
@ -2008,7 +1950,7 @@
|
||||
"support": {
|
||||
"issues": "https://github.com/sebastianbergmann/phpunit/issues",
|
||||
"security": "https://github.com/sebastianbergmann/phpunit/security/policy",
|
||||
"source": "https://github.com/sebastianbergmann/phpunit/tree/10.3.5"
|
||||
"source": "https://github.com/sebastianbergmann/phpunit/tree/10.5.24"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@ -2024,7 +1966,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2023-09-19T05:42:37+00:00"
|
||||
"time": "2024-06-20T13:09:54+00:00"
|
||||
},
|
||||
{
|
||||
"name": "sebastian/cli-parser",
|
||||
|
@ -40,6 +40,7 @@ parameters:
|
||||
- build/php
|
||||
dynamicConstantNames:
|
||||
- pocketmine\VersionInfo::IS_DEVELOPMENT_BUILD
|
||||
- pocketmine\VersionInfo::BUILD_CHANNEL
|
||||
- pocketmine\DEBUG
|
||||
- pocketmine\IS_DEVELOPMENT_BUILD
|
||||
stubFiles:
|
||||
|
@ -31,7 +31,7 @@ use function str_repeat;
|
||||
|
||||
final class VersionInfo{
|
||||
public const NAME = "PocketMine-MP";
|
||||
public const BASE_VERSION = "5.16.1";
|
||||
public const BASE_VERSION = "5.21.2";
|
||||
public const IS_DEVELOPMENT_BUILD = true;
|
||||
public const BUILD_CHANNEL = "stable";
|
||||
|
||||
|
@ -91,7 +91,7 @@ class Anvil extends Transparent implements Fallable{
|
||||
|
||||
public function place(BlockTransaction $tx, Item $item, Block $blockReplace, Block $blockClicked, int $face, Vector3 $clickVector, ?Player $player = null) : bool{
|
||||
if($player !== null){
|
||||
$this->facing = Facing::rotateY($player->getHorizontalFacing(), true);
|
||||
$this->facing = Facing::rotateY($player->getHorizontalFacing(), false);
|
||||
}
|
||||
return parent::place($tx, $item, $blockReplace, $blockClicked, $face, $clickVector, $player);
|
||||
}
|
||||
|
@ -150,6 +150,10 @@ final class Bell extends Transparent{
|
||||
}
|
||||
}
|
||||
|
||||
public function getDropsForIncompatibleTool(Item $item) : array{
|
||||
return [$this->asItem()];
|
||||
}
|
||||
|
||||
private function isValidFaceToRing(int $faceHit) : bool{
|
||||
return match($this->attachmentType){
|
||||
BellAttachmentType::CEILING => true,
|
||||
|
@ -745,8 +745,28 @@ final class BlockTypeIds{
|
||||
public const PITCHER_PLANT = 10715;
|
||||
public const PITCHER_CROP = 10716;
|
||||
public const DOUBLE_PITCHER_CROP = 10717;
|
||||
public const CAMPFIRE = 10718;
|
||||
public const SOUL_CAMPFIRE = 10719;
|
||||
public const TUFF_SLAB = 10720;
|
||||
public const TUFF_STAIRS = 10721;
|
||||
public const TUFF_WALL = 10722;
|
||||
public const CHISELED_TUFF = 10723;
|
||||
public const TUFF_BRICKS = 10724;
|
||||
public const TUFF_BRICK_SLAB = 10725;
|
||||
public const TUFF_BRICK_STAIRS = 10726;
|
||||
public const TUFF_BRICK_WALL = 10727;
|
||||
public const CHISELED_TUFF_BRICKS = 10728;
|
||||
public const POLISHED_TUFF = 10729;
|
||||
public const POLISHED_TUFF_SLAB = 10730;
|
||||
public const POLISHED_TUFF_STAIRS = 10731;
|
||||
public const POLISHED_TUFF_WALL = 10732;
|
||||
public const COPPER_BULB = 10733;
|
||||
public const COPPER_DOOR = 10734;
|
||||
public const COPPER_TRAPDOOR = 10735;
|
||||
public const CHISELED_COPPER = 10736;
|
||||
public const COPPER_GRATE = 10737;
|
||||
|
||||
public const FIRST_UNUSED_BLOCK_ID = 10718;
|
||||
public const FIRST_UNUSED_BLOCK_ID = 10738;
|
||||
|
||||
private static int $nextDynamicId = self::FIRST_UNUSED_BLOCK_ID;
|
||||
|
||||
|
@ -27,10 +27,6 @@ use pocketmine\item\Item;
|
||||
|
||||
class BlueIce extends Opaque{
|
||||
|
||||
public function getLightLevel() : int{
|
||||
return 1;
|
||||
}
|
||||
|
||||
public function getFrictionFactor() : float{
|
||||
return 0.99;
|
||||
}
|
||||
@ -38,4 +34,8 @@ class BlueIce extends Opaque{
|
||||
public function getDropsForCompatibleTool(Item $item) : array{
|
||||
return [];
|
||||
}
|
||||
|
||||
public function isAffectedBySilkTouch() : bool{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
277
src/block/Campfire.php
Normal file
277
src/block/Campfire.php
Normal file
@ -0,0 +1,277 @@
|
||||
<?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\block;
|
||||
|
||||
use pocketmine\block\inventory\CampfireInventory;
|
||||
use pocketmine\block\tile\Campfire as TileCampfire;
|
||||
use pocketmine\block\utils\HorizontalFacingTrait;
|
||||
use pocketmine\block\utils\LightableTrait;
|
||||
use pocketmine\block\utils\SupportType;
|
||||
use pocketmine\crafting\FurnaceRecipe;
|
||||
use pocketmine\crafting\FurnaceType;
|
||||
use pocketmine\data\runtime\RuntimeDataDescriber;
|
||||
use pocketmine\entity\Entity;
|
||||
use pocketmine\entity\Living;
|
||||
use pocketmine\entity\projectile\Projectile;
|
||||
use pocketmine\entity\projectile\SplashPotion;
|
||||
use pocketmine\event\block\CampfireCookEvent;
|
||||
use pocketmine\event\entity\EntityDamageByBlockEvent;
|
||||
use pocketmine\event\entity\EntityDamageEvent;
|
||||
use pocketmine\item\Durable;
|
||||
use pocketmine\item\enchantment\VanillaEnchantments;
|
||||
use pocketmine\item\Item;
|
||||
use pocketmine\item\ItemTypeIds;
|
||||
use pocketmine\item\PotionType;
|
||||
use pocketmine\item\Shovel;
|
||||
use pocketmine\item\VanillaItems;
|
||||
use pocketmine\math\AxisAlignedBB;
|
||||
use pocketmine\math\Facing;
|
||||
use pocketmine\math\RayTraceResult;
|
||||
use pocketmine\math\Vector3;
|
||||
use pocketmine\player\Player;
|
||||
use pocketmine\world\BlockTransaction;
|
||||
use pocketmine\world\sound\BlazeShootSound;
|
||||
use pocketmine\world\sound\FireExtinguishSound;
|
||||
use pocketmine\world\sound\FlintSteelSound;
|
||||
use pocketmine\world\sound\ItemFrameAddItemSound;
|
||||
use function count;
|
||||
use function min;
|
||||
use function mt_rand;
|
||||
|
||||
class Campfire extends Transparent{
|
||||
use HorizontalFacingTrait{
|
||||
HorizontalFacingTrait::describeBlockOnlyState as encodeFacingState;
|
||||
}
|
||||
use LightableTrait{
|
||||
LightableTrait::describeBlockOnlyState as encodeLitState;
|
||||
}
|
||||
|
||||
private const UPDATE_INTERVAL_TICKS = 10;
|
||||
|
||||
protected CampfireInventory $inventory;
|
||||
|
||||
/**
|
||||
* @var int[] slot => ticks
|
||||
* @phpstan-var array<int, int>
|
||||
*/
|
||||
protected array $cookingTimes = [];
|
||||
|
||||
protected function describeBlockOnlyState(RuntimeDataDescriber $w) : void{
|
||||
$this->encodeFacingState($w);
|
||||
$this->encodeLitState($w);
|
||||
}
|
||||
|
||||
public function readStateFromWorld() : Block{
|
||||
parent::readStateFromWorld();
|
||||
$tile = $this->position->getWorld()->getTile($this->position);
|
||||
if($tile instanceof TileCampfire){
|
||||
$this->inventory = $tile->getInventory();
|
||||
$this->cookingTimes = $tile->getCookingTimes();
|
||||
}else{
|
||||
$this->inventory = new CampfireInventory($this->position);
|
||||
}
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
public function writeStateToWorld() : void{
|
||||
parent::writeStateToWorld();
|
||||
$tile = $this->position->getWorld()->getTile($this->position);
|
||||
if($tile instanceof TileCampfire){
|
||||
$tile->setCookingTimes($this->cookingTimes);
|
||||
}
|
||||
}
|
||||
|
||||
public function hasEntityCollision() : bool{
|
||||
return true;
|
||||
}
|
||||
|
||||
public function getLightLevel() : int{
|
||||
return $this->lit ? 15 : 0;
|
||||
}
|
||||
|
||||
public function isAffectedBySilkTouch() : bool{
|
||||
return true;
|
||||
}
|
||||
|
||||
public function getDropsForCompatibleTool(Item $item) : array{
|
||||
return [
|
||||
VanillaItems::CHARCOAL()->setCount(2)
|
||||
];
|
||||
}
|
||||
|
||||
public function getSupportType(int $facing) : SupportType{
|
||||
return SupportType::NONE;
|
||||
}
|
||||
|
||||
protected function recalculateCollisionBoxes() : array{
|
||||
return [AxisAlignedBB::one()->trim(Facing::UP, 9 / 16)];
|
||||
}
|
||||
|
||||
public function getInventory() : CampfireInventory{
|
||||
return $this->inventory;
|
||||
}
|
||||
|
||||
protected function getFurnaceType() : FurnaceType{
|
||||
return FurnaceType::CAMPFIRE;
|
||||
}
|
||||
|
||||
protected function getEntityCollisionDamage() : int{
|
||||
return 1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the number of ticks during the item in the given slot has been cooked.
|
||||
*/
|
||||
public function setCookingTime(int $slot, int $time) : void{
|
||||
if($slot < 0 || $slot > 3){
|
||||
throw new \InvalidArgumentException("Slot must be in range 0-3");
|
||||
}
|
||||
if($time < 0 || $time > $this->getFurnaceType()->getCookDurationTicks()){
|
||||
throw new \InvalidArgumentException("CookingTime must be in range 0-" . $this->getFurnaceType()->getCookDurationTicks());
|
||||
}
|
||||
$this->cookingTimes[$slot] = $time;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the number of ticks during the item in the given slot has been cooked.
|
||||
*/
|
||||
public function getCookingTime(int $slot) : int{
|
||||
return $this->cookingTimes[$slot] ?? 0;
|
||||
}
|
||||
|
||||
public function place(BlockTransaction $tx, Item $item, Block $blockReplace, Block $blockClicked, int $face, Vector3 $clickVector, ?Player $player = null) : bool{
|
||||
if($this->getSide(Facing::DOWN) instanceof Campfire){
|
||||
return false;
|
||||
}
|
||||
if($player !== null){
|
||||
$this->facing = $player->getHorizontalFacing();
|
||||
}
|
||||
$this->lit = true;
|
||||
return parent::place($tx, $item, $blockReplace, $blockClicked, $face, $clickVector, $player);
|
||||
}
|
||||
|
||||
public function onInteract(Item $item, int $face, Vector3 $clickVector, ?Player $player = null, array &$returnedItems = []) : bool{
|
||||
if(!$this->lit){
|
||||
if($item->getTypeId() === ItemTypeIds::FIRE_CHARGE){
|
||||
$item->pop();
|
||||
$this->ignite();
|
||||
$this->position->getWorld()->addSound($this->position, new BlazeShootSound());
|
||||
return true;
|
||||
}elseif($item->getTypeId() === ItemTypeIds::FLINT_AND_STEEL || $item->hasEnchantment(VanillaEnchantments::FIRE_ASPECT())){
|
||||
if($item instanceof Durable){
|
||||
$item->applyDamage(1);
|
||||
}
|
||||
$this->ignite();
|
||||
return true;
|
||||
}
|
||||
}elseif($item instanceof Shovel){
|
||||
$item->applyDamage(1);
|
||||
$this->extinguish();
|
||||
return true;
|
||||
}
|
||||
|
||||
if($this->position->getWorld()->getServer()->getCraftingManager()->getFurnaceRecipeManager($this->getFurnaceType())->match($item) !== null){
|
||||
$ingredient = clone $item;
|
||||
$ingredient->setCount(1);
|
||||
if(count($this->inventory->addItem($ingredient)) === 0){
|
||||
$item->pop();
|
||||
$this->position->getWorld()->addSound($this->position, new ItemFrameAddItemSound());
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public function onNearbyBlockChange() : void{
|
||||
if($this->lit && $this->getSide(Facing::UP)->getTypeId() === BlockTypeIds::WATER){
|
||||
$this->extinguish();
|
||||
//TODO: Waterlogging
|
||||
}
|
||||
}
|
||||
|
||||
public function onEntityInside(Entity $entity) : bool{
|
||||
if(!$this->lit){
|
||||
if($entity->isOnFire()){
|
||||
$this->ignite();
|
||||
return false;
|
||||
}
|
||||
}elseif($entity instanceof Living){
|
||||
$entity->attack(new EntityDamageByBlockEvent($this, $entity, EntityDamageEvent::CAUSE_FIRE, $this->getEntityCollisionDamage()));
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
public function onProjectileHit(Projectile $projectile, RayTraceResult $hitResult) : void{
|
||||
if($this->lit && $projectile instanceof SplashPotion && $projectile->getPotionType() === PotionType::WATER){
|
||||
$this->extinguish();
|
||||
}
|
||||
}
|
||||
|
||||
public function onScheduledUpdate() : void{
|
||||
if($this->lit){
|
||||
$items = $this->inventory->getContents();
|
||||
$furnaceType = $this->getFurnaceType();
|
||||
$maxCookDuration = $furnaceType->getCookDurationTicks();
|
||||
foreach($items as $slot => $item){
|
||||
$this->setCookingTime($slot, min($maxCookDuration, $this->getCookingTime($slot) + self::UPDATE_INTERVAL_TICKS));
|
||||
if($this->getCookingTime($slot) >= $maxCookDuration){
|
||||
$result =
|
||||
($recipe = $this->position->getWorld()->getServer()->getCraftingManager()->getFurnaceRecipeManager($furnaceType)->match($item)) instanceof FurnaceRecipe ?
|
||||
$recipe->getResult() :
|
||||
VanillaItems::AIR();
|
||||
|
||||
$ev = new CampfireCookEvent($this, $slot, $item, $result);
|
||||
$ev->call();
|
||||
|
||||
if ($ev->isCancelled()){
|
||||
continue;
|
||||
}
|
||||
|
||||
$this->inventory->setItem($slot, VanillaItems::AIR());
|
||||
$this->setCookingTime($slot, 0);
|
||||
$this->position->getWorld()->dropItem($this->position->add(0.5, 1, 0.5), $ev->getResult());
|
||||
}
|
||||
}
|
||||
if(count($items) > 0){
|
||||
$this->position->getWorld()->setBlock($this->position, $this);
|
||||
}
|
||||
if(mt_rand(1, 6) === 1){
|
||||
$this->position->getWorld()->addSound($this->position, $furnaceType->getCookSound());
|
||||
}
|
||||
$this->position->getWorld()->scheduleDelayedBlockUpdate($this->position, self::UPDATE_INTERVAL_TICKS);
|
||||
}
|
||||
}
|
||||
|
||||
private function extinguish() : void{
|
||||
$this->position->getWorld()->addSound($this->position, new FireExtinguishSound());
|
||||
$this->position->getWorld()->setBlock($this->position, $this->setLit(false));
|
||||
}
|
||||
|
||||
private function ignite() : void{
|
||||
$this->position->getWorld()->addSound($this->position, new FlintSteelSound());
|
||||
$this->position->getWorld()->setBlock($this->position, $this->setLit(true));
|
||||
$this->position->getWorld()->scheduleDelayedBlockUpdate($this->position, self::UPDATE_INTERVAL_TICKS);
|
||||
}
|
||||
}
|
@ -48,11 +48,32 @@ class ChiseledBookshelf extends Opaque{
|
||||
*/
|
||||
private array $slots = [];
|
||||
|
||||
private ?ChiseledBookshelfSlot $lastInteractedSlot = null;
|
||||
|
||||
protected function describeBlockOnlyState(RuntimeDataDescriber $w) : void{
|
||||
$w->horizontalFacing($this->facing);
|
||||
$w->enumSet($this->slots, ChiseledBookshelfSlot::cases());
|
||||
}
|
||||
|
||||
public function readStateFromWorld() : Block{
|
||||
$tile = $this->position->getWorld()->getTile($this->position);
|
||||
if($tile instanceof TileChiseledBookshelf){
|
||||
$this->lastInteractedSlot = $tile->getLastInteractedSlot();
|
||||
}else{
|
||||
$this->lastInteractedSlot = null;
|
||||
}
|
||||
return $this;
|
||||
}
|
||||
|
||||
public function writeStateToWorld() : void{
|
||||
parent::writeStateToWorld();
|
||||
|
||||
$tile = $this->position->getWorld()->getTile($this->position);
|
||||
if($tile instanceof TileChiseledBookshelf){
|
||||
$tile->setLastInteractedSlot($this->lastInteractedSlot);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns whether the given slot is displayed as occupied.
|
||||
* This doesn't guarantee that there is or isn't a book in the bookshelf's inventory.
|
||||
@ -92,6 +113,23 @@ class ChiseledBookshelf extends Opaque{
|
||||
return $this->slots;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the last slot interacted by a player or null if no slot has been interacted with yet.
|
||||
*/
|
||||
public function getLastInteractedSlot() : ?ChiseledBookshelfSlot{
|
||||
return $this->lastInteractedSlot;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the last slot interacted by a player.
|
||||
*
|
||||
* @return $this
|
||||
*/
|
||||
public function setLastInteractedSlot(?ChiseledBookshelfSlot $lastInteractedSlot) : self{
|
||||
$this->lastInteractedSlot = $lastInteractedSlot;
|
||||
return $this;
|
||||
}
|
||||
|
||||
public function onInteract(Item $item, int $face, Vector3 $clickVector, ?Player $player = null, array &$returnedItems = []) : bool{
|
||||
if($face !== $this->facing){
|
||||
return false;
|
||||
@ -112,10 +150,12 @@ class ChiseledBookshelf extends Opaque{
|
||||
$returnedItems[] = $inventory->getItem($slot->value);
|
||||
$inventory->clear($slot->value);
|
||||
$this->setSlot($slot, false);
|
||||
$this->lastInteractedSlot = $slot;
|
||||
}elseif($item instanceof WritableBookBase || $item instanceof Book || $item instanceof EnchantedBook){
|
||||
//TODO: type tags like blocks would be better for this
|
||||
$inventory->setItem($slot->value, $item->pop());
|
||||
$this->setSlot($slot, true);
|
||||
$this->lastInteractedSlot = $slot;
|
||||
}else{
|
||||
return true;
|
||||
}
|
||||
|
@ -23,8 +23,9 @@ declare(strict_types=1);
|
||||
|
||||
namespace pocketmine\block;
|
||||
|
||||
use pocketmine\block\utils\CopperMaterial;
|
||||
use pocketmine\block\utils\CopperTrait;
|
||||
|
||||
class Copper extends Opaque{
|
||||
class Copper extends Opaque implements CopperMaterial{
|
||||
use CopperTrait;
|
||||
}
|
||||
|
69
src/block/CopperBulb.php
Normal file
69
src/block/CopperBulb.php
Normal file
@ -0,0 +1,69 @@
|
||||
<?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\block;
|
||||
|
||||
use pocketmine\block\utils\CopperMaterial;
|
||||
use pocketmine\block\utils\CopperOxidation;
|
||||
use pocketmine\block\utils\CopperTrait;
|
||||
use pocketmine\block\utils\LightableTrait;
|
||||
use pocketmine\block\utils\PoweredByRedstoneTrait;
|
||||
use pocketmine\data\runtime\RuntimeDataDescriber;
|
||||
|
||||
class CopperBulb extends Opaque implements CopperMaterial{
|
||||
use CopperTrait;
|
||||
use PoweredByRedstoneTrait;
|
||||
use LightableTrait{
|
||||
describeBlockOnlyState as encodeLitState;
|
||||
}
|
||||
|
||||
protected function describeBlockOnlyState(RuntimeDataDescriber $w) : void{
|
||||
$this->encodeLitState($w);
|
||||
$w->bool($this->powered);
|
||||
}
|
||||
|
||||
/** @return $this */
|
||||
public function togglePowered(bool $powered) : self{
|
||||
if($powered === $this->powered){
|
||||
return $this;
|
||||
}
|
||||
if ($powered) {
|
||||
$this->setLit(!$this->lit);
|
||||
}
|
||||
$this->setPowered($powered);
|
||||
return $this;
|
||||
}
|
||||
|
||||
public function getLightLevel() : int{
|
||||
if ($this->lit) {
|
||||
return match($this->oxidation){
|
||||
CopperOxidation::NONE => 15,
|
||||
CopperOxidation::EXPOSED => 12,
|
||||
CopperOxidation::WEATHERED => 8,
|
||||
CopperOxidation::OXIDIZED => 4,
|
||||
};
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
}
|
53
src/block/CopperDoor.php
Normal file
53
src/block/CopperDoor.php
Normal file
@ -0,0 +1,53 @@
|
||||
<?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\block;
|
||||
|
||||
use pocketmine\block\utils\CopperMaterial;
|
||||
use pocketmine\block\utils\CopperTrait;
|
||||
use pocketmine\item\Item;
|
||||
use pocketmine\math\Facing;
|
||||
use pocketmine\math\Vector3;
|
||||
use pocketmine\player\Player;
|
||||
|
||||
class CopperDoor extends Door implements CopperMaterial{
|
||||
use CopperTrait{
|
||||
onInteract as onInteractCopper;
|
||||
}
|
||||
|
||||
public function onInteract(Item $item, int $face, Vector3 $clickVector, ?Player $player = null, array &$returnedItems = []) : bool{
|
||||
if ($player !== null && $player->isSneaking() && $this->onInteractCopper($item, $face, $clickVector, $player, $returnedItems)) {
|
||||
//copy copper properties to other half
|
||||
$other = $this->getSide($this->top ? Facing::DOWN : Facing::UP);
|
||||
$world = $this->position->getWorld();
|
||||
if ($other instanceof CopperDoor) {
|
||||
$other->setOxidation($this->oxidation);
|
||||
$other->setWaxed($this->waxed);
|
||||
$world->setBlock($other->position, $other);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
return parent::onInteract($item, $face, $clickVector, $player, $returnedItems);
|
||||
}
|
||||
}
|
33
src/block/CopperGrate.php
Normal file
33
src/block/CopperGrate.php
Normal file
@ -0,0 +1,33 @@
|
||||
<?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\block;
|
||||
|
||||
use pocketmine\block\utils\CopperMaterial;
|
||||
use pocketmine\block\utils\CopperTrait;
|
||||
|
||||
class CopperGrate extends Transparent implements CopperMaterial{
|
||||
use CopperTrait;
|
||||
|
||||
//TODO: waterlogging!
|
||||
}
|
@ -23,8 +23,9 @@ declare(strict_types=1);
|
||||
|
||||
namespace pocketmine\block;
|
||||
|
||||
use pocketmine\block\utils\CopperMaterial;
|
||||
use pocketmine\block\utils\CopperTrait;
|
||||
|
||||
class CopperSlab extends Slab{
|
||||
class CopperSlab extends Slab implements CopperMaterial{
|
||||
use CopperTrait;
|
||||
}
|
||||
|
@ -23,8 +23,9 @@ declare(strict_types=1);
|
||||
|
||||
namespace pocketmine\block;
|
||||
|
||||
use pocketmine\block\utils\CopperMaterial;
|
||||
use pocketmine\block\utils\CopperTrait;
|
||||
|
||||
class CopperStairs extends Stair{
|
||||
class CopperStairs extends Stair implements CopperMaterial{
|
||||
use CopperTrait;
|
||||
}
|
||||
|
44
src/block/CopperTrapdoor.php
Normal file
44
src/block/CopperTrapdoor.php
Normal file
@ -0,0 +1,44 @@
|
||||
<?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\block;
|
||||
|
||||
use pocketmine\block\utils\CopperMaterial;
|
||||
use pocketmine\block\utils\CopperTrait;
|
||||
use pocketmine\item\Item;
|
||||
use pocketmine\math\Vector3;
|
||||
use pocketmine\player\Player;
|
||||
|
||||
class CopperTrapdoor extends Trapdoor implements CopperMaterial{
|
||||
use CopperTrait{
|
||||
onInteract as onInteractCopper;
|
||||
}
|
||||
|
||||
public function onInteract(Item $item, int $face, Vector3 $clickVector, ?Player $player = null, array &$returnedItems = []) : bool{
|
||||
if ($player !== null && $player->isSneaking() && $this->onInteractCopper($item, $face, $clickVector, $player, $returnedItems)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return parent::onInteract($item, $face, $clickVector, $player, $returnedItems);
|
||||
}
|
||||
}
|
48
src/block/SoulCampfire.php
Normal file
48
src/block/SoulCampfire.php
Normal file
@ -0,0 +1,48 @@
|
||||
<?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\block;
|
||||
|
||||
use pocketmine\crafting\FurnaceType;
|
||||
use pocketmine\item\Item;
|
||||
|
||||
class SoulCampfire extends Campfire{
|
||||
|
||||
public function getLightLevel() : int{
|
||||
return $this->lit ? 10 : 0;
|
||||
}
|
||||
|
||||
public function getDropsForCompatibleTool(Item $item) : array{
|
||||
return [
|
||||
VanillaBlocks::SOUL_SOIL()->asItem()
|
||||
];
|
||||
}
|
||||
|
||||
protected function getEntityCollisionDamage() : int{
|
||||
return 2;
|
||||
}
|
||||
|
||||
protected function getFurnaceType() : FurnaceType{
|
||||
return FurnaceType::SOUL_CAMPFIRE;
|
||||
}
|
||||
}
|
@ -36,6 +36,7 @@ use pocketmine\block\tile\Bed as TileBed;
|
||||
use pocketmine\block\tile\Bell as TileBell;
|
||||
use pocketmine\block\tile\BlastFurnace as TileBlastFurnace;
|
||||
use pocketmine\block\tile\BrewingStand as TileBrewingStand;
|
||||
use pocketmine\block\tile\Campfire as TileCampfire;
|
||||
use pocketmine\block\tile\Cauldron as TileCauldron;
|
||||
use pocketmine\block\tile\Chest as TileChest;
|
||||
use pocketmine\block\tile\ChiseledBookshelf as TileChiseledBookshelf;
|
||||
@ -154,6 +155,7 @@ use function strtolower;
|
||||
* @method static CakeWithCandle CAKE_WITH_CANDLE()
|
||||
* @method static CakeWithDyedCandle CAKE_WITH_DYED_CANDLE()
|
||||
* @method static Opaque CALCITE()
|
||||
* @method static Campfire CAMPFIRE()
|
||||
* @method static Candle CANDLE()
|
||||
* @method static Carpet CARPET()
|
||||
* @method static Carrot CARROTS()
|
||||
@ -179,6 +181,7 @@ use function strtolower;
|
||||
* @method static Wood CHERRY_WOOD()
|
||||
* @method static Chest CHEST()
|
||||
* @method static ChiseledBookshelf CHISELED_BOOKSHELF()
|
||||
* @method static Copper CHISELED_COPPER()
|
||||
* @method static Opaque CHISELED_DEEPSLATE()
|
||||
* @method static Opaque CHISELED_NETHER_BRICKS()
|
||||
* @method static Opaque CHISELED_POLISHED_BLACKSTONE()
|
||||
@ -186,6 +189,8 @@ use function strtolower;
|
||||
* @method static Opaque CHISELED_RED_SANDSTONE()
|
||||
* @method static Opaque CHISELED_SANDSTONE()
|
||||
* @method static Opaque CHISELED_STONE_BRICKS()
|
||||
* @method static Opaque CHISELED_TUFF()
|
||||
* @method static Opaque CHISELED_TUFF_BRICKS()
|
||||
* @method static ChorusFlower CHORUS_FLOWER()
|
||||
* @method static ChorusPlant CHORUS_PLANT()
|
||||
* @method static Clay CLAY()
|
||||
@ -205,7 +210,11 @@ use function strtolower;
|
||||
* @method static Concrete CONCRETE()
|
||||
* @method static ConcretePowder CONCRETE_POWDER()
|
||||
* @method static Copper COPPER()
|
||||
* @method static CopperBulb COPPER_BULB()
|
||||
* @method static CopperDoor COPPER_DOOR()
|
||||
* @method static CopperGrate COPPER_GRATE()
|
||||
* @method static CopperOre COPPER_ORE()
|
||||
* @method static CopperTrapdoor COPPER_TRAPDOOR()
|
||||
* @method static Coral CORAL()
|
||||
* @method static CoralBlock CORAL_BLOCK()
|
||||
* @method static FloorCoralFan CORAL_FAN()
|
||||
@ -607,6 +616,10 @@ use function strtolower;
|
||||
* @method static Opaque POLISHED_GRANITE()
|
||||
* @method static Slab POLISHED_GRANITE_SLAB()
|
||||
* @method static Stair POLISHED_GRANITE_STAIRS()
|
||||
* @method static Opaque POLISHED_TUFF()
|
||||
* @method static Slab POLISHED_TUFF_SLAB()
|
||||
* @method static Stair POLISHED_TUFF_STAIRS()
|
||||
* @method static Wall POLISHED_TUFF_WALL()
|
||||
* @method static Flower POPPY()
|
||||
* @method static Potato POTATOES()
|
||||
* @method static PotionCauldron POTION_CAULDRON()
|
||||
@ -685,6 +698,7 @@ use function strtolower;
|
||||
* @method static Slab SMOOTH_STONE_SLAB()
|
||||
* @method static Snow SNOW()
|
||||
* @method static SnowLayer SNOW_LAYER()
|
||||
* @method static SoulCampfire SOUL_CAMPFIRE()
|
||||
* @method static SoulFire SOUL_FIRE()
|
||||
* @method static Lantern SOUL_LANTERN()
|
||||
* @method static SoulSand SOUL_SAND()
|
||||
@ -735,6 +749,13 @@ use function strtolower;
|
||||
* @method static Tripwire TRIPWIRE()
|
||||
* @method static TripwireHook TRIPWIRE_HOOK()
|
||||
* @method static Opaque TUFF()
|
||||
* @method static Opaque TUFF_BRICKS()
|
||||
* @method static Slab TUFF_BRICK_SLAB()
|
||||
* @method static Stair TUFF_BRICK_STAIRS()
|
||||
* @method static Wall TUFF_BRICK_WALL()
|
||||
* @method static Slab TUFF_SLAB()
|
||||
* @method static Stair TUFF_STAIRS()
|
||||
* @method static Wall TUFF_WALL()
|
||||
* @method static NetherVines TWISTING_VINES()
|
||||
* @method static UnderwaterTorch UNDERWATER_TORCH()
|
||||
* @method static Vine VINES()
|
||||
@ -826,6 +847,11 @@ final class VanillaBlocks{
|
||||
self::register("brown_mushroom", new BrownMushroom(new BID(Ids::BROWN_MUSHROOM), "Brown Mushroom", new Info(BreakInfo::instant(), [Tags::POTTABLE_PLANTS])));
|
||||
self::register("cactus", new Cactus(new BID(Ids::CACTUS), "Cactus", new Info(new BreakInfo(0.4), [Tags::POTTABLE_PLANTS])));
|
||||
self::register("cake", new Cake(new BID(Ids::CAKE), "Cake", new Info(new BreakInfo(0.5))));
|
||||
|
||||
$campfireBreakInfo = new Info(BreakInfo::axe(2.0));
|
||||
self::register("campfire", new Campfire(new BID(Ids::CAMPFIRE, TileCampfire::class), "Campfire", $campfireBreakInfo));
|
||||
self::register("soul_campfire", new SoulCampfire(new BID(Ids::SOUL_CAMPFIRE, TileCampfire::class), "Soul Campfire", $campfireBreakInfo));
|
||||
|
||||
self::register("carrots", new Carrot(new BID(Ids::CARROTS), "Carrot Block", new Info(BreakInfo::instant())));
|
||||
|
||||
$chestBreakInfo = new Info(BreakInfo::axe(2.5));
|
||||
@ -1261,6 +1287,7 @@ final class VanillaBlocks{
|
||||
self::registerBlocksR17();
|
||||
self::registerBlocksR18();
|
||||
self::registerMudBlocks();
|
||||
self::registerTuffBlocks();
|
||||
|
||||
self::registerCraftingTables();
|
||||
self::registerChorusBlocks();
|
||||
@ -1568,7 +1595,6 @@ final class VanillaBlocks{
|
||||
self::register("amethyst_cluster", new AmethystCluster(new BID(Ids::AMETHYST_CLUSTER), "Amethyst Cluster", $amethystInfo));
|
||||
|
||||
self::register("calcite", new Opaque(new BID(Ids::CALCITE), "Calcite", new Info(BreakInfo::pickaxe(0.75, ToolTier::WOOD))));
|
||||
self::register("tuff", new Opaque(new BID(Ids::TUFF), "Tuff", new Info(BreakInfo::pickaxe(1.5, ToolTier::WOOD, 30.0))));
|
||||
|
||||
self::register("raw_copper", new Opaque(new BID(Ids::RAW_COPPER), "Raw Copper Block", new Info(BreakInfo::pickaxe(5, ToolTier::STONE, 30.0))));
|
||||
self::register("raw_gold", new Opaque(new BID(Ids::RAW_GOLD), "Raw Gold Block", new Info(BreakInfo::pickaxe(5, ToolTier::IRON, 30.0))));
|
||||
@ -1621,9 +1647,16 @@ final class VanillaBlocks{
|
||||
self::register("lightning_rod", new LightningRod(new BID(Ids::LIGHTNING_ROD), "Lightning Rod", $copperBreakInfo));
|
||||
|
||||
self::register("copper", new Copper(new BID(Ids::COPPER), "Copper Block", $copperBreakInfo));
|
||||
self::register("chiseled_copper", new Copper(new BID(Ids::CHISELED_COPPER), "Chiseled Copper", $copperBreakInfo));
|
||||
self::register("copper_grate", new CopperGrate(new BID(Ids::COPPER_GRATE), "Copper Grate", $copperBreakInfo));
|
||||
self::register("cut_copper", new Copper(new BID(Ids::CUT_COPPER), "Cut Copper Block", $copperBreakInfo));
|
||||
self::register("cut_copper_slab", new CopperSlab(new BID(Ids::CUT_COPPER_SLAB), "Cut Copper Slab", $copperBreakInfo));
|
||||
self::register("cut_copper_stairs", new CopperStairs(new BID(Ids::CUT_COPPER_STAIRS), "Cut Copper Stairs", $copperBreakInfo));
|
||||
self::register("copper_bulb", new CopperBulb(new BID(Ids::COPPER_BULB), "Copper Bulb", $copperBreakInfo));
|
||||
|
||||
$copperDoorBreakInfo = new Info(BreakInfo::pickaxe(3.0, ToolTier::STONE, 30.0));
|
||||
self::register("copper_door", new CopperDoor(new BID(Ids::COPPER_DOOR), "Copper Door", $copperDoorBreakInfo));
|
||||
self::register("copper_trapdoor", new CopperTrapdoor(new BID(Ids::COPPER_TRAPDOOR), "Copper Trapdoor", $copperDoorBreakInfo));
|
||||
|
||||
$candleBreakInfo = new Info(new BreakInfo(0.1));
|
||||
self::register("candle", new Candle(new BID(Ids::CANDLE), "Candle", $candleBreakInfo));
|
||||
@ -1659,6 +1692,27 @@ final class VanillaBlocks{
|
||||
self::register("mud_brick_wall", new Wall(new BID(Ids::MUD_BRICK_WALL), "Mud Brick Wall", $mudBricksBreakInfo));
|
||||
}
|
||||
|
||||
private static function registerTuffBlocks() : void{
|
||||
$tuffBreakInfo = new Info(BreakInfo::pickaxe(1.5, ToolTier::WOOD, 30.0));
|
||||
|
||||
self::register("tuff", new Opaque(new BID(Ids::TUFF), "Tuff", $tuffBreakInfo));
|
||||
self::register("tuff_slab", new Slab(new BID(Ids::TUFF_SLAB), "Tuff", $tuffBreakInfo));
|
||||
self::register("tuff_stairs", new Stair(new BID(Ids::TUFF_STAIRS), "Tuff Stairs", $tuffBreakInfo));
|
||||
self::register("tuff_wall", new Wall(new BID(Ids::TUFF_WALL), "Tuff Wall", $tuffBreakInfo));
|
||||
self::register("chiseled_tuff", new Opaque(new BID(Ids::CHISELED_TUFF), "Chiseled Tuff", $tuffBreakInfo));
|
||||
|
||||
self::register("tuff_bricks", new Opaque(new BID(Ids::TUFF_BRICKS), "Tuff Bricks", $tuffBreakInfo));
|
||||
self::register("tuff_brick_slab", new Slab(new BID(Ids::TUFF_BRICK_SLAB), "Tuff Brick", $tuffBreakInfo));
|
||||
self::register("tuff_brick_stairs", new Stair(new BID(Ids::TUFF_BRICK_STAIRS), "Tuff Brick Stairs", $tuffBreakInfo));
|
||||
self::register("tuff_brick_wall", new Wall(new BID(Ids::TUFF_BRICK_WALL), "Tuff Brick Wall", $tuffBreakInfo));
|
||||
self::register("chiseled_tuff_bricks", new Opaque(new BID(Ids::CHISELED_TUFF_BRICKS), "Chiseled Tuff Bricks", $tuffBreakInfo));
|
||||
|
||||
self::register("polished_tuff", new Opaque(new BID(Ids::POLISHED_TUFF), "Polished Tuff", $tuffBreakInfo));
|
||||
self::register("polished_tuff_slab", new Slab(new BID(Ids::POLISHED_TUFF_SLAB), "Polished Tuff", $tuffBreakInfo));
|
||||
self::register("polished_tuff_stairs", new Stair(new BID(Ids::POLISHED_TUFF_STAIRS), "Polished Tuff Stairs", $tuffBreakInfo));
|
||||
self::register("polished_tuff_wall", new Wall(new BID(Ids::POLISHED_TUFF_WALL), "Polished Tuff Wall", $tuffBreakInfo));
|
||||
}
|
||||
|
||||
private static function registerCauldronBlocks() : void{
|
||||
$cauldronBreakInfo = new Info(BreakInfo::pickaxe(2, ToolTier::WOOD));
|
||||
|
||||
|
40
src/block/inventory/CampfireInventory.php
Normal file
40
src/block/inventory/CampfireInventory.php
Normal file
@ -0,0 +1,40 @@
|
||||
<?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\block\inventory;
|
||||
|
||||
use pocketmine\inventory\SimpleInventory;
|
||||
use pocketmine\world\Position;
|
||||
|
||||
class CampfireInventory extends SimpleInventory implements BlockInventory{
|
||||
use BlockInventoryTrait;
|
||||
|
||||
public function __construct(Position $holder){
|
||||
$this->holder = $holder;
|
||||
parent::__construct(4);
|
||||
}
|
||||
|
||||
public function getMaxStackSize() : int{
|
||||
return 1;
|
||||
}
|
||||
}
|
143
src/block/tile/Campfire.php
Normal file
143
src/block/tile/Campfire.php
Normal file
@ -0,0 +1,143 @@
|
||||
<?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\block\tile;
|
||||
|
||||
use pocketmine\block\Campfire as BlockCampfire;
|
||||
use pocketmine\block\inventory\CampfireInventory;
|
||||
use pocketmine\inventory\CallbackInventoryListener;
|
||||
use pocketmine\inventory\Inventory;
|
||||
use pocketmine\item\Item;
|
||||
use pocketmine\math\Vector3;
|
||||
use pocketmine\nbt\tag\CompoundTag;
|
||||
use pocketmine\nbt\tag\IntTag;
|
||||
use pocketmine\network\mcpe\convert\TypeConverter;
|
||||
use pocketmine\world\World;
|
||||
|
||||
class Campfire extends Spawnable implements Container{
|
||||
use ContainerTrait;
|
||||
|
||||
private const TAG_FIRST_INPUT_ITEM = "Item1"; //TAG_Compound
|
||||
private const TAG_SECOND_INPUT_ITEM = "Item2"; //TAG_Compound
|
||||
private const TAG_THIRD_INPUT_ITEM = "Item3"; //TAG_Compound
|
||||
private const TAG_FOURTH_INPUT_ITEM = "Item4"; //TAG_Compound
|
||||
|
||||
private const TAG_FIRST_COOKING_TIME = "ItemTime1"; //TAG_Int
|
||||
private const TAG_SECOND_COOKING_TIME = "ItemTime2"; //TAG_Int
|
||||
private const TAG_THIRD_COOKING_TIME = "ItemTime3"; //TAG_Int
|
||||
private const TAG_FOURTH_COOKING_TIME = "ItemTime4"; //TAG_Int
|
||||
|
||||
protected CampfireInventory $inventory;
|
||||
/** @var array<int, int> */
|
||||
private array $cookingTimes = [];
|
||||
|
||||
public function __construct(World $world, Vector3 $pos){
|
||||
parent::__construct($world, $pos);
|
||||
$this->inventory = new CampfireInventory($this->position);
|
||||
$this->inventory->getListeners()->add(CallbackInventoryListener::onAnyChange(
|
||||
static function(Inventory $unused) use ($world, $pos) : void{
|
||||
$block = $world->getBlock($pos);
|
||||
if($block instanceof BlockCampfire){
|
||||
$world->setBlock($pos, $block);
|
||||
}
|
||||
})
|
||||
);
|
||||
}
|
||||
|
||||
public function getInventory() : CampfireInventory{
|
||||
return $this->inventory;
|
||||
}
|
||||
|
||||
public function getRealInventory() : CampfireInventory{
|
||||
return $this->inventory;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return int[]
|
||||
* @phpstan-return array<int, int>
|
||||
*/
|
||||
public function getCookingTimes() : array{
|
||||
return $this->cookingTimes;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param int[] $cookingTimes
|
||||
* @phpstan-param array<int, int> $cookingTimes
|
||||
*/
|
||||
public function setCookingTimes(array $cookingTimes) : void{
|
||||
$this->cookingTimes = $cookingTimes;
|
||||
}
|
||||
|
||||
public function readSaveData(CompoundTag $nbt) : void{
|
||||
$items = [];
|
||||
$listeners = $this->inventory->getListeners()->toArray();
|
||||
$this->inventory->getListeners()->remove(...$listeners); //prevent any events being fired by initialization
|
||||
|
||||
foreach([
|
||||
[0, self::TAG_FIRST_INPUT_ITEM, self::TAG_FIRST_COOKING_TIME],
|
||||
[1, self::TAG_SECOND_INPUT_ITEM, self::TAG_SECOND_COOKING_TIME],
|
||||
[2, self::TAG_THIRD_INPUT_ITEM, self::TAG_THIRD_COOKING_TIME],
|
||||
[3, self::TAG_FOURTH_INPUT_ITEM, self::TAG_FOURTH_COOKING_TIME],
|
||||
] as [$slot, $itemTag, $cookingTimeTag]){
|
||||
if(($tag = $nbt->getTag($itemTag)) instanceof CompoundTag){
|
||||
$items[$slot] = Item::nbtDeserialize($tag);
|
||||
}
|
||||
if(($tag = $nbt->getTag($cookingTimeTag)) instanceof IntTag){
|
||||
$this->cookingTimes[$slot] = $tag->getValue();
|
||||
}
|
||||
}
|
||||
$this->inventory->setContents($items);
|
||||
$this->inventory->getListeners()->add(...$listeners);
|
||||
}
|
||||
|
||||
protected function writeSaveData(CompoundTag $nbt) : void{
|
||||
foreach([
|
||||
[0, self::TAG_FIRST_INPUT_ITEM, self::TAG_FIRST_COOKING_TIME],
|
||||
[1, self::TAG_SECOND_INPUT_ITEM, self::TAG_SECOND_COOKING_TIME],
|
||||
[2, self::TAG_THIRD_INPUT_ITEM, self::TAG_THIRD_COOKING_TIME],
|
||||
[3, self::TAG_FOURTH_INPUT_ITEM, self::TAG_FOURTH_COOKING_TIME],
|
||||
] as [$slot, $itemTag, $cookingTimeTag]){
|
||||
$item = $this->inventory->getItem($slot);
|
||||
if(!$item->isNull()){
|
||||
$nbt->setTag($itemTag, $item->nbtSerialize());
|
||||
if(isset($this->cookingTimes[$slot])){
|
||||
$nbt->setInt($cookingTimeTag, $this->cookingTimes[$slot]);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
protected function addAdditionalSpawnData(CompoundTag $nbt) : void{
|
||||
foreach([
|
||||
0 => self::TAG_FIRST_INPUT_ITEM,
|
||||
1 => self::TAG_SECOND_INPUT_ITEM,
|
||||
2 => self::TAG_THIRD_INPUT_ITEM,
|
||||
3 => self::TAG_FOURTH_INPUT_ITEM
|
||||
] as $slot => $tag){
|
||||
$item = $this->inventory->getItem($slot);
|
||||
if(!$item->isNull()){
|
||||
$nbt->setTag($tag, TypeConverter::getInstance()->getItemTranslator()->toNetworkNbt($item));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -40,8 +40,12 @@ use function count;
|
||||
class ChiseledBookshelf extends Tile implements Container{
|
||||
use ContainerTrait;
|
||||
|
||||
private const TAG_LAST_INTERACTED_SLOT = "LastInteractedSlot"; //TAG_Int
|
||||
|
||||
private SimpleInventory $inventory;
|
||||
|
||||
private ?ChiseledBookshelfSlot $lastInteractedSlot = null;
|
||||
|
||||
public function __construct(World $world, Vector3 $pos){
|
||||
parent::__construct($world, $pos);
|
||||
$this->inventory = new SimpleInventory(count(ChiseledBookshelfSlot::cases()));
|
||||
@ -55,12 +59,30 @@ class ChiseledBookshelf extends Tile implements Container{
|
||||
return $this->inventory;
|
||||
}
|
||||
|
||||
public function readSaveData(CompoundTag $nbt) : void{
|
||||
$this->loadItems($nbt);
|
||||
public function getLastInteractedSlot() : ?ChiseledBookshelfSlot{
|
||||
return $this->lastInteractedSlot;
|
||||
}
|
||||
|
||||
public function writeSaveData(CompoundTag $nbt) : void{
|
||||
public function setLastInteractedSlot(?ChiseledBookshelfSlot $lastInteractedSlot) : void{
|
||||
$this->lastInteractedSlot = $lastInteractedSlot;
|
||||
}
|
||||
|
||||
public function readSaveData(CompoundTag $nbt) : void{
|
||||
$this->loadItems($nbt);
|
||||
|
||||
$lastInteractedSlot = $nbt->getInt(self::TAG_LAST_INTERACTED_SLOT, 0);
|
||||
if($lastInteractedSlot !== 0){
|
||||
$this->lastInteractedSlot = ChiseledBookshelfSlot::tryFrom($lastInteractedSlot - 1);
|
||||
}
|
||||
}
|
||||
|
||||
protected function writeSaveData(CompoundTag $nbt) : void{
|
||||
$this->saveItems($nbt);
|
||||
|
||||
$nbt->setInt(self::TAG_LAST_INTERACTED_SLOT, $this->lastInteractedSlot !== null ?
|
||||
$this->lastInteractedSlot->value + 1 :
|
||||
0
|
||||
);
|
||||
}
|
||||
|
||||
protected function loadItems(CompoundTag $tag) : void{
|
||||
|
@ -57,6 +57,7 @@ final class TileFactory{
|
||||
$this->register(Bell::class, ["Bell", "minecraft:bell"]);
|
||||
$this->register(BlastFurnace::class, ["BlastFurnace", "minecraft:blast_furnace"]);
|
||||
$this->register(BrewingStand::class, ["BrewingStand", "minecraft:brewing_stand"]);
|
||||
$this->register(Campfire::class, ["Campfire", "minecraft:campfire"]);
|
||||
$this->register(Cauldron::class, ["Cauldron", "minecraft:cauldron"]);
|
||||
$this->register(Chest::class, ["Chest", "minecraft:chest"]);
|
||||
$this->register(ChiseledBookshelf::class, ["ChiseledBookshelf", "minecraft:chiseled_bookshelf"]);
|
||||
@ -79,7 +80,6 @@ final class TileFactory{
|
||||
$this->register(MobHead::class, ["Skull", "minecraft:skull"]);
|
||||
$this->register(GlowingItemFrame::class, ["GlowItemFrame"]);
|
||||
|
||||
//TODO: Campfire
|
||||
//TODO: ChalkboardBlock
|
||||
//TODO: ChemistryTable
|
||||
//TODO: CommandBlock
|
||||
|
@ -81,10 +81,12 @@ enum BannerPatternType{
|
||||
case DIAGONAL_RIGHT;
|
||||
case DIAGONAL_UP_LEFT;
|
||||
case DIAGONAL_UP_RIGHT;
|
||||
case FLOW;
|
||||
case FLOWER;
|
||||
case GLOBE;
|
||||
case GRADIENT;
|
||||
case GRADIENT_UP;
|
||||
case GUSTER;
|
||||
case HALF_HORIZONTAL;
|
||||
case HALF_HORIZONTAL_BOTTOM;
|
||||
case HALF_VERTICAL;
|
||||
|
38
src/block/utils/CopperMaterial.php
Normal file
38
src/block/utils/CopperMaterial.php
Normal file
@ -0,0 +1,38 @@
|
||||
<?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\block\utils;
|
||||
|
||||
/**
|
||||
* Represents copper blocks that have oxidized and waxed variations.
|
||||
*/
|
||||
interface CopperMaterial{
|
||||
|
||||
public function getOxidation() : CopperOxidation;
|
||||
|
||||
public function setOxidation(CopperOxidation $oxidation) : CopperMaterial;
|
||||
|
||||
public function isWaxed() : bool;
|
||||
|
||||
public function setWaxed(bool $waxed) : CopperMaterial;
|
||||
}
|
@ -275,7 +275,8 @@ final class CraftingManagerFromDataHelper{
|
||||
"furnace" => FurnaceType::FURNACE,
|
||||
"blast_furnace" => FurnaceType::BLAST_FURNACE,
|
||||
"smoker" => FurnaceType::SMOKER,
|
||||
//TODO: campfire
|
||||
"campfire" => FurnaceType::CAMPFIRE,
|
||||
"soul_campfire" => FurnaceType::SOUL_CAMPFIRE,
|
||||
default => null
|
||||
};
|
||||
if($furnaceType === null){
|
||||
|
@ -25,6 +25,7 @@ namespace pocketmine\crafting;
|
||||
|
||||
use pocketmine\utils\LegacyEnumShimTrait;
|
||||
use pocketmine\world\sound\BlastFurnaceSound;
|
||||
use pocketmine\world\sound\CampfireSound;
|
||||
use pocketmine\world\sound\FurnaceSound;
|
||||
use pocketmine\world\sound\SmokerSound;
|
||||
use pocketmine\world\sound\Sound;
|
||||
@ -35,8 +36,10 @@ use function spl_object_id;
|
||||
* These are retained for backwards compatibility only.
|
||||
*
|
||||
* @method static FurnaceType BLAST_FURNACE()
|
||||
* @method static FurnaceType CAMPFIRE()
|
||||
* @method static FurnaceType FURNACE()
|
||||
* @method static FurnaceType SMOKER()
|
||||
* @method static FurnaceType SOUL_CAMPFIRE()
|
||||
*
|
||||
* @phpstan-type TMetadata array{0: int, 1: Sound}
|
||||
*/
|
||||
@ -46,6 +49,8 @@ enum FurnaceType{
|
||||
case FURNACE;
|
||||
case BLAST_FURNACE;
|
||||
case SMOKER;
|
||||
case CAMPFIRE;
|
||||
case SOUL_CAMPFIRE;
|
||||
|
||||
/**
|
||||
* @phpstan-return TMetadata
|
||||
@ -58,6 +63,7 @@ enum FurnaceType{
|
||||
self::FURNACE => [200, new FurnaceSound()],
|
||||
self::BLAST_FURNACE => [100, new BlastFurnaceSound()],
|
||||
self::SMOKER => [100, new SmokerSound()],
|
||||
self::CAMPFIRE, self::SOUL_CAMPFIRE => [600, new CampfireSound()]
|
||||
};
|
||||
}
|
||||
|
||||
|
@ -56,9 +56,11 @@ final class BannerPatternTypeIdMap{
|
||||
BannerPatternType::DIAGONAL_UP_LEFT => "ld",
|
||||
BannerPatternType::DIAGONAL_UP_RIGHT => "rud",
|
||||
BannerPatternType::FLOWER => "flo",
|
||||
BannerPatternType::FLOW => "flw",
|
||||
BannerPatternType::GLOBE => "glb",
|
||||
BannerPatternType::GRADIENT => "gra",
|
||||
BannerPatternType::GRADIENT_UP => "gru",
|
||||
BannerPatternType::GUSTER => "gus",
|
||||
BannerPatternType::HALF_HORIZONTAL => "hh",
|
||||
BannerPatternType::HALF_HORIZONTAL_BOTTOM => "hhb",
|
||||
BannerPatternType::HALF_VERTICAL => "vh",
|
||||
|
@ -35,6 +35,7 @@ final class BedrockDataFiles{
|
||||
public const BIOME_DEFINITIONS_FULL_NBT = BEDROCK_DATA_PATH . '/biome_definitions_full.nbt';
|
||||
public const BIOME_ID_MAP_JSON = BEDROCK_DATA_PATH . '/biome_id_map.json';
|
||||
public const BLOCK_ID_TO_ITEM_ID_MAP_JSON = BEDROCK_DATA_PATH . '/block_id_to_item_id_map.json';
|
||||
public const BLOCK_PROPERTIES_TABLE_JSON = BEDROCK_DATA_PATH . '/block_properties_table.json';
|
||||
public const BLOCK_STATE_META_MAP_JSON = BEDROCK_DATA_PATH . '/block_state_meta_map.json';
|
||||
public const CANONICAL_BLOCK_STATES_NBT = BEDROCK_DATA_PATH . '/canonical_block_states.nbt';
|
||||
public const COMMAND_ARG_TYPES_JSON = BEDROCK_DATA_PATH . '/command_arg_types.json';
|
||||
|
@ -43,6 +43,7 @@ final class EnchantmentIdMap{
|
||||
$this->register(EnchantmentIds::PROJECTILE_PROTECTION, VanillaEnchantments::PROJECTILE_PROTECTION());
|
||||
$this->register(EnchantmentIds::THORNS, VanillaEnchantments::THORNS());
|
||||
$this->register(EnchantmentIds::RESPIRATION, VanillaEnchantments::RESPIRATION());
|
||||
$this->register(EnchantmentIds::AQUA_AFFINITY, VanillaEnchantments::AQUA_AFFINITY());
|
||||
|
||||
$this->register(EnchantmentIds::SHARPNESS, VanillaEnchantments::SHARPNESS());
|
||||
//TODO: smite, bane of arthropods (these don't make sense now because their applicable mobs don't exist yet)
|
||||
|
@ -38,12 +38,15 @@ use function implode;
|
||||
final class BlockStateData{
|
||||
/**
|
||||
* Bedrock version of the most recent backwards-incompatible change to blockstates.
|
||||
*
|
||||
* This is *not* the same as current game version. It should match the numbers in the
|
||||
* newest blockstate upgrade schema used in BedrockBlockUpgradeSchema.
|
||||
*/
|
||||
public const CURRENT_VERSION =
|
||||
(1 << 24) | //major
|
||||
(21 << 16) | //minor
|
||||
(0 << 8) | //patch
|
||||
(3); //revision
|
||||
(40 << 8) | //patch
|
||||
(1); //revision
|
||||
|
||||
public const TAG_NAME = "name";
|
||||
public const TAG_STATES = "states";
|
||||
|
@ -34,7 +34,6 @@ final class BlockStateNames{
|
||||
public const ACTIVE = "active";
|
||||
public const AGE = "age";
|
||||
public const AGE_BIT = "age_bit";
|
||||
public const ALLOW_UNDERWATER_BIT = "allow_underwater_bit";
|
||||
public const ATTACHED_BIT = "attached_bit";
|
||||
public const ATTACHMENT = "attachment";
|
||||
public const BAMBOO_LEAF_SIZE = "bamboo_leaf_size";
|
||||
@ -42,7 +41,6 @@ final class BlockStateNames{
|
||||
public const BIG_DRIPLEAF_HEAD = "big_dripleaf_head";
|
||||
public const BIG_DRIPLEAF_TILT = "big_dripleaf_tilt";
|
||||
public const BITE_COUNTER = "bite_counter";
|
||||
public const BLOCK_LIGHT_LEVEL = "block_light_level";
|
||||
public const BLOOM = "bloom";
|
||||
public const BOOKS_STORED = "books_stored";
|
||||
public const BREWING_STAND_SLOT_A_BIT = "brewing_stand_slot_a_bit";
|
||||
@ -53,23 +51,17 @@ final class BlockStateNames{
|
||||
public const CAN_SUMMON = "can_summon";
|
||||
public const CANDLES = "candles";
|
||||
public const CAULDRON_LIQUID = "cauldron_liquid";
|
||||
public const CHEMISTRY_TABLE_TYPE = "chemistry_table_type";
|
||||
public const CHISEL_TYPE = "chisel_type";
|
||||
public const CLUSTER_COUNT = "cluster_count";
|
||||
public const COLOR_BIT = "color_bit";
|
||||
public const COMPOSTER_FILL_LEVEL = "composter_fill_level";
|
||||
public const CONDITIONAL_BIT = "conditional_bit";
|
||||
public const CORAL_DIRECTION = "coral_direction";
|
||||
public const CORAL_FAN_DIRECTION = "coral_fan_direction";
|
||||
public const CORAL_HANG_TYPE_BIT = "coral_hang_type_bit";
|
||||
public const COVERED_BIT = "covered_bit";
|
||||
public const CRACKED_STATE = "cracked_state";
|
||||
public const CRAFTING = "crafting";
|
||||
public const DAMAGE = "damage";
|
||||
public const DEAD_BIT = "dead_bit";
|
||||
public const DEPRECATED = "deprecated";
|
||||
public const DIRECTION = "direction";
|
||||
public const DIRT_TYPE = "dirt_type";
|
||||
public const DISARMED_BIT = "disarmed_bit";
|
||||
public const DOOR_HINGE_BIT = "door_hinge_bit";
|
||||
public const DRAG_DOWN = "drag_down";
|
||||
@ -100,7 +92,6 @@ final class BlockStateNames{
|
||||
public const MC_FACING_DIRECTION = "minecraft:facing_direction";
|
||||
public const MC_VERTICAL_HALF = "minecraft:vertical_half";
|
||||
public const MOISTURIZED_AMOUNT = "moisturized_amount";
|
||||
public const MONSTER_EGG_STONE_TYPE = "monster_egg_stone_type";
|
||||
public const MULTI_FACE_DIRECTION_BITS = "multi_face_direction_bits";
|
||||
public const OCCUPIED_BIT = "occupied_bit";
|
||||
public const OMINOUS = "ominous";
|
||||
@ -112,7 +103,6 @@ final class BlockStateNames{
|
||||
public const PILLAR_AXIS = "pillar_axis";
|
||||
public const PORTAL_AXIS = "portal_axis";
|
||||
public const POWERED_BIT = "powered_bit";
|
||||
public const PRISMARINE_BLOCK_TYPE = "prismarine_block_type";
|
||||
public const PROPAGULE_STAGE = "propagule_stage";
|
||||
public const RAIL_DATA_BIT = "rail_data_bit";
|
||||
public const RAIL_DIRECTION = "rail_direction";
|
||||
@ -120,21 +110,11 @@ final class BlockStateNames{
|
||||
public const REPEATER_DELAY = "repeater_delay";
|
||||
public const RESPAWN_ANCHOR_CHARGE = "respawn_anchor_charge";
|
||||
public const ROTATION = "rotation";
|
||||
public const SAND_STONE_TYPE = "sand_stone_type";
|
||||
public const SAND_TYPE = "sand_type";
|
||||
public const SCULK_SENSOR_PHASE = "sculk_sensor_phase";
|
||||
public const SEA_GRASS_TYPE = "sea_grass_type";
|
||||
public const SPONGE_TYPE = "sponge_type";
|
||||
public const STABILITY = "stability";
|
||||
public const STABILITY_CHECK = "stability_check";
|
||||
public const STONE_BRICK_TYPE = "stone_brick_type";
|
||||
public const STONE_SLAB_TYPE = "stone_slab_type";
|
||||
public const STONE_SLAB_TYPE_2 = "stone_slab_type_2";
|
||||
public const STONE_SLAB_TYPE_3 = "stone_slab_type_3";
|
||||
public const STONE_SLAB_TYPE_4 = "stone_slab_type_4";
|
||||
public const STRIPPED_BIT = "stripped_bit";
|
||||
public const STRUCTURE_BLOCK_TYPE = "structure_block_type";
|
||||
public const STRUCTURE_VOID_TYPE = "structure_void_type";
|
||||
public const SUSPENDED_BIT = "suspended_bit";
|
||||
public const TOGGLE_BIT = "toggle_bit";
|
||||
public const TORCH_FACING_DIRECTION = "torch_facing_direction";
|
||||
@ -147,7 +127,6 @@ final class BlockStateNames{
|
||||
public const UPSIDE_DOWN_BIT = "upside_down_bit";
|
||||
public const VAULT_STATE = "vault_state";
|
||||
public const VINE_DIRECTION_BITS = "vine_direction_bits";
|
||||
public const WALL_BLOCK_TYPE = "wall_block_type";
|
||||
public const WALL_CONNECTION_TYPE_EAST = "wall_connection_type_east";
|
||||
public const WALL_CONNECTION_TYPE_NORTH = "wall_connection_type_north";
|
||||
public const WALL_CONNECTION_TYPE_SOUTH = "wall_connection_type_south";
|
||||
|
@ -52,28 +52,10 @@ final class BlockStateStringValues{
|
||||
public const CAULDRON_LIQUID_POWDER_SNOW = "powder_snow";
|
||||
public const CAULDRON_LIQUID_WATER = "water";
|
||||
|
||||
public const CHEMISTRY_TABLE_TYPE_COMPOUND_CREATOR = "compound_creator";
|
||||
public const CHEMISTRY_TABLE_TYPE_ELEMENT_CONSTRUCTOR = "element_constructor";
|
||||
public const CHEMISTRY_TABLE_TYPE_LAB_TABLE = "lab_table";
|
||||
public const CHEMISTRY_TABLE_TYPE_MATERIAL_REDUCER = "material_reducer";
|
||||
|
||||
public const CHISEL_TYPE_CHISELED = "chiseled";
|
||||
public const CHISEL_TYPE_DEFAULT = "default";
|
||||
public const CHISEL_TYPE_LINES = "lines";
|
||||
public const CHISEL_TYPE_SMOOTH = "smooth";
|
||||
|
||||
public const CRACKED_STATE_CRACKED = "cracked";
|
||||
public const CRACKED_STATE_MAX_CRACKED = "max_cracked";
|
||||
public const CRACKED_STATE_NO_CRACKS = "no_cracks";
|
||||
|
||||
public const DAMAGE_BROKEN = "broken";
|
||||
public const DAMAGE_SLIGHTLY_DAMAGED = "slightly_damaged";
|
||||
public const DAMAGE_UNDAMAGED = "undamaged";
|
||||
public const DAMAGE_VERY_DAMAGED = "very_damaged";
|
||||
|
||||
public const DIRT_TYPE_COARSE = "coarse";
|
||||
public const DIRT_TYPE_NORMAL = "normal";
|
||||
|
||||
public const DRIPSTONE_THICKNESS_BASE = "base";
|
||||
public const DRIPSTONE_THICKNESS_FRUSTUM = "frustum";
|
||||
public const DRIPSTONE_THICKNESS_MERGE = "merge";
|
||||
@ -111,13 +93,6 @@ final class BlockStateStringValues{
|
||||
public const MC_VERTICAL_HALF_BOTTOM = "bottom";
|
||||
public const MC_VERTICAL_HALF_TOP = "top";
|
||||
|
||||
public const MONSTER_EGG_STONE_TYPE_CHISELED_STONE_BRICK = "chiseled_stone_brick";
|
||||
public const MONSTER_EGG_STONE_TYPE_COBBLESTONE = "cobblestone";
|
||||
public const MONSTER_EGG_STONE_TYPE_CRACKED_STONE_BRICK = "cracked_stone_brick";
|
||||
public const MONSTER_EGG_STONE_TYPE_MOSSY_STONE_BRICK = "mossy_stone_brick";
|
||||
public const MONSTER_EGG_STONE_TYPE_STONE = "stone";
|
||||
public const MONSTER_EGG_STONE_TYPE_STONE_BRICK = "stone_brick";
|
||||
|
||||
public const ORIENTATION_DOWN_EAST = "down_east";
|
||||
public const ORIENTATION_DOWN_NORTH = "down_north";
|
||||
public const ORIENTATION_DOWN_SOUTH = "down_south";
|
||||
@ -139,64 +114,10 @@ final class BlockStateStringValues{
|
||||
public const PORTAL_AXIS_X = "x";
|
||||
public const PORTAL_AXIS_Z = "z";
|
||||
|
||||
public const PRISMARINE_BLOCK_TYPE_BRICKS = "bricks";
|
||||
public const PRISMARINE_BLOCK_TYPE_DARK = "dark";
|
||||
public const PRISMARINE_BLOCK_TYPE_DEFAULT = "default";
|
||||
|
||||
public const SAND_STONE_TYPE_CUT = "cut";
|
||||
public const SAND_STONE_TYPE_DEFAULT = "default";
|
||||
public const SAND_STONE_TYPE_HEIROGLYPHS = "heiroglyphs";
|
||||
public const SAND_STONE_TYPE_SMOOTH = "smooth";
|
||||
|
||||
public const SAND_TYPE_NORMAL = "normal";
|
||||
public const SAND_TYPE_RED = "red";
|
||||
|
||||
public const SEA_GRASS_TYPE_DEFAULT = "default";
|
||||
public const SEA_GRASS_TYPE_DOUBLE_BOT = "double_bot";
|
||||
public const SEA_GRASS_TYPE_DOUBLE_TOP = "double_top";
|
||||
|
||||
public const SPONGE_TYPE_DRY = "dry";
|
||||
public const SPONGE_TYPE_WET = "wet";
|
||||
|
||||
public const STONE_BRICK_TYPE_CHISELED = "chiseled";
|
||||
public const STONE_BRICK_TYPE_CRACKED = "cracked";
|
||||
public const STONE_BRICK_TYPE_DEFAULT = "default";
|
||||
public const STONE_BRICK_TYPE_MOSSY = "mossy";
|
||||
public const STONE_BRICK_TYPE_SMOOTH = "smooth";
|
||||
|
||||
public const STONE_SLAB_TYPE_BRICK = "brick";
|
||||
public const STONE_SLAB_TYPE_COBBLESTONE = "cobblestone";
|
||||
public const STONE_SLAB_TYPE_NETHER_BRICK = "nether_brick";
|
||||
public const STONE_SLAB_TYPE_QUARTZ = "quartz";
|
||||
public const STONE_SLAB_TYPE_SANDSTONE = "sandstone";
|
||||
public const STONE_SLAB_TYPE_SMOOTH_STONE = "smooth_stone";
|
||||
public const STONE_SLAB_TYPE_STONE_BRICK = "stone_brick";
|
||||
public const STONE_SLAB_TYPE_WOOD = "wood";
|
||||
|
||||
public const STONE_SLAB_TYPE_2_MOSSY_COBBLESTONE = "mossy_cobblestone";
|
||||
public const STONE_SLAB_TYPE_2_PRISMARINE_BRICK = "prismarine_brick";
|
||||
public const STONE_SLAB_TYPE_2_PRISMARINE_DARK = "prismarine_dark";
|
||||
public const STONE_SLAB_TYPE_2_PRISMARINE_ROUGH = "prismarine_rough";
|
||||
public const STONE_SLAB_TYPE_2_PURPUR = "purpur";
|
||||
public const STONE_SLAB_TYPE_2_RED_NETHER_BRICK = "red_nether_brick";
|
||||
public const STONE_SLAB_TYPE_2_RED_SANDSTONE = "red_sandstone";
|
||||
public const STONE_SLAB_TYPE_2_SMOOTH_SANDSTONE = "smooth_sandstone";
|
||||
|
||||
public const STONE_SLAB_TYPE_3_ANDESITE = "andesite";
|
||||
public const STONE_SLAB_TYPE_3_DIORITE = "diorite";
|
||||
public const STONE_SLAB_TYPE_3_END_STONE_BRICK = "end_stone_brick";
|
||||
public const STONE_SLAB_TYPE_3_GRANITE = "granite";
|
||||
public const STONE_SLAB_TYPE_3_POLISHED_ANDESITE = "polished_andesite";
|
||||
public const STONE_SLAB_TYPE_3_POLISHED_DIORITE = "polished_diorite";
|
||||
public const STONE_SLAB_TYPE_3_POLISHED_GRANITE = "polished_granite";
|
||||
public const STONE_SLAB_TYPE_3_SMOOTH_RED_SANDSTONE = "smooth_red_sandstone";
|
||||
|
||||
public const STONE_SLAB_TYPE_4_CUT_RED_SANDSTONE = "cut_red_sandstone";
|
||||
public const STONE_SLAB_TYPE_4_CUT_SANDSTONE = "cut_sandstone";
|
||||
public const STONE_SLAB_TYPE_4_MOSSY_STONE_BRICK = "mossy_stone_brick";
|
||||
public const STONE_SLAB_TYPE_4_SMOOTH_QUARTZ = "smooth_quartz";
|
||||
public const STONE_SLAB_TYPE_4_STONE = "stone";
|
||||
|
||||
public const STRUCTURE_BLOCK_TYPE_CORNER = "corner";
|
||||
public const STRUCTURE_BLOCK_TYPE_DATA = "data";
|
||||
public const STRUCTURE_BLOCK_TYPE_EXPORT = "export";
|
||||
@ -204,9 +125,6 @@ final class BlockStateStringValues{
|
||||
public const STRUCTURE_BLOCK_TYPE_LOAD = "load";
|
||||
public const STRUCTURE_BLOCK_TYPE_SAVE = "save";
|
||||
|
||||
public const STRUCTURE_VOID_TYPE_AIR = "air";
|
||||
public const STRUCTURE_VOID_TYPE_VOID = "void";
|
||||
|
||||
public const TORCH_FACING_DIRECTION_EAST = "east";
|
||||
public const TORCH_FACING_DIRECTION_NORTH = "north";
|
||||
public const TORCH_FACING_DIRECTION_SOUTH = "south";
|
||||
@ -224,21 +142,6 @@ final class BlockStateStringValues{
|
||||
public const VAULT_STATE_INACTIVE = "inactive";
|
||||
public const VAULT_STATE_UNLOCKING = "unlocking";
|
||||
|
||||
public const WALL_BLOCK_TYPE_ANDESITE = "andesite";
|
||||
public const WALL_BLOCK_TYPE_BRICK = "brick";
|
||||
public const WALL_BLOCK_TYPE_COBBLESTONE = "cobblestone";
|
||||
public const WALL_BLOCK_TYPE_DIORITE = "diorite";
|
||||
public const WALL_BLOCK_TYPE_END_BRICK = "end_brick";
|
||||
public const WALL_BLOCK_TYPE_GRANITE = "granite";
|
||||
public const WALL_BLOCK_TYPE_MOSSY_COBBLESTONE = "mossy_cobblestone";
|
||||
public const WALL_BLOCK_TYPE_MOSSY_STONE_BRICK = "mossy_stone_brick";
|
||||
public const WALL_BLOCK_TYPE_NETHER_BRICK = "nether_brick";
|
||||
public const WALL_BLOCK_TYPE_PRISMARINE = "prismarine";
|
||||
public const WALL_BLOCK_TYPE_RED_NETHER_BRICK = "red_nether_brick";
|
||||
public const WALL_BLOCK_TYPE_RED_SANDSTONE = "red_sandstone";
|
||||
public const WALL_BLOCK_TYPE_SANDSTONE = "sandstone";
|
||||
public const WALL_BLOCK_TYPE_STONE_BRICK = "stone_brick";
|
||||
|
||||
public const WALL_CONNECTION_TYPE_EAST_NONE = "none";
|
||||
public const WALL_CONNECTION_TYPE_EAST_SHORT = "short";
|
||||
public const WALL_CONNECTION_TYPE_EAST_TALL = "tall";
|
||||
|
@ -56,7 +56,10 @@ final class BlockTypeNames{
|
||||
public const AMETHYST_CLUSTER = "minecraft:amethyst_cluster";
|
||||
public const ANCIENT_DEBRIS = "minecraft:ancient_debris";
|
||||
public const ANDESITE = "minecraft:andesite";
|
||||
public const ANDESITE_DOUBLE_SLAB = "minecraft:andesite_double_slab";
|
||||
public const ANDESITE_SLAB = "minecraft:andesite_slab";
|
||||
public const ANDESITE_STAIRS = "minecraft:andesite_stairs";
|
||||
public const ANDESITE_WALL = "minecraft:andesite_wall";
|
||||
public const ANVIL = "minecraft:anvil";
|
||||
public const AZALEA = "minecraft:azalea";
|
||||
public const AZALEA_LEAVES = "minecraft:azalea_leaves";
|
||||
@ -146,10 +149,13 @@ final class BlockTypeNames{
|
||||
public const BRAIN_CORAL = "minecraft:brain_coral";
|
||||
public const BRAIN_CORAL_BLOCK = "minecraft:brain_coral_block";
|
||||
public const BRAIN_CORAL_FAN = "minecraft:brain_coral_fan";
|
||||
public const BRAIN_CORAL_WALL_FAN = "minecraft:brain_coral_wall_fan";
|
||||
public const BREWING_STAND = "minecraft:brewing_stand";
|
||||
public const BRICK_BLOCK = "minecraft:brick_block";
|
||||
public const BRICK_DOUBLE_SLAB = "minecraft:brick_double_slab";
|
||||
public const BRICK_SLAB = "minecraft:brick_slab";
|
||||
public const BRICK_STAIRS = "minecraft:brick_stairs";
|
||||
public const BRICK_WALL = "minecraft:brick_wall";
|
||||
public const BROWN_CANDLE = "minecraft:brown_candle";
|
||||
public const BROWN_CANDLE_CAKE = "minecraft:brown_candle_cake";
|
||||
public const BROWN_CARPET = "minecraft:brown_carpet";
|
||||
@ -167,6 +173,7 @@ final class BlockTypeNames{
|
||||
public const BUBBLE_CORAL = "minecraft:bubble_coral";
|
||||
public const BUBBLE_CORAL_BLOCK = "minecraft:bubble_coral_block";
|
||||
public const BUBBLE_CORAL_FAN = "minecraft:bubble_coral_fan";
|
||||
public const BUBBLE_CORAL_WALL_FAN = "minecraft:bubble_coral_wall_fan";
|
||||
public const BUDDING_AMETHYST = "minecraft:budding_amethyst";
|
||||
public const CACTUS = "minecraft:cactus";
|
||||
public const CAKE = "minecraft:cake";
|
||||
@ -186,7 +193,6 @@ final class BlockTypeNames{
|
||||
public const CHAIN = "minecraft:chain";
|
||||
public const CHAIN_COMMAND_BLOCK = "minecraft:chain_command_block";
|
||||
public const CHEMICAL_HEAT = "minecraft:chemical_heat";
|
||||
public const CHEMISTRY_TABLE = "minecraft:chemistry_table";
|
||||
public const CHERRY_BUTTON = "minecraft:cherry_button";
|
||||
public const CHERRY_DOOR = "minecraft:cherry_door";
|
||||
public const CHERRY_DOUBLE_SLAB = "minecraft:cherry_double_slab";
|
||||
@ -205,11 +211,16 @@ final class BlockTypeNames{
|
||||
public const CHERRY_WALL_SIGN = "minecraft:cherry_wall_sign";
|
||||
public const CHERRY_WOOD = "minecraft:cherry_wood";
|
||||
public const CHEST = "minecraft:chest";
|
||||
public const CHIPPED_ANVIL = "minecraft:chipped_anvil";
|
||||
public const CHISELED_BOOKSHELF = "minecraft:chiseled_bookshelf";
|
||||
public const CHISELED_COPPER = "minecraft:chiseled_copper";
|
||||
public const CHISELED_DEEPSLATE = "minecraft:chiseled_deepslate";
|
||||
public const CHISELED_NETHER_BRICKS = "minecraft:chiseled_nether_bricks";
|
||||
public const CHISELED_POLISHED_BLACKSTONE = "minecraft:chiseled_polished_blackstone";
|
||||
public const CHISELED_QUARTZ_BLOCK = "minecraft:chiseled_quartz_block";
|
||||
public const CHISELED_RED_SANDSTONE = "minecraft:chiseled_red_sandstone";
|
||||
public const CHISELED_SANDSTONE = "minecraft:chiseled_sandstone";
|
||||
public const CHISELED_STONE_BRICKS = "minecraft:chiseled_stone_bricks";
|
||||
public const CHISELED_TUFF = "minecraft:chiseled_tuff";
|
||||
public const CHISELED_TUFF_BRICKS = "minecraft:chiseled_tuff_bricks";
|
||||
public const CHORUS_FLOWER = "minecraft:chorus_flower";
|
||||
@ -218,19 +229,24 @@ final class BlockTypeNames{
|
||||
public const CLIENT_REQUEST_PLACEHOLDER_BLOCK = "minecraft:client_request_placeholder_block";
|
||||
public const COAL_BLOCK = "minecraft:coal_block";
|
||||
public const COAL_ORE = "minecraft:coal_ore";
|
||||
public const COARSE_DIRT = "minecraft:coarse_dirt";
|
||||
public const COBBLED_DEEPSLATE = "minecraft:cobbled_deepslate";
|
||||
public const COBBLED_DEEPSLATE_DOUBLE_SLAB = "minecraft:cobbled_deepslate_double_slab";
|
||||
public const COBBLED_DEEPSLATE_SLAB = "minecraft:cobbled_deepslate_slab";
|
||||
public const COBBLED_DEEPSLATE_STAIRS = "minecraft:cobbled_deepslate_stairs";
|
||||
public const COBBLED_DEEPSLATE_WALL = "minecraft:cobbled_deepslate_wall";
|
||||
public const COBBLESTONE = "minecraft:cobblestone";
|
||||
public const COBBLESTONE_DOUBLE_SLAB = "minecraft:cobblestone_double_slab";
|
||||
public const COBBLESTONE_SLAB = "minecraft:cobblestone_slab";
|
||||
public const COBBLESTONE_WALL = "minecraft:cobblestone_wall";
|
||||
public const COCOA = "minecraft:cocoa";
|
||||
public const COLORED_TORCH_BP = "minecraft:colored_torch_bp";
|
||||
public const COLORED_TORCH_RG = "minecraft:colored_torch_rg";
|
||||
public const COLORED_TORCH_BLUE = "minecraft:colored_torch_blue";
|
||||
public const COLORED_TORCH_GREEN = "minecraft:colored_torch_green";
|
||||
public const COLORED_TORCH_PURPLE = "minecraft:colored_torch_purple";
|
||||
public const COLORED_TORCH_RED = "minecraft:colored_torch_red";
|
||||
public const COMMAND_BLOCK = "minecraft:command_block";
|
||||
public const COMPOSTER = "minecraft:composter";
|
||||
public const COMPOUND_CREATOR = "minecraft:compound_creator";
|
||||
public const CONDUIT = "minecraft:conduit";
|
||||
public const COPPER_BLOCK = "minecraft:copper_block";
|
||||
public const COPPER_BULB = "minecraft:copper_bulb";
|
||||
@ -238,16 +254,15 @@ final class BlockTypeNames{
|
||||
public const COPPER_GRATE = "minecraft:copper_grate";
|
||||
public const COPPER_ORE = "minecraft:copper_ore";
|
||||
public const COPPER_TRAPDOOR = "minecraft:copper_trapdoor";
|
||||
public const CORAL_FAN_HANG = "minecraft:coral_fan_hang";
|
||||
public const CORAL_FAN_HANG2 = "minecraft:coral_fan_hang2";
|
||||
public const CORAL_FAN_HANG3 = "minecraft:coral_fan_hang3";
|
||||
public const CORNFLOWER = "minecraft:cornflower";
|
||||
public const CRACKED_DEEPSLATE_BRICKS = "minecraft:cracked_deepslate_bricks";
|
||||
public const CRACKED_DEEPSLATE_TILES = "minecraft:cracked_deepslate_tiles";
|
||||
public const CRACKED_NETHER_BRICKS = "minecraft:cracked_nether_bricks";
|
||||
public const CRACKED_POLISHED_BLACKSTONE_BRICKS = "minecraft:cracked_polished_blackstone_bricks";
|
||||
public const CRACKED_STONE_BRICKS = "minecraft:cracked_stone_bricks";
|
||||
public const CRAFTER = "minecraft:crafter";
|
||||
public const CRAFTING_TABLE = "minecraft:crafting_table";
|
||||
public const CREEPER_HEAD = "minecraft:creeper_head";
|
||||
public const CRIMSON_BUTTON = "minecraft:crimson_button";
|
||||
public const CRIMSON_DOOR = "minecraft:crimson_door";
|
||||
public const CRIMSON_DOUBLE_SLAB = "minecraft:crimson_double_slab";
|
||||
@ -270,6 +285,12 @@ final class BlockTypeNames{
|
||||
public const CUT_COPPER = "minecraft:cut_copper";
|
||||
public const CUT_COPPER_SLAB = "minecraft:cut_copper_slab";
|
||||
public const CUT_COPPER_STAIRS = "minecraft:cut_copper_stairs";
|
||||
public const CUT_RED_SANDSTONE = "minecraft:cut_red_sandstone";
|
||||
public const CUT_RED_SANDSTONE_DOUBLE_SLAB = "minecraft:cut_red_sandstone_double_slab";
|
||||
public const CUT_RED_SANDSTONE_SLAB = "minecraft:cut_red_sandstone_slab";
|
||||
public const CUT_SANDSTONE = "minecraft:cut_sandstone";
|
||||
public const CUT_SANDSTONE_DOUBLE_SLAB = "minecraft:cut_sandstone_double_slab";
|
||||
public const CUT_SANDSTONE_SLAB = "minecraft:cut_sandstone_slab";
|
||||
public const CYAN_CANDLE = "minecraft:cyan_candle";
|
||||
public const CYAN_CANDLE_CAKE = "minecraft:cyan_candle_cake";
|
||||
public const CYAN_CARPET = "minecraft:cyan_carpet";
|
||||
@ -281,6 +302,8 @@ final class BlockTypeNames{
|
||||
public const CYAN_STAINED_GLASS_PANE = "minecraft:cyan_stained_glass_pane";
|
||||
public const CYAN_TERRACOTTA = "minecraft:cyan_terracotta";
|
||||
public const CYAN_WOOL = "minecraft:cyan_wool";
|
||||
public const DAMAGED_ANVIL = "minecraft:damaged_anvil";
|
||||
public const DANDELION = "minecraft:dandelion";
|
||||
public const DARK_OAK_BUTTON = "minecraft:dark_oak_button";
|
||||
public const DARK_OAK_DOOR = "minecraft:dark_oak_door";
|
||||
public const DARK_OAK_DOUBLE_SLAB = "minecraft:dark_oak_double_slab";
|
||||
@ -296,6 +319,9 @@ final class BlockTypeNames{
|
||||
public const DARK_OAK_STAIRS = "minecraft:dark_oak_stairs";
|
||||
public const DARK_OAK_TRAPDOOR = "minecraft:dark_oak_trapdoor";
|
||||
public const DARK_OAK_WOOD = "minecraft:dark_oak_wood";
|
||||
public const DARK_PRISMARINE = "minecraft:dark_prismarine";
|
||||
public const DARK_PRISMARINE_DOUBLE_SLAB = "minecraft:dark_prismarine_double_slab";
|
||||
public const DARK_PRISMARINE_SLAB = "minecraft:dark_prismarine_slab";
|
||||
public const DARK_PRISMARINE_STAIRS = "minecraft:dark_prismarine_stairs";
|
||||
public const DARKOAK_STANDING_SIGN = "minecraft:darkoak_standing_sign";
|
||||
public const DARKOAK_WALL_SIGN = "minecraft:darkoak_wall_sign";
|
||||
@ -304,18 +330,23 @@ final class BlockTypeNames{
|
||||
public const DEAD_BRAIN_CORAL = "minecraft:dead_brain_coral";
|
||||
public const DEAD_BRAIN_CORAL_BLOCK = "minecraft:dead_brain_coral_block";
|
||||
public const DEAD_BRAIN_CORAL_FAN = "minecraft:dead_brain_coral_fan";
|
||||
public const DEAD_BRAIN_CORAL_WALL_FAN = "minecraft:dead_brain_coral_wall_fan";
|
||||
public const DEAD_BUBBLE_CORAL = "minecraft:dead_bubble_coral";
|
||||
public const DEAD_BUBBLE_CORAL_BLOCK = "minecraft:dead_bubble_coral_block";
|
||||
public const DEAD_BUBBLE_CORAL_FAN = "minecraft:dead_bubble_coral_fan";
|
||||
public const DEAD_BUBBLE_CORAL_WALL_FAN = "minecraft:dead_bubble_coral_wall_fan";
|
||||
public const DEAD_FIRE_CORAL = "minecraft:dead_fire_coral";
|
||||
public const DEAD_FIRE_CORAL_BLOCK = "minecraft:dead_fire_coral_block";
|
||||
public const DEAD_FIRE_CORAL_FAN = "minecraft:dead_fire_coral_fan";
|
||||
public const DEAD_FIRE_CORAL_WALL_FAN = "minecraft:dead_fire_coral_wall_fan";
|
||||
public const DEAD_HORN_CORAL = "minecraft:dead_horn_coral";
|
||||
public const DEAD_HORN_CORAL_BLOCK = "minecraft:dead_horn_coral_block";
|
||||
public const DEAD_HORN_CORAL_FAN = "minecraft:dead_horn_coral_fan";
|
||||
public const DEAD_HORN_CORAL_WALL_FAN = "minecraft:dead_horn_coral_wall_fan";
|
||||
public const DEAD_TUBE_CORAL = "minecraft:dead_tube_coral";
|
||||
public const DEAD_TUBE_CORAL_BLOCK = "minecraft:dead_tube_coral_block";
|
||||
public const DEAD_TUBE_CORAL_FAN = "minecraft:dead_tube_coral_fan";
|
||||
public const DEAD_TUBE_CORAL_WALL_FAN = "minecraft:dead_tube_coral_wall_fan";
|
||||
public const DEADBUSH = "minecraft:deadbush";
|
||||
public const DECORATED_POT = "minecraft:decorated_pot";
|
||||
public const DEEPSLATE = "minecraft:deepslate";
|
||||
@ -338,20 +369,23 @@ final class BlockTypeNames{
|
||||
public const DEEPSLATE_TILE_WALL = "minecraft:deepslate_tile_wall";
|
||||
public const DEEPSLATE_TILES = "minecraft:deepslate_tiles";
|
||||
public const DENY = "minecraft:deny";
|
||||
public const DEPRECATED_ANVIL = "minecraft:deprecated_anvil";
|
||||
public const DEPRECATED_PURPUR_BLOCK_1 = "minecraft:deprecated_purpur_block_1";
|
||||
public const DEPRECATED_PURPUR_BLOCK_2 = "minecraft:deprecated_purpur_block_2";
|
||||
public const DETECTOR_RAIL = "minecraft:detector_rail";
|
||||
public const DIAMOND_BLOCK = "minecraft:diamond_block";
|
||||
public const DIAMOND_ORE = "minecraft:diamond_ore";
|
||||
public const DIORITE = "minecraft:diorite";
|
||||
public const DIORITE_DOUBLE_SLAB = "minecraft:diorite_double_slab";
|
||||
public const DIORITE_SLAB = "minecraft:diorite_slab";
|
||||
public const DIORITE_STAIRS = "minecraft:diorite_stairs";
|
||||
public const DIORITE_WALL = "minecraft:diorite_wall";
|
||||
public const DIRT = "minecraft:dirt";
|
||||
public const DIRT_WITH_ROOTS = "minecraft:dirt_with_roots";
|
||||
public const DISPENSER = "minecraft:dispenser";
|
||||
public const DOUBLE_CUT_COPPER_SLAB = "minecraft:double_cut_copper_slab";
|
||||
public const DOUBLE_STONE_BLOCK_SLAB = "minecraft:double_stone_block_slab";
|
||||
public const DOUBLE_STONE_BLOCK_SLAB2 = "minecraft:double_stone_block_slab2";
|
||||
public const DOUBLE_STONE_BLOCK_SLAB3 = "minecraft:double_stone_block_slab3";
|
||||
public const DOUBLE_STONE_BLOCK_SLAB4 = "minecraft:double_stone_block_slab4";
|
||||
public const DRAGON_EGG = "minecraft:dragon_egg";
|
||||
public const DRAGON_HEAD = "minecraft:dragon_head";
|
||||
public const DRIED_KELP_BLOCK = "minecraft:dried_kelp_block";
|
||||
public const DRIPSTONE_BLOCK = "minecraft:dripstone_block";
|
||||
public const DROPPER = "minecraft:dropper";
|
||||
@ -474,6 +508,7 @@ final class BlockTypeNames{
|
||||
public const ELEMENT_97 = "minecraft:element_97";
|
||||
public const ELEMENT_98 = "minecraft:element_98";
|
||||
public const ELEMENT_99 = "minecraft:element_99";
|
||||
public const ELEMENT_CONSTRUCTOR = "minecraft:element_constructor";
|
||||
public const EMERALD_BLOCK = "minecraft:emerald_block";
|
||||
public const EMERALD_ORE = "minecraft:emerald_ore";
|
||||
public const ENCHANTING_TABLE = "minecraft:enchanting_table";
|
||||
@ -484,6 +519,9 @@ final class BlockTypeNames{
|
||||
public const END_PORTAL_FRAME = "minecraft:end_portal_frame";
|
||||
public const END_ROD = "minecraft:end_rod";
|
||||
public const END_STONE = "minecraft:end_stone";
|
||||
public const END_STONE_BRICK_DOUBLE_SLAB = "minecraft:end_stone_brick_double_slab";
|
||||
public const END_STONE_BRICK_SLAB = "minecraft:end_stone_brick_slab";
|
||||
public const END_STONE_BRICK_WALL = "minecraft:end_stone_brick_wall";
|
||||
public const ENDER_CHEST = "minecraft:ender_chest";
|
||||
public const EXPOSED_CHISELED_COPPER = "minecraft:exposed_chiseled_copper";
|
||||
public const EXPOSED_COPPER = "minecraft:exposed_copper";
|
||||
@ -502,6 +540,7 @@ final class BlockTypeNames{
|
||||
public const FIRE_CORAL = "minecraft:fire_coral";
|
||||
public const FIRE_CORAL_BLOCK = "minecraft:fire_coral_block";
|
||||
public const FIRE_CORAL_FAN = "minecraft:fire_coral_fan";
|
||||
public const FIRE_CORAL_WALL_FAN = "minecraft:fire_coral_wall_fan";
|
||||
public const FLETCHING_TABLE = "minecraft:fletching_table";
|
||||
public const FLOWER_POT = "minecraft:flower_pot";
|
||||
public const FLOWERING_AZALEA = "minecraft:flowering_azalea";
|
||||
@ -522,7 +561,10 @@ final class BlockTypeNames{
|
||||
public const GOLD_ORE = "minecraft:gold_ore";
|
||||
public const GOLDEN_RAIL = "minecraft:golden_rail";
|
||||
public const GRANITE = "minecraft:granite";
|
||||
public const GRANITE_DOUBLE_SLAB = "minecraft:granite_double_slab";
|
||||
public const GRANITE_SLAB = "minecraft:granite_slab";
|
||||
public const GRANITE_STAIRS = "minecraft:granite_stairs";
|
||||
public const GRANITE_WALL = "minecraft:granite_wall";
|
||||
public const GRASS_BLOCK = "minecraft:grass_block";
|
||||
public const GRASS_PATH = "minecraft:grass_path";
|
||||
public const GRAVEL = "minecraft:gravel";
|
||||
@ -594,8 +636,15 @@ final class BlockTypeNames{
|
||||
public const HORN_CORAL = "minecraft:horn_coral";
|
||||
public const HORN_CORAL_BLOCK = "minecraft:horn_coral_block";
|
||||
public const HORN_CORAL_FAN = "minecraft:horn_coral_fan";
|
||||
public const HORN_CORAL_WALL_FAN = "minecraft:horn_coral_wall_fan";
|
||||
public const ICE = "minecraft:ice";
|
||||
public const INFESTED_CHISELED_STONE_BRICKS = "minecraft:infested_chiseled_stone_bricks";
|
||||
public const INFESTED_COBBLESTONE = "minecraft:infested_cobblestone";
|
||||
public const INFESTED_CRACKED_STONE_BRICKS = "minecraft:infested_cracked_stone_bricks";
|
||||
public const INFESTED_DEEPSLATE = "minecraft:infested_deepslate";
|
||||
public const INFESTED_MOSSY_STONE_BRICKS = "minecraft:infested_mossy_stone_bricks";
|
||||
public const INFESTED_STONE = "minecraft:infested_stone";
|
||||
public const INFESTED_STONE_BRICKS = "minecraft:infested_stone_bricks";
|
||||
public const INFO_UPDATE = "minecraft:info_update";
|
||||
public const INFO_UPDATE2 = "minecraft:info_update2";
|
||||
public const INVISIBLE_BEDROCK = "minecraft:invisible_bedrock";
|
||||
@ -624,6 +673,7 @@ final class BlockTypeNames{
|
||||
public const JUNGLE_WALL_SIGN = "minecraft:jungle_wall_sign";
|
||||
public const JUNGLE_WOOD = "minecraft:jungle_wood";
|
||||
public const KELP = "minecraft:kelp";
|
||||
public const LAB_TABLE = "minecraft:lab_table";
|
||||
public const LADDER = "minecraft:ladder";
|
||||
public const LANTERN = "minecraft:lantern";
|
||||
public const LAPIS_BLOCK = "minecraft:lapis_block";
|
||||
@ -633,7 +683,22 @@ final class BlockTypeNames{
|
||||
public const LAVA = "minecraft:lava";
|
||||
public const LECTERN = "minecraft:lectern";
|
||||
public const LEVER = "minecraft:lever";
|
||||
public const LIGHT_BLOCK = "minecraft:light_block";
|
||||
public const LIGHT_BLOCK_0 = "minecraft:light_block_0";
|
||||
public const LIGHT_BLOCK_1 = "minecraft:light_block_1";
|
||||
public const LIGHT_BLOCK_10 = "minecraft:light_block_10";
|
||||
public const LIGHT_BLOCK_11 = "minecraft:light_block_11";
|
||||
public const LIGHT_BLOCK_12 = "minecraft:light_block_12";
|
||||
public const LIGHT_BLOCK_13 = "minecraft:light_block_13";
|
||||
public const LIGHT_BLOCK_14 = "minecraft:light_block_14";
|
||||
public const LIGHT_BLOCK_15 = "minecraft:light_block_15";
|
||||
public const LIGHT_BLOCK_2 = "minecraft:light_block_2";
|
||||
public const LIGHT_BLOCK_3 = "minecraft:light_block_3";
|
||||
public const LIGHT_BLOCK_4 = "minecraft:light_block_4";
|
||||
public const LIGHT_BLOCK_5 = "minecraft:light_block_5";
|
||||
public const LIGHT_BLOCK_6 = "minecraft:light_block_6";
|
||||
public const LIGHT_BLOCK_7 = "minecraft:light_block_7";
|
||||
public const LIGHT_BLOCK_8 = "minecraft:light_block_8";
|
||||
public const LIGHT_BLOCK_9 = "minecraft:light_block_9";
|
||||
public const LIGHT_BLUE_CANDLE = "minecraft:light_blue_candle";
|
||||
public const LIGHT_BLUE_CANDLE_CAKE = "minecraft:light_blue_candle_cake";
|
||||
public const LIGHT_BLUE_CARPET = "minecraft:light_blue_carpet";
|
||||
@ -709,16 +774,23 @@ final class BlockTypeNames{
|
||||
public const MANGROVE_TRAPDOOR = "minecraft:mangrove_trapdoor";
|
||||
public const MANGROVE_WALL_SIGN = "minecraft:mangrove_wall_sign";
|
||||
public const MANGROVE_WOOD = "minecraft:mangrove_wood";
|
||||
public const MATERIAL_REDUCER = "minecraft:material_reducer";
|
||||
public const MEDIUM_AMETHYST_BUD = "minecraft:medium_amethyst_bud";
|
||||
public const MELON_BLOCK = "minecraft:melon_block";
|
||||
public const MELON_STEM = "minecraft:melon_stem";
|
||||
public const MOB_SPAWNER = "minecraft:mob_spawner";
|
||||
public const MONSTER_EGG = "minecraft:monster_egg";
|
||||
public const MOSS_BLOCK = "minecraft:moss_block";
|
||||
public const MOSS_CARPET = "minecraft:moss_carpet";
|
||||
public const MOSSY_COBBLESTONE = "minecraft:mossy_cobblestone";
|
||||
public const MOSSY_COBBLESTONE_DOUBLE_SLAB = "minecraft:mossy_cobblestone_double_slab";
|
||||
public const MOSSY_COBBLESTONE_SLAB = "minecraft:mossy_cobblestone_slab";
|
||||
public const MOSSY_COBBLESTONE_STAIRS = "minecraft:mossy_cobblestone_stairs";
|
||||
public const MOSSY_COBBLESTONE_WALL = "minecraft:mossy_cobblestone_wall";
|
||||
public const MOSSY_STONE_BRICK_DOUBLE_SLAB = "minecraft:mossy_stone_brick_double_slab";
|
||||
public const MOSSY_STONE_BRICK_SLAB = "minecraft:mossy_stone_brick_slab";
|
||||
public const MOSSY_STONE_BRICK_STAIRS = "minecraft:mossy_stone_brick_stairs";
|
||||
public const MOSSY_STONE_BRICK_WALL = "minecraft:mossy_stone_brick_wall";
|
||||
public const MOSSY_STONE_BRICKS = "minecraft:mossy_stone_bricks";
|
||||
public const MOVING_BLOCK = "minecraft:moving_block";
|
||||
public const MUD = "minecraft:mud";
|
||||
public const MUD_BRICK_DOUBLE_SLAB = "minecraft:mud_brick_double_slab";
|
||||
@ -727,11 +799,14 @@ final class BlockTypeNames{
|
||||
public const MUD_BRICK_WALL = "minecraft:mud_brick_wall";
|
||||
public const MUD_BRICKS = "minecraft:mud_bricks";
|
||||
public const MUDDY_MANGROVE_ROOTS = "minecraft:muddy_mangrove_roots";
|
||||
public const MUSHROOM_STEM = "minecraft:mushroom_stem";
|
||||
public const MYCELIUM = "minecraft:mycelium";
|
||||
public const NETHER_BRICK = "minecraft:nether_brick";
|
||||
public const NETHER_BRICK_DOUBLE_SLAB = "minecraft:nether_brick_double_slab";
|
||||
public const NETHER_BRICK_FENCE = "minecraft:nether_brick_fence";
|
||||
public const NETHER_BRICK_SLAB = "minecraft:nether_brick_slab";
|
||||
public const NETHER_BRICK_STAIRS = "minecraft:nether_brick_stairs";
|
||||
public const NETHER_BRICK_WALL = "minecraft:nether_brick_wall";
|
||||
public const NETHER_GOLD_ORE = "minecraft:nether_gold_ore";
|
||||
public const NETHER_SPROUTS = "minecraft:nether_sprouts";
|
||||
public const NETHER_WART = "minecraft:nether_wart";
|
||||
@ -739,6 +814,8 @@ final class BlockTypeNames{
|
||||
public const NETHERITE_BLOCK = "minecraft:netherite_block";
|
||||
public const NETHERRACK = "minecraft:netherrack";
|
||||
public const NETHERREACTOR = "minecraft:netherreactor";
|
||||
public const NORMAL_STONE_DOUBLE_SLAB = "minecraft:normal_stone_double_slab";
|
||||
public const NORMAL_STONE_SLAB = "minecraft:normal_stone_slab";
|
||||
public const NORMAL_STONE_STAIRS = "minecraft:normal_stone_stairs";
|
||||
public const NOTEBLOCK = "minecraft:noteblock";
|
||||
public const OAK_DOUBLE_SLAB = "minecraft:oak_double_slab";
|
||||
@ -781,7 +858,9 @@ final class BlockTypeNames{
|
||||
public const PACKED_MUD = "minecraft:packed_mud";
|
||||
public const PEARLESCENT_FROGLIGHT = "minecraft:pearlescent_froglight";
|
||||
public const PEONY = "minecraft:peony";
|
||||
public const PETRIFIED_OAK_DOUBLE_SLAB = "minecraft:petrified_oak_double_slab";
|
||||
public const PETRIFIED_OAK_SLAB = "minecraft:petrified_oak_slab";
|
||||
public const PIGLIN_HEAD = "minecraft:piglin_head";
|
||||
public const PINK_CANDLE = "minecraft:pink_candle";
|
||||
public const PINK_CANDLE_CAKE = "minecraft:pink_candle_cake";
|
||||
public const PINK_CARPET = "minecraft:pink_carpet";
|
||||
@ -799,9 +878,12 @@ final class BlockTypeNames{
|
||||
public const PISTON_ARM_COLLISION = "minecraft:piston_arm_collision";
|
||||
public const PITCHER_CROP = "minecraft:pitcher_crop";
|
||||
public const PITCHER_PLANT = "minecraft:pitcher_plant";
|
||||
public const PLAYER_HEAD = "minecraft:player_head";
|
||||
public const PODZOL = "minecraft:podzol";
|
||||
public const POINTED_DRIPSTONE = "minecraft:pointed_dripstone";
|
||||
public const POLISHED_ANDESITE = "minecraft:polished_andesite";
|
||||
public const POLISHED_ANDESITE_DOUBLE_SLAB = "minecraft:polished_andesite_double_slab";
|
||||
public const POLISHED_ANDESITE_SLAB = "minecraft:polished_andesite_slab";
|
||||
public const POLISHED_ANDESITE_STAIRS = "minecraft:polished_andesite_stairs";
|
||||
public const POLISHED_BASALT = "minecraft:polished_basalt";
|
||||
public const POLISHED_BLACKSTONE = "minecraft:polished_blackstone";
|
||||
@ -822,8 +904,12 @@ final class BlockTypeNames{
|
||||
public const POLISHED_DEEPSLATE_STAIRS = "minecraft:polished_deepslate_stairs";
|
||||
public const POLISHED_DEEPSLATE_WALL = "minecraft:polished_deepslate_wall";
|
||||
public const POLISHED_DIORITE = "minecraft:polished_diorite";
|
||||
public const POLISHED_DIORITE_DOUBLE_SLAB = "minecraft:polished_diorite_double_slab";
|
||||
public const POLISHED_DIORITE_SLAB = "minecraft:polished_diorite_slab";
|
||||
public const POLISHED_DIORITE_STAIRS = "minecraft:polished_diorite_stairs";
|
||||
public const POLISHED_GRANITE = "minecraft:polished_granite";
|
||||
public const POLISHED_GRANITE_DOUBLE_SLAB = "minecraft:polished_granite_double_slab";
|
||||
public const POLISHED_GRANITE_SLAB = "minecraft:polished_granite_slab";
|
||||
public const POLISHED_GRANITE_STAIRS = "minecraft:polished_granite_stairs";
|
||||
public const POLISHED_TUFF = "minecraft:polished_tuff";
|
||||
public const POLISHED_TUFF_DOUBLE_SLAB = "minecraft:polished_tuff_double_slab";
|
||||
@ -837,8 +923,14 @@ final class BlockTypeNames{
|
||||
public const POWERED_COMPARATOR = "minecraft:powered_comparator";
|
||||
public const POWERED_REPEATER = "minecraft:powered_repeater";
|
||||
public const PRISMARINE = "minecraft:prismarine";
|
||||
public const PRISMARINE_BRICK_DOUBLE_SLAB = "minecraft:prismarine_brick_double_slab";
|
||||
public const PRISMARINE_BRICK_SLAB = "minecraft:prismarine_brick_slab";
|
||||
public const PRISMARINE_BRICKS = "minecraft:prismarine_bricks";
|
||||
public const PRISMARINE_BRICKS_STAIRS = "minecraft:prismarine_bricks_stairs";
|
||||
public const PRISMARINE_DOUBLE_SLAB = "minecraft:prismarine_double_slab";
|
||||
public const PRISMARINE_SLAB = "minecraft:prismarine_slab";
|
||||
public const PRISMARINE_STAIRS = "minecraft:prismarine_stairs";
|
||||
public const PRISMARINE_WALL = "minecraft:prismarine_wall";
|
||||
public const PUMPKIN = "minecraft:pumpkin";
|
||||
public const PUMPKIN_STEM = "minecraft:pumpkin_stem";
|
||||
public const PURPLE_CANDLE = "minecraft:purple_candle";
|
||||
@ -853,10 +945,15 @@ final class BlockTypeNames{
|
||||
public const PURPLE_TERRACOTTA = "minecraft:purple_terracotta";
|
||||
public const PURPLE_WOOL = "minecraft:purple_wool";
|
||||
public const PURPUR_BLOCK = "minecraft:purpur_block";
|
||||
public const PURPUR_DOUBLE_SLAB = "minecraft:purpur_double_slab";
|
||||
public const PURPUR_PILLAR = "minecraft:purpur_pillar";
|
||||
public const PURPUR_SLAB = "minecraft:purpur_slab";
|
||||
public const PURPUR_STAIRS = "minecraft:purpur_stairs";
|
||||
public const QUARTZ_BLOCK = "minecraft:quartz_block";
|
||||
public const QUARTZ_BRICKS = "minecraft:quartz_bricks";
|
||||
public const QUARTZ_DOUBLE_SLAB = "minecraft:quartz_double_slab";
|
||||
public const QUARTZ_ORE = "minecraft:quartz_ore";
|
||||
public const QUARTZ_PILLAR = "minecraft:quartz_pillar";
|
||||
public const QUARTZ_SLAB = "minecraft:quartz_slab";
|
||||
public const QUARTZ_STAIRS = "minecraft:quartz_stairs";
|
||||
public const RAIL = "minecraft:rail";
|
||||
@ -872,9 +969,16 @@ final class BlockTypeNames{
|
||||
public const RED_MUSHROOM = "minecraft:red_mushroom";
|
||||
public const RED_MUSHROOM_BLOCK = "minecraft:red_mushroom_block";
|
||||
public const RED_NETHER_BRICK = "minecraft:red_nether_brick";
|
||||
public const RED_NETHER_BRICK_DOUBLE_SLAB = "minecraft:red_nether_brick_double_slab";
|
||||
public const RED_NETHER_BRICK_SLAB = "minecraft:red_nether_brick_slab";
|
||||
public const RED_NETHER_BRICK_STAIRS = "minecraft:red_nether_brick_stairs";
|
||||
public const RED_NETHER_BRICK_WALL = "minecraft:red_nether_brick_wall";
|
||||
public const RED_SAND = "minecraft:red_sand";
|
||||
public const RED_SANDSTONE = "minecraft:red_sandstone";
|
||||
public const RED_SANDSTONE_DOUBLE_SLAB = "minecraft:red_sandstone_double_slab";
|
||||
public const RED_SANDSTONE_SLAB = "minecraft:red_sandstone_slab";
|
||||
public const RED_SANDSTONE_STAIRS = "minecraft:red_sandstone_stairs";
|
||||
public const RED_SANDSTONE_WALL = "minecraft:red_sandstone_wall";
|
||||
public const RED_SHULKER_BOX = "minecraft:red_shulker_box";
|
||||
public const RED_STAINED_GLASS = "minecraft:red_stained_glass";
|
||||
public const RED_STAINED_GLASS_PANE = "minecraft:red_stained_glass_pane";
|
||||
@ -894,8 +998,10 @@ final class BlockTypeNames{
|
||||
public const ROSE_BUSH = "minecraft:rose_bush";
|
||||
public const SAND = "minecraft:sand";
|
||||
public const SANDSTONE = "minecraft:sandstone";
|
||||
public const SANDSTONE_DOUBLE_SLAB = "minecraft:sandstone_double_slab";
|
||||
public const SANDSTONE_SLAB = "minecraft:sandstone_slab";
|
||||
public const SANDSTONE_STAIRS = "minecraft:sandstone_stairs";
|
||||
public const SANDSTONE_WALL = "minecraft:sandstone_wall";
|
||||
public const SCAFFOLDING = "minecraft:scaffolding";
|
||||
public const SCULK = "minecraft:sculk";
|
||||
public const SCULK_CATALYST = "minecraft:sculk_catalyst";
|
||||
@ -908,17 +1014,27 @@ final class BlockTypeNames{
|
||||
public const SHORT_GRASS = "minecraft:short_grass";
|
||||
public const SHROOMLIGHT = "minecraft:shroomlight";
|
||||
public const SILVER_GLAZED_TERRACOTTA = "minecraft:silver_glazed_terracotta";
|
||||
public const SKULL = "minecraft:skull";
|
||||
public const SKELETON_SKULL = "minecraft:skeleton_skull";
|
||||
public const SLIME = "minecraft:slime";
|
||||
public const SMALL_AMETHYST_BUD = "minecraft:small_amethyst_bud";
|
||||
public const SMALL_DRIPLEAF_BLOCK = "minecraft:small_dripleaf_block";
|
||||
public const SMITHING_TABLE = "minecraft:smithing_table";
|
||||
public const SMOKER = "minecraft:smoker";
|
||||
public const SMOOTH_BASALT = "minecraft:smooth_basalt";
|
||||
public const SMOOTH_QUARTZ = "minecraft:smooth_quartz";
|
||||
public const SMOOTH_QUARTZ_DOUBLE_SLAB = "minecraft:smooth_quartz_double_slab";
|
||||
public const SMOOTH_QUARTZ_SLAB = "minecraft:smooth_quartz_slab";
|
||||
public const SMOOTH_QUARTZ_STAIRS = "minecraft:smooth_quartz_stairs";
|
||||
public const SMOOTH_RED_SANDSTONE = "minecraft:smooth_red_sandstone";
|
||||
public const SMOOTH_RED_SANDSTONE_DOUBLE_SLAB = "minecraft:smooth_red_sandstone_double_slab";
|
||||
public const SMOOTH_RED_SANDSTONE_SLAB = "minecraft:smooth_red_sandstone_slab";
|
||||
public const SMOOTH_RED_SANDSTONE_STAIRS = "minecraft:smooth_red_sandstone_stairs";
|
||||
public const SMOOTH_SANDSTONE = "minecraft:smooth_sandstone";
|
||||
public const SMOOTH_SANDSTONE_DOUBLE_SLAB = "minecraft:smooth_sandstone_double_slab";
|
||||
public const SMOOTH_SANDSTONE_SLAB = "minecraft:smooth_sandstone_slab";
|
||||
public const SMOOTH_SANDSTONE_STAIRS = "minecraft:smooth_sandstone_stairs";
|
||||
public const SMOOTH_STONE = "minecraft:smooth_stone";
|
||||
public const SMOOTH_STONE_DOUBLE_SLAB = "minecraft:smooth_stone_double_slab";
|
||||
public const SMOOTH_STONE_SLAB = "minecraft:smooth_stone_slab";
|
||||
public const SNIFFER_EGG = "minecraft:sniffer_egg";
|
||||
public const SNOW = "minecraft:snow";
|
||||
@ -953,15 +1069,14 @@ final class BlockTypeNames{
|
||||
public const STICKY_PISTON = "minecraft:sticky_piston";
|
||||
public const STICKY_PISTON_ARM_COLLISION = "minecraft:sticky_piston_arm_collision";
|
||||
public const STONE = "minecraft:stone";
|
||||
public const STONE_BLOCK_SLAB2 = "minecraft:stone_block_slab2";
|
||||
public const STONE_BLOCK_SLAB3 = "minecraft:stone_block_slab3";
|
||||
public const STONE_BLOCK_SLAB4 = "minecraft:stone_block_slab4";
|
||||
public const STONE_BRICK_DOUBLE_SLAB = "minecraft:stone_brick_double_slab";
|
||||
public const STONE_BRICK_SLAB = "minecraft:stone_brick_slab";
|
||||
public const STONE_BRICK_STAIRS = "minecraft:stone_brick_stairs";
|
||||
public const STONE_BRICK_WALL = "minecraft:stone_brick_wall";
|
||||
public const STONE_BRICKS = "minecraft:stone_bricks";
|
||||
public const STONE_BUTTON = "minecraft:stone_button";
|
||||
public const STONE_PRESSURE_PLATE = "minecraft:stone_pressure_plate";
|
||||
public const STONE_STAIRS = "minecraft:stone_stairs";
|
||||
public const STONEBRICK = "minecraft:stonebrick";
|
||||
public const STONECUTTER = "minecraft:stonecutter";
|
||||
public const STONECUTTER_BLOCK = "minecraft:stonecutter_block";
|
||||
public const STRIPPED_ACACIA_LOG = "minecraft:stripped_acacia_log";
|
||||
@ -1006,6 +1121,7 @@ final class BlockTypeNames{
|
||||
public const TUBE_CORAL = "minecraft:tube_coral";
|
||||
public const TUBE_CORAL_BLOCK = "minecraft:tube_coral_block";
|
||||
public const TUBE_CORAL_FAN = "minecraft:tube_coral_fan";
|
||||
public const TUBE_CORAL_WALL_FAN = "minecraft:tube_coral_wall_fan";
|
||||
public const TUFF = "minecraft:tuff";
|
||||
public const TUFF_BRICK_DOUBLE_SLAB = "minecraft:tuff_brick_double_slab";
|
||||
public const TUFF_BRICK_SLAB = "minecraft:tuff_brick_slab";
|
||||
@ -1018,6 +1134,7 @@ final class BlockTypeNames{
|
||||
public const TUFF_WALL = "minecraft:tuff_wall";
|
||||
public const TURTLE_EGG = "minecraft:turtle_egg";
|
||||
public const TWISTING_VINES = "minecraft:twisting_vines";
|
||||
public const UNDERWATER_TNT = "minecraft:underwater_tnt";
|
||||
public const UNDERWATER_TORCH = "minecraft:underwater_torch";
|
||||
public const UNDYED_SHULKER_BOX = "minecraft:undyed_shulker_box";
|
||||
public const UNKNOWN = "minecraft:unknown";
|
||||
@ -1102,6 +1219,7 @@ final class BlockTypeNames{
|
||||
public const WEATHERED_DOUBLE_CUT_COPPER_SLAB = "minecraft:weathered_double_cut_copper_slab";
|
||||
public const WEB = "minecraft:web";
|
||||
public const WEEPING_VINES = "minecraft:weeping_vines";
|
||||
public const WET_SPONGE = "minecraft:wet_sponge";
|
||||
public const WHEAT = "minecraft:wheat";
|
||||
public const WHITE_CANDLE = "minecraft:white_candle";
|
||||
public const WHITE_CANDLE_CAKE = "minecraft:white_candle_cake";
|
||||
@ -1116,6 +1234,7 @@ final class BlockTypeNames{
|
||||
public const WHITE_TULIP = "minecraft:white_tulip";
|
||||
public const WHITE_WOOL = "minecraft:white_wool";
|
||||
public const WITHER_ROSE = "minecraft:wither_rose";
|
||||
public const WITHER_SKELETON_SKULL = "minecraft:wither_skeleton_skull";
|
||||
public const WOODEN_BUTTON = "minecraft:wooden_button";
|
||||
public const WOODEN_DOOR = "minecraft:wooden_door";
|
||||
public const WOODEN_PRESSURE_PLATE = "minecraft:wooden_pressure_plate";
|
||||
@ -1124,11 +1243,11 @@ final class BlockTypeNames{
|
||||
public const YELLOW_CARPET = "minecraft:yellow_carpet";
|
||||
public const YELLOW_CONCRETE = "minecraft:yellow_concrete";
|
||||
public const YELLOW_CONCRETE_POWDER = "minecraft:yellow_concrete_powder";
|
||||
public const YELLOW_FLOWER = "minecraft:yellow_flower";
|
||||
public const YELLOW_GLAZED_TERRACOTTA = "minecraft:yellow_glazed_terracotta";
|
||||
public const YELLOW_SHULKER_BOX = "minecraft:yellow_shulker_box";
|
||||
public const YELLOW_STAINED_GLASS = "minecraft:yellow_stained_glass";
|
||||
public const YELLOW_STAINED_GLASS_PANE = "minecraft:yellow_stained_glass_pane";
|
||||
public const YELLOW_TERRACOTTA = "minecraft:yellow_terracotta";
|
||||
public const YELLOW_WOOL = "minecraft:yellow_wool";
|
||||
public const ZOMBIE_HEAD = "minecraft:zombie_head";
|
||||
}
|
||||
|
@ -43,6 +43,7 @@ use pocketmine\block\Cactus;
|
||||
use pocketmine\block\Cake;
|
||||
use pocketmine\block\CakeWithCandle;
|
||||
use pocketmine\block\CakeWithDyedCandle;
|
||||
use pocketmine\block\Campfire;
|
||||
use pocketmine\block\Candle;
|
||||
use pocketmine\block\Carpet;
|
||||
use pocketmine\block\Carrot;
|
||||
@ -57,8 +58,12 @@ use pocketmine\block\CocoaBlock;
|
||||
use pocketmine\block\Concrete;
|
||||
use pocketmine\block\ConcretePowder;
|
||||
use pocketmine\block\Copper;
|
||||
use pocketmine\block\CopperBulb;
|
||||
use pocketmine\block\CopperDoor;
|
||||
use pocketmine\block\CopperGrate;
|
||||
use pocketmine\block\CopperSlab;
|
||||
use pocketmine\block\CopperStairs;
|
||||
use pocketmine\block\CopperTrapdoor;
|
||||
use pocketmine\block\Coral;
|
||||
use pocketmine\block\CoralBlock;
|
||||
use pocketmine\block\DaylightSensor;
|
||||
@ -124,6 +129,7 @@ use pocketmine\block\SimplePressurePlate;
|
||||
use pocketmine\block\Slab;
|
||||
use pocketmine\block\SmallDripleaf;
|
||||
use pocketmine\block\SnowLayer;
|
||||
use pocketmine\block\SoulCampfire;
|
||||
use pocketmine\block\Sponge;
|
||||
use pocketmine\block\StainedGlass;
|
||||
use pocketmine\block\StainedGlassPane;
|
||||
@ -151,6 +157,7 @@ use pocketmine\block\utils\DripleafState;
|
||||
use pocketmine\block\utils\DyeColor;
|
||||
use pocketmine\block\utils\FroglightType;
|
||||
use pocketmine\block\utils\LeverFacing;
|
||||
use pocketmine\block\utils\MobHeadType;
|
||||
use pocketmine\block\VanillaBlocks as Blocks;
|
||||
use pocketmine\block\Vine;
|
||||
use pocketmine\block\Wall;
|
||||
@ -205,6 +212,7 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
$this->registerFlatWoodBlockSerializers();
|
||||
$this->registerLeavesSerializers();
|
||||
$this->registerSaplingSerializers();
|
||||
$this->registerMobHeadSerializers();
|
||||
$this->registerSimpleSerializers();
|
||||
$this->registerSerializers();
|
||||
}
|
||||
@ -562,6 +570,17 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
CoralType::TUBE => $block->isDead() ? Ids::DEAD_TUBE_CORAL_BLOCK : Ids::TUBE_CORAL_BLOCK,
|
||||
}
|
||||
));
|
||||
|
||||
$this->map(Blocks::WALL_CORAL_FAN(), fn(WallCoralFan $block) => Writer::create(
|
||||
match($block->getCoralType()){
|
||||
CoralType::TUBE => $block->isDead() ? Ids::DEAD_TUBE_CORAL_WALL_FAN : Ids::TUBE_CORAL_WALL_FAN,
|
||||
CoralType::BRAIN => $block->isDead() ? Ids::DEAD_BRAIN_CORAL_WALL_FAN : Ids::BRAIN_CORAL_WALL_FAN,
|
||||
CoralType::BUBBLE => $block->isDead() ? Ids::DEAD_BUBBLE_CORAL_WALL_FAN : Ids::BUBBLE_CORAL_WALL_FAN,
|
||||
CoralType::FIRE => $block->isDead() ? Ids::DEAD_FIRE_CORAL_WALL_FAN : Ids::FIRE_CORAL_WALL_FAN,
|
||||
CoralType::HORN => $block->isDead() ? Ids::DEAD_HORN_CORAL_WALL_FAN : Ids::HORN_CORAL_WALL_FAN,
|
||||
})
|
||||
->writeCoralFacing($block->getFacing())
|
||||
);
|
||||
}
|
||||
|
||||
private function registerCauldronSerializers() : void{
|
||||
@ -613,17 +632,7 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
$this->mapSimple(Blocks::CHERRY_PLANKS(), Ids::CHERRY_PLANKS);
|
||||
$this->mapSlab(Blocks::CHERRY_SLAB(), Ids::CHERRY_SLAB, Ids::CHERRY_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::CHERRY_STAIRS(), Ids::CHERRY_STAIRS);
|
||||
$this->map(Blocks::CHERRY_WOOD(), function(Wood $block) : Writer{
|
||||
//we can't use the standard method for this because cherry_wood has a useless property attached to it
|
||||
if(!$block->isStripped()){
|
||||
return Writer::create(Ids::CHERRY_WOOD)
|
||||
->writePillarAxis($block->getAxis())
|
||||
->writeBool(StateNames::STRIPPED_BIT, false); //this is useless, but it has to be written
|
||||
}else{
|
||||
return Writer::create(Ids::STRIPPED_CHERRY_WOOD)
|
||||
->writePillarAxis($block->getAxis());
|
||||
}
|
||||
});
|
||||
$this->mapLog(Blocks::CHERRY_WOOD(), Ids::CHERRY_WOOD, Ids::STRIPPED_CHERRY_WOOD);
|
||||
|
||||
$this->map(Blocks::CRIMSON_BUTTON(), fn(Button $block) => Helper::encodeButton($block, new Writer(Ids::CRIMSON_BUTTON)));
|
||||
$this->map(Blocks::CRIMSON_DOOR(), fn(Door $block) => Helper::encodeDoor($block, new Writer(Ids::CRIMSON_DOOR)));
|
||||
@ -679,17 +688,7 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
$this->mapSimple(Blocks::MANGROVE_PLANKS(), Ids::MANGROVE_PLANKS);
|
||||
$this->mapSlab(Blocks::MANGROVE_SLAB(), Ids::MANGROVE_SLAB, Ids::MANGROVE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::MANGROVE_STAIRS(), Ids::MANGROVE_STAIRS);
|
||||
$this->map(Blocks::MANGROVE_WOOD(), function(Wood $block) : Writer{
|
||||
//we can't use the standard method for this because mangrove_wood has a useless property attached to it
|
||||
if(!$block->isStripped()){
|
||||
return Writer::create(Ids::MANGROVE_WOOD)
|
||||
->writePillarAxis($block->getAxis())
|
||||
->writeBool(StateNames::STRIPPED_BIT, false); //this is useless, but it has to be written
|
||||
}else{
|
||||
return Writer::create(Ids::STRIPPED_MANGROVE_WOOD)
|
||||
->writePillarAxis($block->getAxis());
|
||||
}
|
||||
});
|
||||
$this->mapLog(Blocks::MANGROVE_WOOD(), Ids::MANGROVE_WOOD, Ids::STRIPPED_MANGROVE_WOOD);
|
||||
|
||||
$this->map(Blocks::OAK_BUTTON(), fn(WoodenButton $block) => Helper::encodeButton($block, new Writer(Ids::WOODEN_BUTTON)));
|
||||
$this->map(Blocks::OAK_DOOR(), fn(WoodenDoor $block) => Helper::encodeDoor($block, new Writer(Ids::WOODEN_DOOR)));
|
||||
@ -764,6 +763,18 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
}
|
||||
}
|
||||
|
||||
private function registerMobHeadSerializers() : void{
|
||||
$this->map(Blocks::MOB_HEAD(), fn(MobHead $block) => Writer::create(match ($block->getMobHeadType()){
|
||||
MobHeadType::CREEPER => Ids::CREEPER_HEAD,
|
||||
MobHeadType::DRAGON => Ids::DRAGON_HEAD,
|
||||
MobHeadType::PIGLIN => Ids::PIGLIN_HEAD,
|
||||
MobHeadType::PLAYER => Ids::PLAYER_HEAD,
|
||||
MobHeadType::SKELETON => Ids::SKELETON_SKULL,
|
||||
MobHeadType::WITHER_SKELETON => Ids::WITHER_SKELETON_SKULL,
|
||||
MobHeadType::ZOMBIE => Ids::ZOMBIE_HEAD,
|
||||
})->writeFacingWithoutDown($block->getFacing()));
|
||||
}
|
||||
|
||||
private function registerSimpleSerializers() : void{
|
||||
$this->mapSimple(Blocks::AIR(), Ids::AIR);
|
||||
$this->mapSimple(Blocks::AMETHYST(), Ids::AMETHYST_BLOCK);
|
||||
@ -783,6 +794,11 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
$this->mapSimple(Blocks::CHISELED_DEEPSLATE(), Ids::CHISELED_DEEPSLATE);
|
||||
$this->mapSimple(Blocks::CHISELED_NETHER_BRICKS(), Ids::CHISELED_NETHER_BRICKS);
|
||||
$this->mapSimple(Blocks::CHISELED_POLISHED_BLACKSTONE(), Ids::CHISELED_POLISHED_BLACKSTONE);
|
||||
$this->mapSimple(Blocks::CHISELED_RED_SANDSTONE(), Ids::CHISELED_RED_SANDSTONE);
|
||||
$this->mapSimple(Blocks::CHISELED_SANDSTONE(), Ids::CHISELED_SANDSTONE);
|
||||
$this->mapSimple(Blocks::CHISELED_STONE_BRICKS(), Ids::CHISELED_STONE_BRICKS);
|
||||
$this->mapSimple(Blocks::CHISELED_TUFF(), Ids::CHISELED_TUFF);
|
||||
$this->mapSimple(Blocks::CHISELED_TUFF_BRICKS(), Ids::CHISELED_TUFF_BRICKS);
|
||||
$this->mapSimple(Blocks::CHORUS_PLANT(), Ids::CHORUS_PLANT);
|
||||
$this->mapSimple(Blocks::CLAY(), Ids::CLAY);
|
||||
$this->mapSimple(Blocks::COAL(), Ids::COAL_BLOCK);
|
||||
@ -795,10 +811,14 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
$this->mapSimple(Blocks::CRACKED_DEEPSLATE_TILES(), Ids::CRACKED_DEEPSLATE_TILES);
|
||||
$this->mapSimple(Blocks::CRACKED_NETHER_BRICKS(), Ids::CRACKED_NETHER_BRICKS);
|
||||
$this->mapSimple(Blocks::CRACKED_POLISHED_BLACKSTONE_BRICKS(), Ids::CRACKED_POLISHED_BLACKSTONE_BRICKS);
|
||||
$this->mapSimple(Blocks::CRACKED_STONE_BRICKS(), Ids::CRACKED_STONE_BRICKS);
|
||||
$this->mapSimple(Blocks::CRAFTING_TABLE(), Ids::CRAFTING_TABLE);
|
||||
$this->mapSimple(Blocks::CRIMSON_ROOTS(), Ids::CRIMSON_ROOTS);
|
||||
$this->mapSimple(Blocks::CRYING_OBSIDIAN(), Ids::CRYING_OBSIDIAN);
|
||||
$this->mapSimple(Blocks::DANDELION(), Ids::YELLOW_FLOWER);
|
||||
$this->mapSimple(Blocks::DANDELION(), Ids::DANDELION);
|
||||
$this->mapSimple(Blocks::CUT_RED_SANDSTONE(), Ids::CUT_RED_SANDSTONE);
|
||||
$this->mapSimple(Blocks::CUT_SANDSTONE(), Ids::CUT_SANDSTONE);
|
||||
$this->mapSimple(Blocks::DARK_PRISMARINE(), Ids::DARK_PRISMARINE);
|
||||
$this->mapSimple(Blocks::DEAD_BUSH(), Ids::DEADBUSH);
|
||||
$this->mapSimple(Blocks::DEEPSLATE_BRICKS(), Ids::DEEPSLATE_BRICKS);
|
||||
$this->mapSimple(Blocks::DEEPSLATE_COAL_ORE(), Ids::DEEPSLATE_COAL_ORE);
|
||||
@ -957,6 +977,12 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
$this->mapSimple(Blocks::HARDENED_GLASS_PANE(), Ids::HARD_GLASS_PANE);
|
||||
$this->mapSimple(Blocks::HONEYCOMB(), Ids::HONEYCOMB_BLOCK);
|
||||
$this->mapSimple(Blocks::ICE(), Ids::ICE);
|
||||
$this->mapSimple(Blocks::INFESTED_CHISELED_STONE_BRICK(), Ids::INFESTED_CHISELED_STONE_BRICKS);
|
||||
$this->mapSimple(Blocks::INFESTED_COBBLESTONE(), Ids::INFESTED_COBBLESTONE);
|
||||
$this->mapSimple(Blocks::INFESTED_CRACKED_STONE_BRICK(), Ids::INFESTED_CRACKED_STONE_BRICKS);
|
||||
$this->mapSimple(Blocks::INFESTED_MOSSY_STONE_BRICK(), Ids::INFESTED_MOSSY_STONE_BRICKS);
|
||||
$this->mapSimple(Blocks::INFESTED_STONE(), Ids::INFESTED_STONE);
|
||||
$this->mapSimple(Blocks::INFESTED_STONE_BRICK(), Ids::INFESTED_STONE_BRICKS);
|
||||
$this->mapSimple(Blocks::INFO_UPDATE(), Ids::INFO_UPDATE);
|
||||
$this->mapSimple(Blocks::INFO_UPDATE2(), Ids::INFO_UPDATE2);
|
||||
$this->mapSimple(Blocks::INVISIBLE_BEDROCK(), Ids::INVISIBLE_BEDROCK);
|
||||
@ -973,6 +999,7 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
$this->mapSimple(Blocks::MELON(), Ids::MELON_BLOCK);
|
||||
$this->mapSimple(Blocks::MONSTER_SPAWNER(), Ids::MOB_SPAWNER);
|
||||
$this->mapSimple(Blocks::MOSSY_COBBLESTONE(), Ids::MOSSY_COBBLESTONE);
|
||||
$this->mapSimple(Blocks::MOSSY_STONE_BRICKS(), Ids::MOSSY_STONE_BRICKS);
|
||||
$this->mapSimple(Blocks::MUD(), Ids::MUD);
|
||||
$this->mapSimple(Blocks::MUD_BRICKS(), Ids::MUD_BRICKS);
|
||||
$this->mapSimple(Blocks::MYCELIUM(), Ids::MYCELIUM);
|
||||
@ -995,6 +1022,9 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
$this->mapSimple(Blocks::POLISHED_DEEPSLATE(), Ids::POLISHED_DEEPSLATE);
|
||||
$this->mapSimple(Blocks::POLISHED_DIORITE(), Ids::POLISHED_DIORITE);
|
||||
$this->mapSimple(Blocks::POLISHED_GRANITE(), Ids::POLISHED_GRANITE);
|
||||
$this->mapSimple(Blocks::POLISHED_TUFF(), Ids::POLISHED_TUFF);
|
||||
$this->mapSimple(Blocks::PRISMARINE(), Ids::PRISMARINE);
|
||||
$this->mapSimple(Blocks::PRISMARINE_BRICKS(), Ids::PRISMARINE_BRICKS);
|
||||
$this->mapSimple(Blocks::QUARTZ_BRICKS(), Ids::QUARTZ_BRICKS);
|
||||
$this->mapSimple(Blocks::RAW_COPPER(), Ids::RAW_COPPER_BLOCK);
|
||||
$this->mapSimple(Blocks::RAW_GOLD(), Ids::RAW_GOLD_BLOCK);
|
||||
@ -1002,8 +1032,12 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
$this->mapSimple(Blocks::REDSTONE(), Ids::REDSTONE_BLOCK);
|
||||
$this->mapSimple(Blocks::RED_MUSHROOM(), Ids::RED_MUSHROOM);
|
||||
$this->mapSimple(Blocks::RED_NETHER_BRICKS(), Ids::RED_NETHER_BRICK);
|
||||
$this->mapSimple(Blocks::RED_SAND(), Ids::RED_SAND);
|
||||
$this->mapSimple(Blocks::RED_SANDSTONE(), Ids::RED_SANDSTONE);
|
||||
$this->mapSimple(Blocks::REINFORCED_DEEPSLATE(), Ids::REINFORCED_DEEPSLATE);
|
||||
$this->mapSimple(Blocks::RESERVED6(), Ids::RESERVED6);
|
||||
$this->mapSimple(Blocks::SAND(), Ids::SAND);
|
||||
$this->mapSimple(Blocks::SANDSTONE(), Ids::SANDSTONE);
|
||||
$this->mapSimple(Blocks::SCULK(), Ids::SCULK);
|
||||
$this->mapSimple(Blocks::SEA_LANTERN(), Ids::SEA_LANTERN);
|
||||
$this->mapSimple(Blocks::SHROOMLIGHT(), Ids::SHROOMLIGHT);
|
||||
@ -1011,16 +1045,20 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
$this->mapSimple(Blocks::SLIME(), Ids::SLIME);
|
||||
$this->mapSimple(Blocks::SMITHING_TABLE(), Ids::SMITHING_TABLE);
|
||||
$this->mapSimple(Blocks::SMOOTH_BASALT(), Ids::SMOOTH_BASALT);
|
||||
$this->mapSimple(Blocks::SMOOTH_RED_SANDSTONE(), Ids::SMOOTH_RED_SANDSTONE);
|
||||
$this->mapSimple(Blocks::SMOOTH_SANDSTONE(), Ids::SMOOTH_SANDSTONE);
|
||||
$this->mapSimple(Blocks::SMOOTH_STONE(), Ids::SMOOTH_STONE);
|
||||
$this->mapSimple(Blocks::SNOW(), Ids::SNOW);
|
||||
$this->mapSimple(Blocks::SOUL_SAND(), Ids::SOUL_SAND);
|
||||
$this->mapSimple(Blocks::SOUL_SOIL(), Ids::SOUL_SOIL);
|
||||
$this->mapSimple(Blocks::SPORE_BLOSSOM(), Ids::SPORE_BLOSSOM);
|
||||
$this->mapSimple(Blocks::STONE(), Ids::STONE);
|
||||
$this->mapSimple(Blocks::TALL_GRASS(), Ids::SHORT_GRASS); //no, this is not a typo - tall_grass is now the double block, just to be confusing :(
|
||||
$this->mapSimple(Blocks::STONE_BRICKS(), Ids::STONE_BRICKS);
|
||||
$this->mapSimple(Blocks::TALL_GRASS(), Ids::SHORT_GRASS); //no, this is not a typo - tall_grass is now the double block, just to be confusing :(
|
||||
$this->mapSimple(Blocks::TINTED_GLASS(), Ids::TINTED_GLASS);
|
||||
$this->mapSimple(Blocks::TORCHFLOWER(), Ids::TORCHFLOWER);
|
||||
$this->mapSimple(Blocks::TUFF(), Ids::TUFF);
|
||||
$this->mapSimple(Blocks::TUFF_BRICKS(), Ids::TUFF_BRICKS);
|
||||
$this->mapSimple(Blocks::WARPED_WART_BLOCK(), Ids::WARPED_WART_BLOCK);
|
||||
$this->mapSimple(Blocks::WARPED_ROOTS(), Ids::WARPED_ROOTS);
|
||||
$this->mapSimple(Blocks::WITHER_ROSE(), Ids::WITHER_ROSE);
|
||||
@ -1044,7 +1082,7 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
->writeBool(StateNames::RAIL_DATA_BIT, $block->isPowered())
|
||||
->writeInt(StateNames::RAIL_DIRECTION, $block->getShape());
|
||||
});
|
||||
$this->map(Blocks::ALL_SIDED_MUSHROOM_STEM(), fn() => Writer::create(Ids::BROWN_MUSHROOM_BLOCK)
|
||||
$this->map(Blocks::ALL_SIDED_MUSHROOM_STEM(), fn() => Writer::create(Ids::MUSHROOM_STEM)
|
||||
->writeInt(StateNames::HUGE_MUSHROOM_BITS, BlockLegacyMetadata::MUSHROOM_BLOCK_ALL_STEM));
|
||||
$this->map(Blocks::AMETHYST_CLUSTER(), fn(AmethystCluster $block) => Writer::create(
|
||||
match($stage = $block->getStage()){
|
||||
@ -1056,19 +1094,18 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
})
|
||||
->writeBlockFace($block->getFacing())
|
||||
);
|
||||
$this->map(Blocks::ANDESITE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab3($block, StringValues::STONE_SLAB_TYPE_3_ANDESITE));
|
||||
$this->mapSlab(Blocks::ANDESITE_SLAB(), Ids::ANDESITE_SLAB, Ids::ANDESITE_DOUBLE_SLAB);
|
||||
$this->map(Blocks::ANDESITE_STAIRS(), fn(Stair $block) => Helper::encodeStairs($block, new Writer(Ids::ANDESITE_STAIRS)));
|
||||
$this->map(Blocks::ANDESITE_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_ANDESITE));
|
||||
$this->map(Blocks::ANVIL(), function(Anvil $block) : Writer{
|
||||
return Writer::create(Ids::ANVIL)
|
||||
->writeCardinalHorizontalFacing($block->getFacing())
|
||||
->writeString(StateNames::DAMAGE, match($damage = $block->getDamage()){
|
||||
0 => StringValues::DAMAGE_UNDAMAGED,
|
||||
1 => StringValues::DAMAGE_SLIGHTLY_DAMAGED,
|
||||
2 => StringValues::DAMAGE_VERY_DAMAGED,
|
||||
default => throw new BlockStateSerializeException("Invalid Anvil damage {$damage}"),
|
||||
});
|
||||
});
|
||||
$this->map(Blocks::ANDESITE_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::ANDESITE_WALL)));
|
||||
$this->map(Blocks::ANVIL(), fn(Anvil $block) : Writer => Writer::create(
|
||||
match($damage = $block->getDamage()){
|
||||
0 => Ids::ANVIL,
|
||||
1 => Ids::CHIPPED_ANVIL,
|
||||
2 => Ids::DAMAGED_ANVIL,
|
||||
default => throw new BlockStateSerializeException("Invalid Anvil damage {$damage}"),
|
||||
})
|
||||
->writeCardinalHorizontalFacing($block->getFacing())
|
||||
);
|
||||
$this->map(Blocks::BAMBOO(), function(Bamboo $block) : Writer{
|
||||
return Writer::create(Ids::BAMBOO)
|
||||
->writeBool(StateNames::AGE_BIT, $block->isReady())
|
||||
@ -1136,7 +1173,7 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
$this->mapStairs(Blocks::BLACKSTONE_STAIRS(), Ids::BLACKSTONE_STAIRS);
|
||||
$this->map(Blocks::BLACKSTONE_WALL(), fn(Wall $block) => Helper::encodeWall($block, new Writer(Ids::BLACKSTONE_WALL)));
|
||||
$this->map(Blocks::BLAST_FURNACE(), fn(Furnace $block) => Helper::encodeFurnace($block, Ids::BLAST_FURNACE, Ids::LIT_BLAST_FURNACE));
|
||||
$this->map(Blocks::BLUE_TORCH(), fn(Torch $block) => Helper::encodeColoredTorch($block, false, Writer::create(Ids::COLORED_TORCH_BP)));
|
||||
$this->map(Blocks::BLUE_TORCH(), fn(Torch $block) => Helper::encodeTorch($block, Writer::create(Ids::COLORED_TORCH_BLUE)));
|
||||
$this->map(Blocks::BONE_BLOCK(), function(BoneBlock $block) : Writer{
|
||||
return Writer::create(Ids::BONE_BLOCK)
|
||||
->writeInt(StateNames::DEPRECATED, 0)
|
||||
@ -1148,9 +1185,9 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
->writeBool(StateNames::BREWING_STAND_SLOT_B_BIT, $block->hasSlot(BrewingStandSlot::SOUTHWEST))
|
||||
->writeBool(StateNames::BREWING_STAND_SLOT_C_BIT, $block->hasSlot(BrewingStandSlot::NORTHWEST));
|
||||
});
|
||||
$this->map(Blocks::BRICK_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab1($block, Ids::BRICK_SLAB, StringValues::STONE_SLAB_TYPE_BRICK));
|
||||
$this->mapSlab(Blocks::BRICK_SLAB(), Ids::BRICK_SLAB, Ids::BRICK_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::BRICK_STAIRS(), Ids::BRICK_STAIRS);
|
||||
$this->map(Blocks::BRICK_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_BRICK));
|
||||
$this->map(Blocks::BRICK_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::BRICK_WALL)));
|
||||
$this->map(Blocks::BROWN_MUSHROOM_BLOCK(), fn(BrownMushroomBlock $block) => Helper::encodeMushroomBlock($block, new Writer(Ids::BROWN_MUSHROOM_BLOCK)));
|
||||
$this->map(Blocks::CACTUS(), function(Cactus $block) : Writer{
|
||||
return Writer::create(Ids::CACTUS)
|
||||
@ -1160,6 +1197,11 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
return Writer::create(Ids::CAKE)
|
||||
->writeInt(StateNames::BITE_COUNTER, $block->getBites());
|
||||
});
|
||||
$this->map(Blocks::CAMPFIRE(), function(Campfire $block) : Writer{
|
||||
return Writer::create(Ids::CAMPFIRE)
|
||||
->writeCardinalHorizontalFacing($block->getFacing())
|
||||
->writeBool(StateNames::EXTINGUISHED, !$block->isLit());
|
||||
});
|
||||
$this->map(Blocks::CARROTS(), fn(Carrot $block) => Helper::encodeCrops($block, new Writer(Ids::CARROTS)));
|
||||
$this->map(Blocks::CARVED_PUMPKIN(), function(CarvedPumpkin $block) : Writer{
|
||||
return Writer::create(Ids::CARVED_PUMPKIN)
|
||||
@ -1193,10 +1235,7 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
->writeLegacyHorizontalFacing($block->getFacing())
|
||||
->writeInt(StateNames::BOOKS_STORED, $flags);
|
||||
});
|
||||
$this->map(Blocks::CHISELED_QUARTZ(), fn(SimplePillar $block) => Helper::encodeQuartz(StringValues::CHISEL_TYPE_CHISELED, $block->getAxis()));
|
||||
$this->map(Blocks::CHISELED_RED_SANDSTONE(), fn() => Helper::encodeSandstone(Ids::RED_SANDSTONE, StringValues::SAND_STONE_TYPE_HEIROGLYPHS));
|
||||
$this->map(Blocks::CHISELED_SANDSTONE(), fn() => Helper::encodeSandstone(Ids::SANDSTONE, StringValues::SAND_STONE_TYPE_HEIROGLYPHS));
|
||||
$this->map(Blocks::CHISELED_STONE_BRICKS(), fn() => Helper::encodeStoneBricks(StringValues::STONE_BRICK_TYPE_CHISELED));
|
||||
$this->map(Blocks::CHISELED_QUARTZ(), fn(SimplePillar $block) => Helper::encodeQuartz($block->getAxis(), Writer::create(Ids::CHISELED_QUARTZ_BLOCK)));
|
||||
$this->map(Blocks::CHORUS_FLOWER(), function(ChorusFlower $block) : Writer{
|
||||
return Writer::create(Ids::CHORUS_FLOWER)
|
||||
->writeInt(StateNames::AGE, $block->getAge());
|
||||
@ -1204,9 +1243,9 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
$this->mapSlab(Blocks::COBBLED_DEEPSLATE_SLAB(), Ids::COBBLED_DEEPSLATE_SLAB, Ids::COBBLED_DEEPSLATE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::COBBLED_DEEPSLATE_STAIRS(), Ids::COBBLED_DEEPSLATE_STAIRS);
|
||||
$this->map(Blocks::COBBLED_DEEPSLATE_WALL(), fn(Wall $block) => Helper::encodeWall($block, new Writer(Ids::COBBLED_DEEPSLATE_WALL)));
|
||||
$this->map(Blocks::COBBLESTONE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab1($block, Ids::COBBLESTONE_SLAB, StringValues::STONE_SLAB_TYPE_COBBLESTONE));
|
||||
$this->mapSlab(Blocks::COBBLESTONE_SLAB(), Ids::COBBLESTONE_SLAB, Ids::COBBLESTONE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::COBBLESTONE_STAIRS(), Ids::STONE_STAIRS);
|
||||
$this->map(Blocks::COBBLESTONE_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_COBBLESTONE));
|
||||
$this->map(Blocks::COBBLESTONE_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::COBBLESTONE_WALL)));
|
||||
$this->map(Blocks::COPPER(), function(Copper $block) : Writer{
|
||||
$oxidation = $block->getOxidation();
|
||||
return new Writer($block->isWaxed() ?
|
||||
@ -1214,6 +1253,40 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
Helper::selectCopperId($oxidation, Ids::COPPER_BLOCK, Ids::EXPOSED_COPPER, Ids::WEATHERED_COPPER, Ids::OXIDIZED_COPPER)
|
||||
);
|
||||
});
|
||||
$this->map(Blocks::CHISELED_COPPER(), function(Copper $block) : Writer{
|
||||
$oxidation = $block->getOxidation();
|
||||
return new Writer($block->isWaxed() ?
|
||||
Helper::selectCopperId($oxidation,
|
||||
Ids::WAXED_CHISELED_COPPER,
|
||||
Ids::WAXED_EXPOSED_CHISELED_COPPER,
|
||||
Ids::WAXED_WEATHERED_CHISELED_COPPER,
|
||||
Ids::WAXED_OXIDIZED_CHISELED_COPPER
|
||||
) :
|
||||
Helper::selectCopperId($oxidation,
|
||||
Ids::CHISELED_COPPER,
|
||||
Ids::EXPOSED_CHISELED_COPPER,
|
||||
Ids::WEATHERED_CHISELED_COPPER,
|
||||
Ids::OXIDIZED_CHISELED_COPPER
|
||||
)
|
||||
);
|
||||
});
|
||||
$this->map(Blocks::COPPER_GRATE(), function(CopperGrate $block) : Writer{
|
||||
$oxidation = $block->getOxidation();
|
||||
return new Writer($block->isWaxed() ?
|
||||
Helper::selectCopperId($oxidation,
|
||||
Ids::WAXED_COPPER_GRATE,
|
||||
Ids::WAXED_EXPOSED_COPPER_GRATE,
|
||||
Ids::WAXED_WEATHERED_COPPER_GRATE,
|
||||
Ids::WAXED_OXIDIZED_COPPER_GRATE
|
||||
) :
|
||||
Helper::selectCopperId($oxidation,
|
||||
Ids::COPPER_GRATE,
|
||||
Ids::EXPOSED_COPPER_GRATE,
|
||||
Ids::WEATHERED_COPPER_GRATE,
|
||||
Ids::OXIDIZED_COPPER_GRATE
|
||||
)
|
||||
);
|
||||
});
|
||||
$this->map(Blocks::CUT_COPPER(), function(Copper $block) : Writer{
|
||||
$oxidation = $block->getOxidation();
|
||||
return new Writer($block->isWaxed() ?
|
||||
@ -1281,20 +1354,76 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
)
|
||||
);
|
||||
});
|
||||
$this->map(Blocks::COPPER_BULB(), function(CopperBulb $block) : Writer{
|
||||
$oxidation = $block->getOxidation();
|
||||
return Writer::create($block->isWaxed() ?
|
||||
Helper::selectCopperId($oxidation,
|
||||
Ids::WAXED_COPPER_BULB,
|
||||
Ids::WAXED_EXPOSED_COPPER_BULB,
|
||||
Ids::WAXED_WEATHERED_COPPER_BULB,
|
||||
Ids::WAXED_OXIDIZED_COPPER_BULB) :
|
||||
Helper::selectCopperId($oxidation,
|
||||
Ids::COPPER_BULB,
|
||||
Ids::EXPOSED_COPPER_BULB,
|
||||
Ids::WEATHERED_COPPER_BULB,
|
||||
Ids::OXIDIZED_COPPER_BULB
|
||||
))
|
||||
->writeBool(StateNames::LIT, $block->isLit())
|
||||
->writeBool(StateNames::POWERED_BIT, $block->isPowered());
|
||||
});
|
||||
$this->map(Blocks::COPPER_DOOR(), function(CopperDoor $block) : Writer{
|
||||
$oxidation = $block->getOxidation();
|
||||
return Helper::encodeDoor(
|
||||
$block,
|
||||
new Writer($block->isWaxed() ?
|
||||
Helper::selectCopperId(
|
||||
$oxidation,
|
||||
Ids::WAXED_COPPER_DOOR,
|
||||
Ids::WAXED_EXPOSED_COPPER_DOOR,
|
||||
Ids::WAXED_WEATHERED_COPPER_DOOR,
|
||||
Ids::WAXED_OXIDIZED_COPPER_DOOR
|
||||
) :
|
||||
Helper::selectCopperId(
|
||||
$oxidation,
|
||||
Ids::COPPER_DOOR,
|
||||
Ids::EXPOSED_COPPER_DOOR,
|
||||
Ids::WEATHERED_COPPER_DOOR,
|
||||
Ids::OXIDIZED_COPPER_DOOR
|
||||
)
|
||||
)
|
||||
);
|
||||
});
|
||||
$this->map(Blocks::COPPER_TRAPDOOR(), function(CopperTrapdoor $block) : Writer{
|
||||
$oxidation = $block->getOxidation();
|
||||
return Helper::encodeTrapdoor(
|
||||
$block,
|
||||
new Writer($block->isWaxed() ?
|
||||
Helper::selectCopperId(
|
||||
$oxidation,
|
||||
Ids::WAXED_COPPER_TRAPDOOR,
|
||||
Ids::WAXED_EXPOSED_COPPER_TRAPDOOR,
|
||||
Ids::WAXED_WEATHERED_COPPER_TRAPDOOR,
|
||||
Ids::WAXED_OXIDIZED_COPPER_TRAPDOOR
|
||||
) :
|
||||
Helper::selectCopperId(
|
||||
$oxidation,
|
||||
Ids::COPPER_TRAPDOOR,
|
||||
Ids::EXPOSED_COPPER_TRAPDOOR,
|
||||
Ids::WEATHERED_COPPER_TRAPDOOR,
|
||||
Ids::OXIDIZED_COPPER_TRAPDOOR
|
||||
)
|
||||
)
|
||||
);
|
||||
});
|
||||
$this->map(Blocks::COCOA_POD(), function(CocoaBlock $block) : Writer{
|
||||
return Writer::create(Ids::COCOA)
|
||||
->writeInt(StateNames::AGE, $block->getAge())
|
||||
->writeLegacyHorizontalFacing(Facing::opposite($block->getFacing()));
|
||||
});
|
||||
$this->map(Blocks::COMPOUND_CREATOR(), fn(ChemistryTable $block) => Helper::encodeChemistryTable($block, StringValues::CHEMISTRY_TABLE_TYPE_COMPOUND_CREATOR, new Writer(Ids::CHEMISTRY_TABLE)));
|
||||
$this->map(Blocks::CRACKED_STONE_BRICKS(), fn() => Helper::encodeStoneBricks(StringValues::STONE_BRICK_TYPE_CRACKED));
|
||||
$this->map(Blocks::CUT_RED_SANDSTONE(), fn() => Helper::encodeSandstone(Ids::RED_SANDSTONE, StringValues::SAND_STONE_TYPE_CUT));
|
||||
$this->map(Blocks::CUT_RED_SANDSTONE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab4($block, StringValues::STONE_SLAB_TYPE_4_CUT_RED_SANDSTONE));
|
||||
$this->map(Blocks::CUT_SANDSTONE(), fn() => Helper::encodeSandstone(Ids::SANDSTONE, StringValues::SAND_STONE_TYPE_CUT));
|
||||
$this->map(Blocks::CUT_SANDSTONE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab4($block, StringValues::STONE_SLAB_TYPE_4_CUT_SANDSTONE));
|
||||
$this->map(Blocks::DARK_PRISMARINE(), fn() => Writer::create(Ids::PRISMARINE)
|
||||
->writeString(StateNames::PRISMARINE_BLOCK_TYPE, StringValues::PRISMARINE_BLOCK_TYPE_DARK));
|
||||
$this->map(Blocks::DARK_PRISMARINE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab2($block, StringValues::STONE_SLAB_TYPE_2_PRISMARINE_DARK));
|
||||
$this->map(Blocks::COMPOUND_CREATOR(), fn(ChemistryTable $block) => Helper::encodeChemistryTable($block, Writer::create(Ids::COMPOUND_CREATOR)));
|
||||
$this->mapSlab(Blocks::CUT_RED_SANDSTONE_SLAB(), Ids::CUT_RED_SANDSTONE_SLAB, Ids::CUT_RED_SANDSTONE_DOUBLE_SLAB);
|
||||
$this->mapSlab(Blocks::CUT_SANDSTONE_SLAB(), Ids::CUT_SANDSTONE_SLAB, Ids::CUT_SANDSTONE_DOUBLE_SLAB);
|
||||
$this->mapSlab(Blocks::DARK_PRISMARINE_SLAB(), Ids::DARK_PRISMARINE_SLAB, Ids::DARK_PRISMARINE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::DARK_PRISMARINE_STAIRS(), Ids::DARK_PRISMARINE_STAIRS);
|
||||
$this->map(Blocks::DAYLIGHT_SENSOR(), function(DaylightSensor $block) : Writer{
|
||||
return Writer::create($block->isInverted() ? Ids::DAYLIGHT_DETECTOR_INVERTED : Ids::DAYLIGHT_DETECTOR)
|
||||
@ -1316,23 +1445,18 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
->writeBool(StateNames::RAIL_DATA_BIT, $block->isActivated())
|
||||
->writeInt(StateNames::RAIL_DIRECTION, $block->getShape());
|
||||
});
|
||||
$this->map(Blocks::DIORITE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab3($block, StringValues::STONE_SLAB_TYPE_3_DIORITE));
|
||||
$this->mapSlab(Blocks::DIORITE_SLAB(), Ids::DIORITE_SLAB, Ids::DIORITE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::DIORITE_STAIRS(), Ids::DIORITE_STAIRS);
|
||||
$this->map(Blocks::DIORITE_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_DIORITE));
|
||||
$this->map(Blocks::DIORITE_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::DIORITE_WALL)));
|
||||
$this->map(Blocks::DIRT(), function(Dirt $block) : Writer{
|
||||
$dirtType = $block->getDirtType();
|
||||
if($dirtType === DirtType::ROOTED){
|
||||
return new Writer(Ids::DIRT_WITH_ROOTS);
|
||||
}
|
||||
return Writer::create(Ids::DIRT)
|
||||
->writeString(StateNames::DIRT_TYPE, match($dirtType){
|
||||
DirtType::COARSE => StringValues::DIRT_TYPE_COARSE,
|
||||
DirtType::NORMAL => StringValues::DIRT_TYPE_NORMAL,
|
||||
//ROOTED was already checked above
|
||||
});
|
||||
return Writer::create(match($block->getDirtType()){
|
||||
DirtType::NORMAL => Ids::DIRT,
|
||||
DirtType::COARSE => Ids::COARSE_DIRT,
|
||||
DirtType::ROOTED => Ids::DIRT_WITH_ROOTS,
|
||||
});
|
||||
});
|
||||
$this->map(Blocks::DOUBLE_TALLGRASS(), fn(DoubleTallGrass $block) => Helper::encodeDoublePlant($block, Writer::create(Ids::TALL_GRASS)));
|
||||
$this->map(Blocks::ELEMENT_CONSTRUCTOR(), fn(ChemistryTable $block) => Helper::encodeChemistryTable($block, StringValues::CHEMISTRY_TABLE_TYPE_ELEMENT_CONSTRUCTOR, new Writer(Ids::CHEMISTRY_TABLE)));
|
||||
$this->map(Blocks::ELEMENT_CONSTRUCTOR(), fn(ChemistryTable $block) => Helper::encodeChemistryTable($block, Writer::create(Ids::ELEMENT_CONSTRUCTOR)));
|
||||
$this->map(Blocks::ENDER_CHEST(), function(EnderChest $block) : Writer{
|
||||
return Writer::create(Ids::ENDER_CHEST)
|
||||
->writeCardinalHorizontalFacing($block->getFacing());
|
||||
@ -1346,10 +1470,10 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
return Writer::create(Ids::END_ROD)
|
||||
->writeEndRodFacingDirection($block->getFacing());
|
||||
});
|
||||
$this->map(Blocks::END_STONE_BRICK_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab3($block, StringValues::STONE_SLAB_TYPE_3_END_STONE_BRICK));
|
||||
$this->mapSlab(Blocks::END_STONE_BRICK_SLAB(), Ids::END_STONE_BRICK_SLAB, Ids::END_STONE_BRICK_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::END_STONE_BRICK_STAIRS(), Ids::END_BRICK_STAIRS);
|
||||
$this->map(Blocks::END_STONE_BRICK_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_END_BRICK));
|
||||
$this->map(Blocks::FAKE_WOODEN_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab1($block, Ids::PETRIFIED_OAK_SLAB, StringValues::STONE_SLAB_TYPE_WOOD));
|
||||
$this->map(Blocks::END_STONE_BRICK_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::END_STONE_BRICK_WALL)));
|
||||
$this->mapSlab(Blocks::FAKE_WOODEN_SLAB(), Ids::PETRIFIED_OAK_SLAB, Ids::PETRIFIED_OAK_DOUBLE_SLAB);
|
||||
$this->map(Blocks::FARMLAND(), function(Farmland $block) : Writer{
|
||||
return Writer::create(Ids::FARMLAND)
|
||||
->writeInt(StateNames::MOISTURIZED_AMOUNT, $block->getWetness());
|
||||
@ -1380,10 +1504,10 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
->writeFacingFlags($block->getFaces());
|
||||
});
|
||||
$this->map(Blocks::GLOWING_ITEM_FRAME(), fn(ItemFrame $block) => Helper::encodeItemFrame($block, Ids::GLOW_FRAME));
|
||||
$this->map(Blocks::GRANITE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab3($block, StringValues::STONE_SLAB_TYPE_3_GRANITE));
|
||||
$this->mapSlab(Blocks::GRANITE_SLAB(), Ids::GRANITE_SLAB, Ids::GRANITE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::GRANITE_STAIRS(), Ids::GRANITE_STAIRS);
|
||||
$this->map(Blocks::GRANITE_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_GRANITE));
|
||||
$this->map(Blocks::GREEN_TORCH(), fn(Torch $block) => Helper::encodeColoredTorch($block, true, Writer::create(Ids::COLORED_TORCH_RG)));
|
||||
$this->map(Blocks::GRANITE_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::GRANITE_WALL)));
|
||||
$this->map(Blocks::GREEN_TORCH(), fn(Torch $block) => Helper::encodeTorch($block, Writer::create(Ids::COLORED_TORCH_GREEN)));
|
||||
$this->map(Blocks::HAY_BALE(), function(HayBale $block) : Writer{
|
||||
return Writer::create(Ids::HAY_BLOCK)
|
||||
->writeInt(StateNames::DEPRECATED, 0)
|
||||
@ -1394,22 +1518,10 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
->writeBool(StateNames::TOGGLE_BIT, $block->isPowered())
|
||||
->writeFacingWithoutUp($block->getFacing());
|
||||
});
|
||||
$this->map(Blocks::INFESTED_CHISELED_STONE_BRICK(), fn() => Writer::create(Ids::MONSTER_EGG)
|
||||
->writeString(StateNames::MONSTER_EGG_STONE_TYPE, StringValues::MONSTER_EGG_STONE_TYPE_CHISELED_STONE_BRICK));
|
||||
$this->map(Blocks::INFESTED_COBBLESTONE(), fn() => Writer::create(Ids::MONSTER_EGG)
|
||||
->writeString(StateNames::MONSTER_EGG_STONE_TYPE, StringValues::MONSTER_EGG_STONE_TYPE_COBBLESTONE));
|
||||
$this->map(Blocks::INFESTED_CRACKED_STONE_BRICK(), fn() => Writer::create(Ids::MONSTER_EGG)
|
||||
->writeString(StateNames::MONSTER_EGG_STONE_TYPE, StringValues::MONSTER_EGG_STONE_TYPE_CRACKED_STONE_BRICK));
|
||||
$this->map(Blocks::INFESTED_MOSSY_STONE_BRICK(), fn() => Writer::create(Ids::MONSTER_EGG)
|
||||
->writeString(StateNames::MONSTER_EGG_STONE_TYPE, StringValues::MONSTER_EGG_STONE_TYPE_MOSSY_STONE_BRICK));
|
||||
$this->map(Blocks::INFESTED_STONE(), fn() => Writer::create(Ids::MONSTER_EGG)
|
||||
->writeString(StateNames::MONSTER_EGG_STONE_TYPE, StringValues::MONSTER_EGG_STONE_TYPE_STONE));
|
||||
$this->map(Blocks::INFESTED_STONE_BRICK(), fn() => Writer::create(Ids::MONSTER_EGG)
|
||||
->writeString(StateNames::MONSTER_EGG_STONE_TYPE, StringValues::MONSTER_EGG_STONE_TYPE_STONE_BRICK));
|
||||
$this->map(Blocks::IRON_DOOR(), fn(Door $block) => Helper::encodeDoor($block, new Writer(Ids::IRON_DOOR)));
|
||||
$this->map(Blocks::IRON_TRAPDOOR(), fn(Trapdoor $block) => Helper::encodeTrapdoor($block, new Writer(Ids::IRON_TRAPDOOR)));
|
||||
$this->map(Blocks::ITEM_FRAME(), fn(ItemFrame $block) => Helper::encodeItemFrame($block, Ids::FRAME));
|
||||
$this->map(Blocks::LAB_TABLE(), fn(ChemistryTable $block) => Helper::encodeChemistryTable($block, StringValues::CHEMISTRY_TABLE_TYPE_LAB_TABLE, new Writer(Ids::CHEMISTRY_TABLE)));
|
||||
$this->map(Blocks::LAB_TABLE(), fn(ChemistryTable $block) => Helper::encodeChemistryTable($block, Writer::create(Ids::LAB_TABLE)));
|
||||
$this->map(Blocks::LADDER(), function(Ladder $block) : Writer{
|
||||
return Writer::create(Ids::LADDER)
|
||||
->writeHorizontalFacing($block->getFacing());
|
||||
@ -1440,8 +1552,25 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
});
|
||||
});
|
||||
$this->map(Blocks::LIGHT(), function(Light $block) : Writer{
|
||||
return Writer::create(Ids::LIGHT_BLOCK)
|
||||
->writeInt(StateNames::BLOCK_LIGHT_LEVEL, $block->getLightLevel());
|
||||
return Writer::create(match($block->getLightLevel()){
|
||||
0 => Ids::LIGHT_BLOCK_0,
|
||||
1 => Ids::LIGHT_BLOCK_1,
|
||||
2 => Ids::LIGHT_BLOCK_2,
|
||||
3 => Ids::LIGHT_BLOCK_3,
|
||||
4 => Ids::LIGHT_BLOCK_4,
|
||||
5 => Ids::LIGHT_BLOCK_5,
|
||||
6 => Ids::LIGHT_BLOCK_6,
|
||||
7 => Ids::LIGHT_BLOCK_7,
|
||||
8 => Ids::LIGHT_BLOCK_8,
|
||||
9 => Ids::LIGHT_BLOCK_9,
|
||||
10 => Ids::LIGHT_BLOCK_10,
|
||||
11 => Ids::LIGHT_BLOCK_11,
|
||||
12 => Ids::LIGHT_BLOCK_12,
|
||||
13 => Ids::LIGHT_BLOCK_13,
|
||||
14 => Ids::LIGHT_BLOCK_14,
|
||||
15 => Ids::LIGHT_BLOCK_15,
|
||||
default => throw new BlockStateSerializeException("Invalid light level " . $block->getLightLevel()),
|
||||
});
|
||||
});
|
||||
$this->map(Blocks::LIGHTNING_ROD(), function(LightningRod $block) : Writer{
|
||||
return Writer::create(Ids::LIGHTNING_ROD)
|
||||
@ -1456,29 +1585,24 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
return Writer::create(Ids::LOOM)
|
||||
->writeLegacyHorizontalFacing($block->getFacing());
|
||||
});
|
||||
$this->map(Blocks::MATERIAL_REDUCER(), fn(ChemistryTable $block) => Helper::encodeChemistryTable($block, StringValues::CHEMISTRY_TABLE_TYPE_MATERIAL_REDUCER, new Writer(Ids::CHEMISTRY_TABLE)));
|
||||
$this->map(Blocks::MATERIAL_REDUCER(), fn(ChemistryTable $block) => Helper::encodeChemistryTable($block, Writer::create(Ids::MATERIAL_REDUCER)));
|
||||
$this->map(Blocks::MELON_STEM(), fn(MelonStem $block) => Helper::encodeStem($block, new Writer(Ids::MELON_STEM)));
|
||||
$this->map(Blocks::MOB_HEAD(), function(MobHead $block) : Writer{
|
||||
return Writer::create(Ids::SKULL)
|
||||
->writeFacingWithoutDown($block->getFacing());
|
||||
});
|
||||
$this->map(Blocks::MOSSY_COBBLESTONE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab2($block, StringValues::STONE_SLAB_TYPE_2_MOSSY_COBBLESTONE));
|
||||
$this->mapSlab(Blocks::MOSSY_COBBLESTONE_SLAB(), Ids::MOSSY_COBBLESTONE_SLAB, Ids::MOSSY_COBBLESTONE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::MOSSY_COBBLESTONE_STAIRS(), Ids::MOSSY_COBBLESTONE_STAIRS);
|
||||
$this->map(Blocks::MOSSY_COBBLESTONE_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_MOSSY_COBBLESTONE));
|
||||
$this->map(Blocks::MOSSY_STONE_BRICKS(), fn() => Helper::encodeStoneBricks(StringValues::STONE_BRICK_TYPE_MOSSY));
|
||||
$this->map(Blocks::MOSSY_STONE_BRICK_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab4($block, StringValues::STONE_SLAB_TYPE_4_MOSSY_STONE_BRICK));
|
||||
$this->map(Blocks::MOSSY_COBBLESTONE_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::MOSSY_COBBLESTONE_WALL)));
|
||||
$this->mapSlab(Blocks::MOSSY_STONE_BRICK_SLAB(), Ids::MOSSY_STONE_BRICK_SLAB, Ids::MOSSY_STONE_BRICK_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::MOSSY_STONE_BRICK_STAIRS(), Ids::MOSSY_STONE_BRICK_STAIRS);
|
||||
$this->map(Blocks::MOSSY_STONE_BRICK_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_MOSSY_STONE_BRICK));
|
||||
$this->map(Blocks::MOSSY_STONE_BRICK_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::MOSSY_STONE_BRICK_WALL)));
|
||||
$this->mapSlab(Blocks::MUD_BRICK_SLAB(), Ids::MUD_BRICK_SLAB, Ids::MUD_BRICK_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::MUD_BRICK_STAIRS(), Ids::MUD_BRICK_STAIRS);
|
||||
$this->map(Blocks::MUD_BRICK_WALL(), fn(Wall $block) => Helper::encodeWall($block, new Writer(Ids::MUD_BRICK_WALL)));
|
||||
$this->map(Blocks::MUDDY_MANGROVE_ROOTS(), fn(SimplePillar $block) => Writer::create(Ids::MUDDY_MANGROVE_ROOTS)
|
||||
->writePillarAxis($block->getAxis()));
|
||||
$this->map(Blocks::MUSHROOM_STEM(), fn() => Writer::create(Ids::BROWN_MUSHROOM_BLOCK)
|
||||
$this->map(Blocks::MUSHROOM_STEM(), fn() => Writer::create(Ids::MUSHROOM_STEM)
|
||||
->writeInt(StateNames::HUGE_MUSHROOM_BITS, BlockLegacyMetadata::MUSHROOM_BLOCK_STEM));
|
||||
$this->map(Blocks::NETHER_BRICK_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab1($block, Ids::NETHER_BRICK_SLAB, StringValues::STONE_SLAB_TYPE_NETHER_BRICK));
|
||||
$this->mapSlab(Blocks::NETHER_BRICK_SLAB(), Ids::NETHER_BRICK_SLAB, Ids::NETHER_BRICK_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::NETHER_BRICK_STAIRS(), Ids::NETHER_BRICK_STAIRS);
|
||||
$this->map(Blocks::NETHER_BRICK_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_NETHER_BRICK));
|
||||
$this->map(Blocks::NETHER_BRICK_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::NETHER_BRICK_WALL)));
|
||||
$this->map(Blocks::NETHER_PORTAL(), function(NetherPortal $block) : Writer{
|
||||
return Writer::create(Ids::PORTAL)
|
||||
->writeString(StateNames::PORTAL_AXIS, match($block->getAxis()){
|
||||
@ -1511,7 +1635,7 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
->writeInt(StateNames::GROWTH, $block->getAge() + 1 + PitcherCrop::MAX_AGE)
|
||||
->writeBool(StateNames::UPPER_BLOCK_BIT, $block->isTop());
|
||||
});
|
||||
$this->map(Blocks::POLISHED_ANDESITE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab3($block, StringValues::STONE_SLAB_TYPE_3_POLISHED_ANDESITE));
|
||||
$this->mapSlab(Blocks::POLISHED_ANDESITE_SLAB(), Ids::POLISHED_ANDESITE_SLAB, Ids::POLISHED_ANDESITE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::POLISHED_ANDESITE_STAIRS(), Ids::POLISHED_ANDESITE_STAIRS);
|
||||
$this->map(Blocks::POLISHED_BASALT(), function(SimplePillar $block) : Writer{
|
||||
return Writer::create(Ids::POLISHED_BASALT)
|
||||
@ -1528,46 +1652,40 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
$this->mapSlab(Blocks::POLISHED_DEEPSLATE_SLAB(), Ids::POLISHED_DEEPSLATE_SLAB, Ids::POLISHED_DEEPSLATE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::POLISHED_DEEPSLATE_STAIRS(), Ids::POLISHED_DEEPSLATE_STAIRS);
|
||||
$this->map(Blocks::POLISHED_DEEPSLATE_WALL(), fn(Wall $block) => Helper::encodeWall($block, new Writer(Ids::POLISHED_DEEPSLATE_WALL)));
|
||||
$this->map(Blocks::POLISHED_DIORITE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab3($block, StringValues::STONE_SLAB_TYPE_3_POLISHED_DIORITE));
|
||||
$this->mapSlab(Blocks::POLISHED_DIORITE_SLAB(), Ids::POLISHED_DIORITE_SLAB, Ids::POLISHED_DIORITE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::POLISHED_DIORITE_STAIRS(), Ids::POLISHED_DIORITE_STAIRS);
|
||||
$this->map(Blocks::POLISHED_GRANITE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab3($block, StringValues::STONE_SLAB_TYPE_3_POLISHED_GRANITE));
|
||||
$this->mapSlab(Blocks::POLISHED_GRANITE_SLAB(), Ids::POLISHED_GRANITE_SLAB, Ids::POLISHED_GRANITE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::POLISHED_GRANITE_STAIRS(), Ids::POLISHED_GRANITE_STAIRS);
|
||||
$this->mapSlab(Blocks::POLISHED_TUFF_SLAB(), Ids::POLISHED_TUFF_SLAB, Ids::POLISHED_TUFF_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::POLISHED_TUFF_STAIRS(), Ids::POLISHED_TUFF_STAIRS);
|
||||
$this->map(Blocks::POLISHED_TUFF_WALL(), fn(Wall $block) => Helper::encodeWall($block, new Writer(Ids::POLISHED_TUFF_WALL)));
|
||||
$this->map(Blocks::POTATOES(), fn(Potato $block) => Helper::encodeCrops($block, new Writer(Ids::POTATOES)));
|
||||
$this->map(Blocks::POWERED_RAIL(), function(PoweredRail $block) : Writer{
|
||||
return Writer::create(Ids::GOLDEN_RAIL)
|
||||
->writeBool(StateNames::RAIL_DATA_BIT, $block->isPowered())
|
||||
->writeInt(StateNames::RAIL_DIRECTION, $block->getShape());
|
||||
});
|
||||
$this->map(Blocks::PRISMARINE(), fn() => Writer::create(Ids::PRISMARINE)
|
||||
->writeString(StateNames::PRISMARINE_BLOCK_TYPE, StringValues::PRISMARINE_BLOCK_TYPE_DEFAULT));
|
||||
$this->map(Blocks::PRISMARINE_BRICKS(), fn() => Writer::create(Ids::PRISMARINE)
|
||||
->writeString(StateNames::PRISMARINE_BLOCK_TYPE, StringValues::PRISMARINE_BLOCK_TYPE_BRICKS));
|
||||
$this->map(Blocks::PRISMARINE_BRICKS_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab2($block, StringValues::STONE_SLAB_TYPE_2_PRISMARINE_BRICK));
|
||||
$this->mapSlab(Blocks::PRISMARINE_BRICKS_SLAB(), Ids::PRISMARINE_BRICK_SLAB, Ids::PRISMARINE_BRICK_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::PRISMARINE_BRICKS_STAIRS(), Ids::PRISMARINE_BRICKS_STAIRS);
|
||||
$this->map(Blocks::PRISMARINE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab2($block, StringValues::STONE_SLAB_TYPE_2_PRISMARINE_ROUGH));
|
||||
$this->mapSlab(Blocks::PRISMARINE_SLAB(), Ids::PRISMARINE_SLAB, Ids::PRISMARINE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::PRISMARINE_STAIRS(), Ids::PRISMARINE_STAIRS);
|
||||
$this->map(Blocks::PRISMARINE_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_PRISMARINE));
|
||||
$this->map(Blocks::PRISMARINE_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::PRISMARINE_WALL)));
|
||||
$this->map(Blocks::PUMPKIN(), function() : Writer{
|
||||
return Writer::create(Ids::PUMPKIN)
|
||||
->writeCardinalHorizontalFacing(Facing::SOUTH); //no longer used
|
||||
});
|
||||
$this->map(Blocks::PUMPKIN_STEM(), fn(PumpkinStem $block) => Helper::encodeStem($block, new Writer(Ids::PUMPKIN_STEM)));
|
||||
$this->map(Blocks::PURPLE_TORCH(), fn(Torch $block) => Helper::encodeColoredTorch($block, true, Writer::create(Ids::COLORED_TORCH_BP)));
|
||||
$this->map(Blocks::PURPUR(), function() : Writer{
|
||||
return Writer::create(Ids::PURPUR_BLOCK)
|
||||
->writeString(StateNames::CHISEL_TYPE, StringValues::CHISEL_TYPE_DEFAULT)
|
||||
->writePillarAxis(Axis::Y); //useless, but MCPE wants it
|
||||
});
|
||||
$this->map(Blocks::PURPUR(), fn() => Writer::create(Ids::PURPUR_BLOCK)->writePillarAxis(Axis::Y));
|
||||
$this->map(Blocks::PURPLE_TORCH(), fn(Torch $block) => Helper::encodeTorch($block, Writer::create(Ids::COLORED_TORCH_PURPLE)));
|
||||
$this->map(Blocks::PURPUR_PILLAR(), function(SimplePillar $block) : Writer{
|
||||
return Writer::create(Ids::PURPUR_BLOCK)
|
||||
->writeString(StateNames::CHISEL_TYPE, StringValues::CHISEL_TYPE_LINES)
|
||||
return Writer::create(Ids::PURPUR_PILLAR)
|
||||
->writePillarAxis($block->getAxis());
|
||||
});
|
||||
$this->map(Blocks::PURPUR_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab2($block, StringValues::STONE_SLAB_TYPE_2_PURPUR));
|
||||
$this->mapSlab(Blocks::PURPUR_SLAB(), Ids::PURPUR_SLAB, Ids::PURPUR_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::PURPUR_STAIRS(), Ids::PURPUR_STAIRS);
|
||||
$this->map(Blocks::QUARTZ(), fn() => Helper::encodeQuartz(StringValues::CHISEL_TYPE_DEFAULT, Axis::Y));
|
||||
$this->map(Blocks::QUARTZ_PILLAR(), fn(SimplePillar $block) => Helper::encodeQuartz(StringValues::CHISEL_TYPE_LINES, $block->getAxis()));
|
||||
$this->map(Blocks::QUARTZ_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab1($block, Ids::QUARTZ_SLAB, StringValues::STONE_SLAB_TYPE_QUARTZ));
|
||||
$this->map(Blocks::QUARTZ(), fn() => Helper::encodeQuartz(Axis::Y, Writer::create(Ids::QUARTZ_BLOCK)));
|
||||
$this->map(Blocks::QUARTZ_PILLAR(), fn(SimplePillar $block) => Helper::encodeQuartz($block->getAxis(), Writer::create(Ids::QUARTZ_PILLAR)));
|
||||
$this->mapSlab(Blocks::QUARTZ_SLAB(), Ids::QUARTZ_SLAB, Ids::QUARTZ_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::QUARTZ_STAIRS(), Ids::QUARTZ_STAIRS);
|
||||
$this->map(Blocks::RAIL(), function(Rail $block) : Writer{
|
||||
return Writer::create(Ids::RAIL)
|
||||
@ -1595,23 +1713,17 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
->writeInt(StateNames::REDSTONE_SIGNAL, $block->getOutputSignalStrength());
|
||||
});
|
||||
$this->map(Blocks::RED_MUSHROOM_BLOCK(), fn(RedMushroomBlock $block) => Helper::encodeMushroomBlock($block, new Writer(Ids::RED_MUSHROOM_BLOCK)));
|
||||
$this->map(Blocks::RED_NETHER_BRICK_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab2($block, StringValues::STONE_SLAB_TYPE_2_RED_NETHER_BRICK));
|
||||
$this->mapSlab(Blocks::RED_NETHER_BRICK_SLAB(), Ids::RED_NETHER_BRICK_SLAB, Ids::RED_NETHER_BRICK_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::RED_NETHER_BRICK_STAIRS(), Ids::RED_NETHER_BRICK_STAIRS);
|
||||
$this->map(Blocks::RED_NETHER_BRICK_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_RED_NETHER_BRICK));
|
||||
$this->map(Blocks::RED_SAND(), fn() => Writer::create(Ids::SAND)
|
||||
->writeString(StateNames::SAND_TYPE, StringValues::SAND_TYPE_RED));
|
||||
$this->map(Blocks::RED_SANDSTONE(), fn() => Helper::encodeSandstone(Ids::RED_SANDSTONE, StringValues::SAND_STONE_TYPE_DEFAULT));
|
||||
$this->map(Blocks::RED_SANDSTONE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab2($block, StringValues::STONE_SLAB_TYPE_2_RED_SANDSTONE));
|
||||
$this->map(Blocks::RED_NETHER_BRICK_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::RED_NETHER_BRICK_WALL)));
|
||||
$this->mapSlab(Blocks::RED_SANDSTONE_SLAB(), Ids::RED_SANDSTONE_SLAB, Ids::RED_SANDSTONE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::RED_SANDSTONE_STAIRS(), Ids::RED_SANDSTONE_STAIRS);
|
||||
$this->map(Blocks::RED_SANDSTONE_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_RED_SANDSTONE));
|
||||
$this->map(Blocks::RED_TORCH(), fn(Torch $block) => Helper::encodeColoredTorch($block, false, Writer::create(Ids::COLORED_TORCH_RG)));
|
||||
$this->map(Blocks::RED_SANDSTONE_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::RED_SANDSTONE_WALL)));
|
||||
$this->map(Blocks::RED_TORCH(), fn(Torch $block) => Helper::encodeTorch($block, Writer::create(Ids::COLORED_TORCH_RED)));
|
||||
$this->map(Blocks::ROSE_BUSH(), fn(DoublePlant $block) => Helper::encodeDoublePlant($block, Writer::create(Ids::ROSE_BUSH)));
|
||||
$this->map(Blocks::SAND(), fn() => Writer::create(Ids::SAND)
|
||||
->writeString(StateNames::SAND_TYPE, StringValues::SAND_TYPE_NORMAL));
|
||||
$this->map(Blocks::SANDSTONE(), fn() => Helper::encodeSandstone(Ids::SANDSTONE, StringValues::SAND_STONE_TYPE_DEFAULT));
|
||||
$this->map(Blocks::SANDSTONE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab1($block, Ids::SANDSTONE_SLAB, StringValues::STONE_SLAB_TYPE_SANDSTONE));
|
||||
$this->mapSlab(Blocks::SANDSTONE_SLAB(), Ids::SANDSTONE_SLAB, Ids::SANDSTONE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::SANDSTONE_STAIRS(), Ids::SANDSTONE_STAIRS);
|
||||
$this->map(Blocks::SANDSTONE_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_SANDSTONE));
|
||||
$this->map(Blocks::SANDSTONE_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::SANDSTONE_WALL)));
|
||||
$this->map(Blocks::SEA_PICKLE(), function(SeaPickle $block) : Writer{
|
||||
return Writer::create(Ids::SEA_PICKLE)
|
||||
->writeBool(StateNames::DEAD_BIT, !$block->isUnderwater())
|
||||
@ -1623,21 +1735,24 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
->writeBool(StateNames::UPPER_BLOCK_BIT, $block->isTop());
|
||||
});
|
||||
$this->map(Blocks::SMOKER(), fn(Furnace $block) => Helper::encodeFurnace($block, Ids::SMOKER, Ids::LIT_SMOKER));
|
||||
$this->map(Blocks::SMOOTH_QUARTZ(), fn() => Helper::encodeQuartz(StringValues::CHISEL_TYPE_SMOOTH, Axis::Y));
|
||||
$this->map(Blocks::SMOOTH_QUARTZ_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab4($block, StringValues::STONE_SLAB_TYPE_4_SMOOTH_QUARTZ));
|
||||
$this->map(Blocks::SMOOTH_QUARTZ(), fn() => Helper::encodeQuartz(Axis::Y, Writer::create(Ids::SMOOTH_QUARTZ)));
|
||||
$this->mapSlab(Blocks::SMOOTH_QUARTZ_SLAB(), Ids::SMOOTH_QUARTZ_SLAB, Ids::SMOOTH_QUARTZ_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::SMOOTH_QUARTZ_STAIRS(), Ids::SMOOTH_QUARTZ_STAIRS);
|
||||
$this->map(Blocks::SMOOTH_RED_SANDSTONE(), fn() => Helper::encodeSandstone(Ids::RED_SANDSTONE, StringValues::SAND_STONE_TYPE_SMOOTH));
|
||||
$this->map(Blocks::SMOOTH_RED_SANDSTONE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab3($block, StringValues::STONE_SLAB_TYPE_3_SMOOTH_RED_SANDSTONE));
|
||||
$this->mapSlab(Blocks::SMOOTH_RED_SANDSTONE_SLAB(), Ids::SMOOTH_RED_SANDSTONE_SLAB, Ids::SMOOTH_RED_SANDSTONE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::SMOOTH_RED_SANDSTONE_STAIRS(), Ids::SMOOTH_RED_SANDSTONE_STAIRS);
|
||||
$this->map(Blocks::SMOOTH_SANDSTONE(), fn() => Helper::encodeSandstone(Ids::SANDSTONE, StringValues::SAND_STONE_TYPE_SMOOTH));
|
||||
$this->map(Blocks::SMOOTH_SANDSTONE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab2($block, StringValues::STONE_SLAB_TYPE_2_SMOOTH_SANDSTONE));
|
||||
$this->mapSlab(Blocks::SMOOTH_SANDSTONE_SLAB(), Ids::SMOOTH_SANDSTONE_SLAB, Ids::SMOOTH_SANDSTONE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::SMOOTH_SANDSTONE_STAIRS(), Ids::SMOOTH_SANDSTONE_STAIRS);
|
||||
$this->map(Blocks::SMOOTH_STONE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab1($block, Ids::SMOOTH_STONE_SLAB, StringValues::STONE_SLAB_TYPE_SMOOTH_STONE));
|
||||
$this->mapSlab(Blocks::SMOOTH_STONE_SLAB(), Ids::SMOOTH_STONE_SLAB, Ids::SMOOTH_STONE_DOUBLE_SLAB);
|
||||
$this->map(Blocks::SNOW_LAYER(), function(SnowLayer $block) : Writer{
|
||||
return Writer::create(Ids::SNOW_LAYER)
|
||||
->writeBool(StateNames::COVERED_BIT, false)
|
||||
->writeInt(StateNames::HEIGHT, $block->getLayers() - 1);
|
||||
});
|
||||
$this->map(Blocks::SOUL_CAMPFIRE(), function(SoulCampfire $block) : Writer{
|
||||
return Writer::create(Ids::SOUL_CAMPFIRE)
|
||||
->writeCardinalHorizontalFacing($block->getFacing())
|
||||
->writeBool(StateNames::EXTINGUISHED, !$block->isLit());
|
||||
});
|
||||
$this->map(Blocks::SOUL_FIRE(), function() : Writer{
|
||||
return Writer::create(Ids::SOUL_FIRE)
|
||||
->writeInt(StateNames::AGE, 0); //useless for soul fire, we don't track it
|
||||
@ -1650,19 +1765,15 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
return Writer::create(Ids::SOUL_TORCH)
|
||||
->writeTorchFacing($block->getFacing());
|
||||
});
|
||||
$this->map(Blocks::SPONGE(), function(Sponge $block) : Writer{
|
||||
return Writer::create(Ids::SPONGE)
|
||||
->writeString(StateNames::SPONGE_TYPE, $block->isWet() ? StringValues::SPONGE_TYPE_WET : StringValues::SPONGE_TYPE_DRY);
|
||||
});
|
||||
$this->map(Blocks::SPONGE(), fn(Sponge $block) => Writer::create($block->isWet() ? Ids::WET_SPONGE : Ids::SPONGE));
|
||||
$this->map(Blocks::STONECUTTER(), fn(Stonecutter $block) => Writer::create(Ids::STONECUTTER_BLOCK)
|
||||
->writeCardinalHorizontalFacing($block->getFacing()));
|
||||
$this->map(Blocks::STONE_BRICKS(), fn() => Helper::encodeStoneBricks(StringValues::STONE_BRICK_TYPE_DEFAULT));
|
||||
$this->map(Blocks::STONE_BRICK_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab1($block, Ids::STONE_BRICK_SLAB, StringValues::STONE_SLAB_TYPE_STONE_BRICK));
|
||||
$this->mapSlab(Blocks::STONE_BRICK_SLAB(), Ids::STONE_BRICK_SLAB, Ids::STONE_BRICK_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::STONE_BRICK_STAIRS(), Ids::STONE_BRICK_STAIRS);
|
||||
$this->map(Blocks::STONE_BRICK_WALL(), fn(Wall $block) => Helper::encodeLegacyWall($block, StringValues::WALL_BLOCK_TYPE_STONE_BRICK));
|
||||
$this->map(Blocks::STONE_BRICK_WALL(), fn(Wall $block) => Helper::encodeWall($block, Writer::create(Ids::STONE_BRICK_WALL)));
|
||||
$this->map(Blocks::STONE_BUTTON(), fn(StoneButton $block) => Helper::encodeButton($block, new Writer(Ids::STONE_BUTTON)));
|
||||
$this->map(Blocks::STONE_PRESSURE_PLATE(), fn(StonePressurePlate $block) => Helper::encodeSimplePressurePlate($block, new Writer(Ids::STONE_PRESSURE_PLATE)));
|
||||
$this->map(Blocks::STONE_SLAB(), fn(Slab $block) => Helper::encodeStoneSlab4($block, StringValues::STONE_SLAB_TYPE_4_STONE));
|
||||
$this->mapSlab(Blocks::STONE_SLAB(), Ids::NORMAL_STONE_SLAB, Ids::NORMAL_STONE_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::STONE_STAIRS(), Ids::NORMAL_STONE_STAIRS);
|
||||
$this->map(Blocks::SUGARCANE(), function(Sugarcane $block) : Writer{
|
||||
return Writer::create(Ids::REEDS)
|
||||
@ -1673,11 +1784,9 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
return Writer::create(Ids::SWEET_BERRY_BUSH)
|
||||
->writeInt(StateNames::GROWTH, $block->getAge());
|
||||
});
|
||||
$this->map(Blocks::TNT(), function(TNT $block) : Writer{
|
||||
return Writer::create(Ids::TNT)
|
||||
->writeBool(StateNames::ALLOW_UNDERWATER_BIT, $block->worksUnderwater())
|
||||
->writeBool(StateNames::EXPLODE_BIT, $block->isUnstable());
|
||||
});
|
||||
$this->map(Blocks::TNT(), fn(TNT $block) => Writer::create($block->worksUnderwater() ? Ids::UNDERWATER_TNT : Ids::TNT)
|
||||
->writeBool(StateNames::EXPLODE_BIT, $block->isUnstable())
|
||||
);
|
||||
$this->map(Blocks::TORCH(), function(Torch $block) : Writer{
|
||||
return Writer::create(Ids::TORCH)
|
||||
->writeTorchFacing($block->getFacing());
|
||||
@ -1703,6 +1812,12 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
->writeBool(StateNames::POWERED_BIT, $block->isPowered())
|
||||
->writeLegacyHorizontalFacing($block->getFacing());
|
||||
});
|
||||
$this->mapSlab(Blocks::TUFF_BRICK_SLAB(), Ids::TUFF_BRICK_SLAB, Ids::TUFF_BRICK_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::TUFF_BRICK_STAIRS(), Ids::TUFF_BRICK_STAIRS);
|
||||
$this->map(Blocks::TUFF_BRICK_WALL(), fn(Wall $block) => Helper::encodeWall($block, new Writer(Ids::TUFF_BRICK_WALL)));
|
||||
$this->mapSlab(Blocks::TUFF_SLAB(), Ids::TUFF_SLAB, Ids::TUFF_DOUBLE_SLAB);
|
||||
$this->mapStairs(Blocks::TUFF_STAIRS(), Ids::TUFF_STAIRS);
|
||||
$this->map(Blocks::TUFF_WALL(), fn(Wall $block) => Helper::encodeWall($block, new Writer(Ids::TUFF_WALL)));
|
||||
$this->map(Blocks::TWISTING_VINES(), function(NetherVines $block) : Writer{
|
||||
return Writer::create(Ids::TWISTING_VINES)
|
||||
->writeInt(StateNames::TWISTING_VINES_AGE, $block->getAge());
|
||||
@ -1719,17 +1834,6 @@ final class BlockObjectToStateSerializer implements BlockStateSerializer{
|
||||
return Writer::create(Ids::WALL_BANNER)
|
||||
->writeHorizontalFacing($block->getFacing());
|
||||
});
|
||||
$this->map(Blocks::WALL_CORAL_FAN(), function(WallCoralFan $block) : Writer{
|
||||
$coralType = $block->getCoralType();
|
||||
return Writer::create(match($coralType){
|
||||
CoralType::TUBE, CoralType::BRAIN => Ids::CORAL_FAN_HANG,
|
||||
CoralType::BUBBLE, CoralType::FIRE => Ids::CORAL_FAN_HANG2,
|
||||
CoralType::HORN => Ids::CORAL_FAN_HANG3,
|
||||
})
|
||||
->writeBool(StateNames::CORAL_HANG_TYPE_BIT, $coralType === CoralType::BRAIN || $coralType === CoralType::FIRE)
|
||||
->writeBool(StateNames::DEAD_BIT, $block->isDead())
|
||||
->writeCoralFacing($block->getFacing());
|
||||
});
|
||||
$this->map(Blocks::WATER(), fn(Water $block) => Helper::encodeLiquid($block, Ids::WATER, Ids::FLOWING_WATER));
|
||||
$this->map(Blocks::WEEPING_VINES(), function(NetherVines $block) : Writer{
|
||||
return Writer::create(Ids::WEEPING_VINES)
|
||||
|
@ -26,9 +26,6 @@ namespace pocketmine\data\bedrock\block\convert;
|
||||
use pocketmine\block\Block;
|
||||
use pocketmine\block\Button;
|
||||
use pocketmine\block\Candle;
|
||||
use pocketmine\block\Copper;
|
||||
use pocketmine\block\CopperSlab;
|
||||
use pocketmine\block\CopperStairs;
|
||||
use pocketmine\block\Crops;
|
||||
use pocketmine\block\DaylightSensor;
|
||||
use pocketmine\block\Door;
|
||||
@ -48,11 +45,10 @@ use pocketmine\block\Slab;
|
||||
use pocketmine\block\Stair;
|
||||
use pocketmine\block\Stem;
|
||||
use pocketmine\block\Trapdoor;
|
||||
use pocketmine\block\utils\CopperMaterial;
|
||||
use pocketmine\block\utils\CopperOxidation;
|
||||
use pocketmine\block\utils\SlabType;
|
||||
use pocketmine\block\VanillaBlocks;
|
||||
use pocketmine\block\Wall;
|
||||
use pocketmine\block\WallCoralFan;
|
||||
use pocketmine\block\WallSign;
|
||||
use pocketmine\block\WeightedPressurePlate;
|
||||
use pocketmine\block\Wood;
|
||||
@ -60,7 +56,6 @@ use pocketmine\data\bedrock\block\BlockLegacyMetadata;
|
||||
use pocketmine\data\bedrock\block\BlockStateDeserializeException;
|
||||
use pocketmine\data\bedrock\block\BlockStateNames;
|
||||
use pocketmine\data\bedrock\block\BlockStateNames as StateNames;
|
||||
use pocketmine\data\bedrock\block\BlockStateStringValues as StringValues;
|
||||
use pocketmine\data\bedrock\MushroomBlockTypeIdMap;
|
||||
use pocketmine\math\Axis;
|
||||
use pocketmine\math\Facing;
|
||||
@ -102,24 +97,24 @@ final class BlockStateDeserializerHelper{
|
||||
}
|
||||
|
||||
/**
|
||||
* @phpstan-template TBlock of Copper|CopperSlab|CopperStairs
|
||||
* @phpstan-template TBlock of CopperMaterial
|
||||
*
|
||||
* @phpstan-param TBlock $block
|
||||
* @phpstan-return TBlock
|
||||
*/
|
||||
public static function decodeCopper(Copper|CopperSlab|CopperStairs $block, CopperOxidation $oxidation) : Copper|CopperSlab|CopperStairs{
|
||||
public static function decodeCopper(CopperMaterial $block, CopperOxidation $oxidation) : CopperMaterial{
|
||||
$block->setOxidation($oxidation);
|
||||
$block->setWaxed(false);
|
||||
return $block;
|
||||
}
|
||||
|
||||
/**
|
||||
* @phpstan-template TBlock of Copper|CopperSlab|CopperStairs
|
||||
* @phpstan-template TBlock of CopperMaterial
|
||||
*
|
||||
* @phpstan-param TBlock $block
|
||||
* @phpstan-return TBlock
|
||||
*/
|
||||
public static function decodeWaxedCopper(Copper|CopperSlab|CopperStairs $block, CopperOxidation $oxidation) : Copper|CopperSlab|CopperStairs{
|
||||
public static function decodeWaxedCopper(CopperMaterial $block, CopperOxidation $oxidation) : CopperMaterial{
|
||||
$block->setOxidation($oxidation);
|
||||
$block->setWaxed(true);
|
||||
return $block;
|
||||
@ -212,8 +207,8 @@ final class BlockStateDeserializerHelper{
|
||||
/** @throws BlockStateDeserializeException */
|
||||
public static function decodeMushroomBlock(RedMushroomBlock $block, BlockStateReader $in) : Block{
|
||||
switch($type = $in->readBoundedInt(BlockStateNames::HUGE_MUSHROOM_BITS, 0, 15)){
|
||||
case BlockLegacyMetadata::MUSHROOM_BLOCK_ALL_STEM: return VanillaBlocks::ALL_SIDED_MUSHROOM_STEM();
|
||||
case BlockLegacyMetadata::MUSHROOM_BLOCK_STEM: return VanillaBlocks::MUSHROOM_STEM();
|
||||
case BlockLegacyMetadata::MUSHROOM_BLOCK_ALL_STEM:
|
||||
case BlockLegacyMetadata::MUSHROOM_BLOCK_STEM: throw new BlockStateDeserializeException("This state does not exist");
|
||||
default:
|
||||
//invalid types get left as default
|
||||
$type = MushroomBlockTypeIdMap::getInstance()->fromId($type);
|
||||
@ -288,13 +283,6 @@ final class BlockStateDeserializerHelper{
|
||||
return $block;
|
||||
}
|
||||
|
||||
/** @throws BlockStateDeserializeException */
|
||||
public static function decodeWallCoralFan(WallCoralFan $block, BlockStateReader $in) : WallCoralFan{
|
||||
return $block
|
||||
->setDead($in->readBool(BlockStateNames::DEAD_BIT))
|
||||
->setFacing($in->readCoralFacing());
|
||||
}
|
||||
|
||||
/** @throws BlockStateDeserializeException */
|
||||
public static function decodeWallSign(WallSign $block, BlockStateReader $in) : WallSign{
|
||||
return $block
|
||||
@ -305,86 +293,4 @@ final class BlockStateDeserializerHelper{
|
||||
return $block
|
||||
->setOutputSignalStrength($in->readBoundedInt(BlockStateNames::REDSTONE_SIGNAL, 0, 15));
|
||||
}
|
||||
|
||||
/** @throws BlockStateDeserializeException */
|
||||
public static function mapLegacyWallType(BlockStateReader $in) : Wall{
|
||||
return self::decodeWall(match($type = $in->readString(BlockStateNames::WALL_BLOCK_TYPE)){
|
||||
StringValues::WALL_BLOCK_TYPE_ANDESITE => VanillaBlocks::ANDESITE_WALL(),
|
||||
StringValues::WALL_BLOCK_TYPE_BRICK => VanillaBlocks::BRICK_WALL(),
|
||||
StringValues::WALL_BLOCK_TYPE_COBBLESTONE => VanillaBlocks::COBBLESTONE_WALL(),
|
||||
StringValues::WALL_BLOCK_TYPE_DIORITE => VanillaBlocks::DIORITE_WALL(),
|
||||
StringValues::WALL_BLOCK_TYPE_END_BRICK => VanillaBlocks::END_STONE_BRICK_WALL(),
|
||||
StringValues::WALL_BLOCK_TYPE_GRANITE => VanillaBlocks::GRANITE_WALL(),
|
||||
StringValues::WALL_BLOCK_TYPE_MOSSY_COBBLESTONE => VanillaBlocks::MOSSY_COBBLESTONE_WALL(),
|
||||
StringValues::WALL_BLOCK_TYPE_MOSSY_STONE_BRICK => VanillaBlocks::MOSSY_STONE_BRICK_WALL(),
|
||||
StringValues::WALL_BLOCK_TYPE_NETHER_BRICK => VanillaBlocks::NETHER_BRICK_WALL(),
|
||||
StringValues::WALL_BLOCK_TYPE_PRISMARINE => VanillaBlocks::PRISMARINE_WALL(),
|
||||
StringValues::WALL_BLOCK_TYPE_RED_NETHER_BRICK => VanillaBlocks::RED_NETHER_BRICK_WALL(),
|
||||
StringValues::WALL_BLOCK_TYPE_RED_SANDSTONE => VanillaBlocks::RED_SANDSTONE_WALL(),
|
||||
StringValues::WALL_BLOCK_TYPE_SANDSTONE => VanillaBlocks::SANDSTONE_WALL(),
|
||||
StringValues::WALL_BLOCK_TYPE_STONE_BRICK => VanillaBlocks::STONE_BRICK_WALL(),
|
||||
default => throw $in->badValueException(BlockStateNames::WALL_BLOCK_TYPE, $type),
|
||||
}, $in);
|
||||
}
|
||||
|
||||
/** @throws BlockStateDeserializeException */
|
||||
public static function mapStoneSlab1Type(BlockStateReader $in) : Slab{
|
||||
//* stone_slab_type (StringTag) = brick, cobblestone, nether_brick, quartz, sandstone, smooth_stone, stone_brick, wood
|
||||
return match($type = $in->readString(BlockStateNames::STONE_SLAB_TYPE)){
|
||||
StringValues::STONE_SLAB_TYPE_BRICK => VanillaBlocks::BRICK_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_COBBLESTONE => VanillaBlocks::COBBLESTONE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_NETHER_BRICK => VanillaBlocks::NETHER_BRICK_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_QUARTZ => VanillaBlocks::QUARTZ_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_SANDSTONE => VanillaBlocks::SANDSTONE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_SMOOTH_STONE => VanillaBlocks::SMOOTH_STONE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_STONE_BRICK => VanillaBlocks::STONE_BRICK_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_WOOD => VanillaBlocks::FAKE_WOODEN_SLAB(),
|
||||
default => throw $in->badValueException(BlockStateNames::STONE_SLAB_TYPE, $type),
|
||||
};
|
||||
}
|
||||
|
||||
/** @throws BlockStateDeserializeException */
|
||||
public static function mapStoneSlab2Type(BlockStateReader $in) : Slab{
|
||||
// * stone_slab_type_2 (StringTag) = mossy_cobblestone, prismarine_brick, prismarine_dark, prismarine_rough, purpur, red_nether_brick, red_sandstone, smooth_sandstone
|
||||
return match($type = $in->readString(BlockStateNames::STONE_SLAB_TYPE_2)){
|
||||
StringValues::STONE_SLAB_TYPE_2_MOSSY_COBBLESTONE => VanillaBlocks::MOSSY_COBBLESTONE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_2_PRISMARINE_BRICK => VanillaBlocks::PRISMARINE_BRICKS_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_2_PRISMARINE_DARK => VanillaBlocks::DARK_PRISMARINE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_2_PRISMARINE_ROUGH => VanillaBlocks::PRISMARINE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_2_PURPUR => VanillaBlocks::PURPUR_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_2_RED_NETHER_BRICK => VanillaBlocks::RED_NETHER_BRICK_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_2_RED_SANDSTONE => VanillaBlocks::RED_SANDSTONE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_2_SMOOTH_SANDSTONE => VanillaBlocks::SMOOTH_SANDSTONE_SLAB(),
|
||||
default => throw $in->badValueException(BlockStateNames::STONE_SLAB_TYPE_2, $type),
|
||||
};
|
||||
}
|
||||
|
||||
/** @throws BlockStateDeserializeException */
|
||||
public static function mapStoneSlab3Type(BlockStateReader $in) : Slab{
|
||||
// * stone_slab_type_3 (StringTag) = andesite, diorite, end_stone_brick, granite, polished_andesite, polished_diorite, polished_granite, smooth_red_sandstone
|
||||
return match($type = $in->readString(BlockStateNames::STONE_SLAB_TYPE_3)){
|
||||
StringValues::STONE_SLAB_TYPE_3_ANDESITE => VanillaBlocks::ANDESITE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_3_DIORITE => VanillaBlocks::DIORITE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_3_END_STONE_BRICK => VanillaBlocks::END_STONE_BRICK_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_3_GRANITE => VanillaBlocks::GRANITE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_3_POLISHED_ANDESITE => VanillaBlocks::POLISHED_ANDESITE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_3_POLISHED_DIORITE => VanillaBlocks::POLISHED_DIORITE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_3_POLISHED_GRANITE => VanillaBlocks::POLISHED_GRANITE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_3_SMOOTH_RED_SANDSTONE => VanillaBlocks::SMOOTH_RED_SANDSTONE_SLAB(),
|
||||
default => throw $in->badValueException(BlockStateNames::STONE_SLAB_TYPE_3, $type),
|
||||
};
|
||||
}
|
||||
|
||||
/** @throws BlockStateDeserializeException */
|
||||
public static function mapStoneSlab4Type(BlockStateReader $in) : Slab{
|
||||
// * stone_slab_type_4 (StringTag) = cut_red_sandstone, cut_sandstone, mossy_stone_brick, smooth_quartz, stone
|
||||
return match($type = $in->readString(BlockStateNames::STONE_SLAB_TYPE_4)){
|
||||
StringValues::STONE_SLAB_TYPE_4_CUT_RED_SANDSTONE => VanillaBlocks::CUT_RED_SANDSTONE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_4_CUT_SANDSTONE => VanillaBlocks::CUT_SANDSTONE_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_4_MOSSY_STONE_BRICK => VanillaBlocks::MOSSY_STONE_BRICK_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_4_SMOOTH_QUARTZ => VanillaBlocks::SMOOTH_QUARTZ_SLAB(),
|
||||
StringValues::STONE_SLAB_TYPE_4_STONE => VanillaBlocks::STONE_SLAB(),
|
||||
default => throw $in->badValueException(BlockStateNames::STONE_SLAB_TYPE_4, $type),
|
||||
};
|
||||
}
|
||||
}
|
||||
|
@ -68,9 +68,8 @@ final class BlockStateSerializerHelper{
|
||||
->writeInt(StateNames::CANDLES, $block->getCount() - 1);
|
||||
}
|
||||
|
||||
public static function encodeChemistryTable(ChemistryTable $block, string $chemistryTableType, Writer $out) : Writer{
|
||||
public static function encodeChemistryTable(ChemistryTable $block, Writer $out) : Writer{
|
||||
return $out
|
||||
->writeString(BlockStateNames::CHEMISTRY_TABLE_TYPE, $chemistryTableType)
|
||||
->writeLegacyHorizontalFacing(Facing::opposite($block->getFacing()));
|
||||
}
|
||||
|
||||
@ -78,9 +77,8 @@ final class BlockStateSerializerHelper{
|
||||
return $out->writeInt(BlockStateNames::GROWTH, $block->getAge());
|
||||
}
|
||||
|
||||
public static function encodeColoredTorch(Torch $block, bool $highBit, Writer $out) : Writer{
|
||||
public static function encodeTorch(Torch $block, Writer $out) : Writer{
|
||||
return $out
|
||||
->writeBool(BlockStateNames::COLOR_BIT, $highBit)
|
||||
->writeTorchFacing($block->getFacing());
|
||||
}
|
||||
|
||||
@ -160,16 +158,11 @@ final class BlockStateSerializerHelper{
|
||||
->writeInt(BlockStateNames::HUGE_MUSHROOM_BITS, MushroomBlockTypeIdMap::getInstance()->toId($block->getMushroomBlockType()));
|
||||
}
|
||||
|
||||
public static function encodeQuartz(string $type, int $axis) : Writer{
|
||||
return Writer::create(Ids::QUARTZ_BLOCK)
|
||||
->writeString(BlockStateNames::CHISEL_TYPE, $type)
|
||||
public static function encodeQuartz(int $axis, Writer $out) : Writer{
|
||||
return $out
|
||||
->writePillarAxis($axis); //this isn't needed for all types, but we have to write it anyway
|
||||
}
|
||||
|
||||
public static function encodeSandstone(string $id, string $type) : Writer{
|
||||
return Writer::create($id)->writeString(BlockStateNames::SAND_STONE_TYPE, $type);
|
||||
}
|
||||
|
||||
public static function encodeSapling(Sapling $block, Writer $out) : Writer{
|
||||
return $out
|
||||
->writeBool(BlockStateNames::AGE_BIT, $block->isReady());
|
||||
@ -214,36 +207,6 @@ final class BlockStateSerializerHelper{
|
||||
->writeFacingWithoutUp($facing === Facing::UP ? Facing::DOWN : $facing);
|
||||
}
|
||||
|
||||
public static function encodeStoneBricks(string $type) : Writer{
|
||||
return Writer::create(Ids::STONEBRICK)
|
||||
->writeString(BlockStateNames::STONE_BRICK_TYPE, $type);
|
||||
}
|
||||
|
||||
private static function encodeStoneSlab(Slab $block, string $singleId, string $doubleId, string $typeKey, string $typeValue) : Writer{
|
||||
return self::encodeSlab($block, $singleId, $doubleId)
|
||||
->writeString($typeKey, $typeValue);
|
||||
}
|
||||
|
||||
public static function encodeStoneSlab1(Slab $block, string $singleId, string $doubleTypeValue) : Writer{
|
||||
//1.21 made this a mess by flattening single slab IDs but not double ones
|
||||
return $block->getSlabType() === SlabType::DOUBLE ?
|
||||
self::encodeDoubleSlab($block, Ids::DOUBLE_STONE_BLOCK_SLAB)
|
||||
->writeString(BlockStateNames::STONE_SLAB_TYPE, $doubleTypeValue) :
|
||||
self::encodeSingleSlab($block, $singleId);
|
||||
}
|
||||
|
||||
public static function encodeStoneSlab2(Slab $block, string $typeValue) : Writer{
|
||||
return self::encodeStoneSlab($block, Ids::STONE_BLOCK_SLAB2, Ids::DOUBLE_STONE_BLOCK_SLAB2, BlockStateNames::STONE_SLAB_TYPE_2, $typeValue);
|
||||
}
|
||||
|
||||
public static function encodeStoneSlab3(Slab $block, string $typeValue) : Writer{
|
||||
return self::encodeStoneSlab($block, Ids::STONE_BLOCK_SLAB3, Ids::DOUBLE_STONE_BLOCK_SLAB3, BlockStateNames::STONE_SLAB_TYPE_3, $typeValue);
|
||||
}
|
||||
|
||||
public static function encodeStoneSlab4(Slab $block, string $typeValue) : Writer{
|
||||
return self::encodeStoneSlab($block, Ids::STONE_BLOCK_SLAB4, Ids::DOUBLE_STONE_BLOCK_SLAB4, BlockStateNames::STONE_SLAB_TYPE_4, $typeValue);
|
||||
}
|
||||
|
||||
public static function encodeTrapdoor(Trapdoor $block, Writer $out) : Writer{
|
||||
return $out
|
||||
->write5MinusHorizontalFacing($block->getFacing())
|
||||
@ -260,11 +223,6 @@ final class BlockStateSerializerHelper{
|
||||
->writeWallConnectionType(BlockStateNames::WALL_CONNECTION_TYPE_WEST, $block->getConnection(Facing::WEST));
|
||||
}
|
||||
|
||||
public static function encodeLegacyWall(Wall $block, string $type) : Writer{
|
||||
return self::encodeWall($block, Writer::create(Ids::COBBLESTONE_WALL))
|
||||
->writeString(BlockStateNames::WALL_BLOCK_TYPE, $type);
|
||||
}
|
||||
|
||||
public static function encodeWallSign(WallSign $block, Writer $out) : Writer{
|
||||
return $out
|
||||
->writeHorizontalFacing($block->getFacing());
|
||||
|
@ -24,12 +24,13 @@ declare(strict_types=1);
|
||||
namespace pocketmine\data\bedrock\block\convert;
|
||||
|
||||
use pocketmine\block\AmethystCluster;
|
||||
use pocketmine\block\Anvil;
|
||||
use pocketmine\block\Bamboo;
|
||||
use pocketmine\block\Block;
|
||||
use pocketmine\block\CaveVines;
|
||||
use pocketmine\block\ChorusFlower;
|
||||
use pocketmine\block\DoublePitcherCrop;
|
||||
use pocketmine\block\Light;
|
||||
use pocketmine\block\Opaque;
|
||||
use pocketmine\block\PinkPetals;
|
||||
use pocketmine\block\PitcherCrop;
|
||||
use pocketmine\block\Slab;
|
||||
@ -44,6 +45,7 @@ use pocketmine\block\utils\DripleafState;
|
||||
use pocketmine\block\utils\DyeColor;
|
||||
use pocketmine\block\utils\FroglightType;
|
||||
use pocketmine\block\utils\LeverFacing;
|
||||
use pocketmine\block\utils\MobHeadType;
|
||||
use pocketmine\block\VanillaBlocks as Blocks;
|
||||
use pocketmine\block\Wood;
|
||||
use pocketmine\data\bedrock\block\BlockLegacyMetadata;
|
||||
@ -83,6 +85,8 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->registerFlatWoodBlockDeserializers();
|
||||
$this->registerLeavesDeserializers();
|
||||
$this->registerSaplingDeserializers();
|
||||
$this->registerLightDeserializers();
|
||||
$this->registerMobHeadDeserializers();
|
||||
$this->registerSimpleDeserializers();
|
||||
$this->registerDeserializers();
|
||||
}
|
||||
@ -457,6 +461,17 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->map($aliveId, fn(Reader $in) => Blocks::CORAL_BLOCK()->setCoralType($coralType)->setDead(false));
|
||||
$this->map($deadId, fn(Reader $in) => Blocks::CORAL_BLOCK()->setCoralType($coralType)->setDead(true));
|
||||
}
|
||||
|
||||
foreach([
|
||||
[CoralType::BRAIN, Ids::BRAIN_CORAL_WALL_FAN, Ids::DEAD_BRAIN_CORAL_WALL_FAN],
|
||||
[CoralType::BUBBLE, Ids::BUBBLE_CORAL_WALL_FAN, Ids::DEAD_BUBBLE_CORAL_WALL_FAN],
|
||||
[CoralType::FIRE, Ids::FIRE_CORAL_WALL_FAN, Ids::DEAD_FIRE_CORAL_WALL_FAN],
|
||||
[CoralType::HORN, Ids::HORN_CORAL_WALL_FAN, Ids::DEAD_HORN_CORAL_WALL_FAN],
|
||||
[CoralType::TUBE, Ids::TUBE_CORAL_WALL_FAN, Ids::DEAD_TUBE_CORAL_WALL_FAN],
|
||||
] as [$coralType, $aliveId, $deadId]){
|
||||
$this->map($aliveId, fn(Reader $in) => Blocks::WALL_CORAL_FAN()->setFacing($in->readCoralFacing())->setCoralType($coralType)->setDead(false));
|
||||
$this->map($deadId, fn(Reader $in) => Blocks::WALL_CORAL_FAN()->setFacing($in->readCoralFacing())->setCoralType($coralType)->setDead(true));
|
||||
}
|
||||
}
|
||||
|
||||
private function registerCauldronDeserializers() : void{
|
||||
@ -518,10 +533,7 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->mapSimple(Ids::CHERRY_PLANKS, fn() => Blocks::CHERRY_PLANKS());
|
||||
$this->mapSlab(Ids::CHERRY_SLAB, Ids::CHERRY_DOUBLE_SLAB, fn() => Blocks::CHERRY_SLAB());
|
||||
$this->mapStairs(Ids::CHERRY_STAIRS, fn() => Blocks::CHERRY_STAIRS());
|
||||
$this->map(Ids::CHERRY_WOOD, function(Reader $in){
|
||||
$in->ignored(StateNames::STRIPPED_BIT); //this is also ignored by vanilla
|
||||
return Helper::decodeLog(Blocks::CHERRY_WOOD(), false, $in);
|
||||
});
|
||||
$this->map(Ids::CHERRY_WOOD, fn(Reader $in) => Helper::decodeLog(Blocks::CHERRY_WOOD(), false, $in));
|
||||
$this->map(Ids::STRIPPED_CHERRY_WOOD, fn(Reader $in) => Helper::decodeLog(Blocks::CHERRY_WOOD(), true, $in));
|
||||
|
||||
$this->map(Ids::CRIMSON_BUTTON, fn(Reader $in) => Helper::decodeButton(Blocks::CRIMSON_BUTTON(), $in));
|
||||
@ -578,10 +590,7 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->mapSimple(Ids::MANGROVE_PLANKS, fn() => Blocks::MANGROVE_PLANKS());
|
||||
$this->mapSlab(Ids::MANGROVE_SLAB, Ids::MANGROVE_DOUBLE_SLAB, fn() => Blocks::MANGROVE_SLAB());
|
||||
$this->mapStairs(Ids::MANGROVE_STAIRS, fn() => Blocks::MANGROVE_STAIRS());
|
||||
$this->map(Ids::MANGROVE_WOOD, function(Reader $in){
|
||||
$in->ignored(StateNames::STRIPPED_BIT); //this is also ignored by vanilla
|
||||
return Helper::decodeLog(Blocks::MANGROVE_WOOD(), false, $in);
|
||||
});
|
||||
$this->map(Ids::MANGROVE_WOOD, fn(Reader $in) => Helper::decodeLog(Blocks::MANGROVE_WOOD(), false, $in));
|
||||
$this->map(Ids::STRIPPED_MANGROVE_WOOD, fn(Reader $in) => Helper::decodeLog(Blocks::MANGROVE_WOOD(), true, $in));
|
||||
|
||||
//oak - due to age, many of these don't specify "oak", making for confusing reading
|
||||
@ -654,6 +663,43 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
}
|
||||
}
|
||||
|
||||
private function registerLightDeserializers() : void{
|
||||
foreach([
|
||||
Ids::LIGHT_BLOCK_0 => 0,
|
||||
Ids::LIGHT_BLOCK_1 => 1,
|
||||
Ids::LIGHT_BLOCK_2 => 2,
|
||||
Ids::LIGHT_BLOCK_3 => 3,
|
||||
Ids::LIGHT_BLOCK_4 => 4,
|
||||
Ids::LIGHT_BLOCK_5 => 5,
|
||||
Ids::LIGHT_BLOCK_6 => 6,
|
||||
Ids::LIGHT_BLOCK_7 => 7,
|
||||
Ids::LIGHT_BLOCK_8 => 8,
|
||||
Ids::LIGHT_BLOCK_9 => 9,
|
||||
Ids::LIGHT_BLOCK_10 => 10,
|
||||
Ids::LIGHT_BLOCK_11 => 11,
|
||||
Ids::LIGHT_BLOCK_12 => 12,
|
||||
Ids::LIGHT_BLOCK_13 => 13,
|
||||
Ids::LIGHT_BLOCK_14 => 14,
|
||||
Ids::LIGHT_BLOCK_15 => 15,
|
||||
] as $id => $level){
|
||||
$this->mapSimple($id, fn() => Blocks::LIGHT()->setLightLevel($level));
|
||||
}
|
||||
}
|
||||
|
||||
private function registerMobHeadDeserializers() : void{
|
||||
foreach([
|
||||
Ids::CREEPER_HEAD => MobHeadType::CREEPER,
|
||||
Ids::DRAGON_HEAD => MobHeadType::DRAGON,
|
||||
Ids::PIGLIN_HEAD => MobHeadType::PIGLIN,
|
||||
Ids::PLAYER_HEAD => MobHeadType::PLAYER,
|
||||
Ids::SKELETON_SKULL => MobHeadType::SKELETON,
|
||||
Ids::WITHER_SKELETON_SKULL => MobHeadType::WITHER_SKELETON,
|
||||
Ids::ZOMBIE_HEAD => MobHeadType::ZOMBIE
|
||||
] as $id => $mobHeadType){
|
||||
$this->map($id, fn(Reader $in) => Blocks::MOB_HEAD()->setMobHeadType($mobHeadType)->setFacing($in->readFacingWithoutDown()));
|
||||
}
|
||||
}
|
||||
|
||||
private function registerSimpleDeserializers() : void{
|
||||
$this->mapSimple(Ids::AIR, fn() => Blocks::AIR());
|
||||
$this->mapSimple(Ids::AMETHYST_BLOCK, fn() => Blocks::AMETHYST());
|
||||
@ -673,6 +719,11 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->mapSimple(Ids::CHISELED_DEEPSLATE, fn() => Blocks::CHISELED_DEEPSLATE());
|
||||
$this->mapSimple(Ids::CHISELED_NETHER_BRICKS, fn() => Blocks::CHISELED_NETHER_BRICKS());
|
||||
$this->mapSimple(Ids::CHISELED_POLISHED_BLACKSTONE, fn() => Blocks::CHISELED_POLISHED_BLACKSTONE());
|
||||
$this->mapSimple(Ids::CHISELED_RED_SANDSTONE, fn() => Blocks::CHISELED_RED_SANDSTONE());
|
||||
$this->mapSimple(Ids::CHISELED_SANDSTONE, fn() => Blocks::CHISELED_SANDSTONE());
|
||||
$this->mapSimple(Ids::CHISELED_STONE_BRICKS, fn() => Blocks::CHISELED_STONE_BRICKS());
|
||||
$this->mapSimple(Ids::CHISELED_TUFF, fn() => Blocks::CHISELED_TUFF());
|
||||
$this->mapSimple(Ids::CHISELED_TUFF_BRICKS, fn() => Blocks::CHISELED_TUFF_BRICKS());
|
||||
$this->mapSimple(Ids::CHORUS_PLANT, fn() => Blocks::CHORUS_PLANT());
|
||||
$this->mapSimple(Ids::CLAY, fn() => Blocks::CLAY());
|
||||
$this->mapSimple(Ids::COAL_BLOCK, fn() => Blocks::COAL());
|
||||
@ -684,9 +735,13 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->mapSimple(Ids::CRACKED_DEEPSLATE_TILES, fn() => Blocks::CRACKED_DEEPSLATE_TILES());
|
||||
$this->mapSimple(Ids::CRACKED_NETHER_BRICKS, fn() => Blocks::CRACKED_NETHER_BRICKS());
|
||||
$this->mapSimple(Ids::CRACKED_POLISHED_BLACKSTONE_BRICKS, fn() => Blocks::CRACKED_POLISHED_BLACKSTONE_BRICKS());
|
||||
$this->mapSimple(Ids::CRACKED_STONE_BRICKS, fn() => Blocks::CRACKED_STONE_BRICKS());
|
||||
$this->mapSimple(Ids::CRAFTING_TABLE, fn() => Blocks::CRAFTING_TABLE());
|
||||
$this->mapSimple(Ids::CRIMSON_ROOTS, fn() => Blocks::CRIMSON_ROOTS());
|
||||
$this->mapSimple(Ids::CRYING_OBSIDIAN, fn() => Blocks::CRYING_OBSIDIAN());
|
||||
$this->mapSimple(Ids::CUT_RED_SANDSTONE, fn() => Blocks::CUT_RED_SANDSTONE());
|
||||
$this->mapSimple(Ids::CUT_SANDSTONE, fn() => Blocks::CUT_SANDSTONE());
|
||||
$this->mapSimple(Ids::DARK_PRISMARINE, fn() => Blocks::DARK_PRISMARINE());
|
||||
$this->mapSimple(Ids::DEADBUSH, fn() => Blocks::DEAD_BUSH());
|
||||
$this->mapSimple(Ids::DEEPSLATE_BRICKS, fn() => Blocks::DEEPSLATE_BRICKS());
|
||||
$this->mapSimple(Ids::DEEPSLATE_COAL_ORE, fn() => Blocks::DEEPSLATE_COAL_ORE());
|
||||
@ -845,6 +900,12 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->mapSimple(Ids::HARDENED_CLAY, fn() => Blocks::HARDENED_CLAY());
|
||||
$this->mapSimple(Ids::HONEYCOMB_BLOCK, fn() => Blocks::HONEYCOMB());
|
||||
$this->mapSimple(Ids::ICE, fn() => Blocks::ICE());
|
||||
$this->mapSimple(Ids::INFESTED_CHISELED_STONE_BRICKS, fn() => Blocks::INFESTED_CHISELED_STONE_BRICK());
|
||||
$this->mapSimple(Ids::INFESTED_COBBLESTONE, fn() => Blocks::INFESTED_COBBLESTONE());
|
||||
$this->mapSimple(Ids::INFESTED_CRACKED_STONE_BRICKS, fn() => Blocks::INFESTED_CRACKED_STONE_BRICK());
|
||||
$this->mapSimple(Ids::INFESTED_MOSSY_STONE_BRICKS, fn() => Blocks::INFESTED_MOSSY_STONE_BRICK());
|
||||
$this->mapSimple(Ids::INFESTED_STONE, fn() => Blocks::INFESTED_STONE());
|
||||
$this->mapSimple(Ids::INFESTED_STONE_BRICKS, fn() => Blocks::INFESTED_STONE_BRICK());
|
||||
$this->mapSimple(Ids::INFO_UPDATE, fn() => Blocks::INFO_UPDATE());
|
||||
$this->mapSimple(Ids::INFO_UPDATE2, fn() => Blocks::INFO_UPDATE2());
|
||||
$this->mapSimple(Ids::INVISIBLE_BEDROCK, fn() => Blocks::INVISIBLE_BEDROCK());
|
||||
@ -859,6 +920,7 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->mapSimple(Ids::MELON_BLOCK, fn() => Blocks::MELON());
|
||||
$this->mapSimple(Ids::MOB_SPAWNER, fn() => Blocks::MONSTER_SPAWNER());
|
||||
$this->mapSimple(Ids::MOSSY_COBBLESTONE, fn() => Blocks::MOSSY_COBBLESTONE());
|
||||
$this->mapSimple(Ids::MOSSY_STONE_BRICKS, fn() => Blocks::MOSSY_STONE_BRICKS());
|
||||
$this->mapSimple(Ids::MUD, fn() => Blocks::MUD());
|
||||
$this->mapSimple(Ids::MUD_BRICKS, fn() => Blocks::MUD_BRICKS());
|
||||
$this->mapSimple(Ids::MYCELIUM, fn() => Blocks::MYCELIUM());
|
||||
@ -880,6 +942,9 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->mapSimple(Ids::POLISHED_DEEPSLATE, fn() => Blocks::POLISHED_DEEPSLATE());
|
||||
$this->mapSimple(Ids::POLISHED_DIORITE, fn() => Blocks::POLISHED_DIORITE());
|
||||
$this->mapSimple(Ids::POLISHED_GRANITE, fn() => Blocks::POLISHED_GRANITE());
|
||||
$this->mapSimple(Ids::POLISHED_TUFF, fn() => Blocks::POLISHED_TUFF());
|
||||
$this->mapSimple(Ids::PRISMARINE, fn() => Blocks::PRISMARINE());
|
||||
$this->mapSimple(Ids::PRISMARINE_BRICKS, fn() => Blocks::PRISMARINE_BRICKS());
|
||||
$this->mapSimple(Ids::QUARTZ_BRICKS, fn() => Blocks::QUARTZ_BRICKS());
|
||||
$this->mapSimple(Ids::QUARTZ_ORE, fn() => Blocks::NETHER_QUARTZ_ORE());
|
||||
$this->mapSimple(Ids::RAW_COPPER_BLOCK, fn() => Blocks::RAW_COPPER());
|
||||
@ -887,9 +952,13 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->mapSimple(Ids::RAW_IRON_BLOCK, fn() => Blocks::RAW_IRON());
|
||||
$this->mapSimple(Ids::RED_MUSHROOM, fn() => Blocks::RED_MUSHROOM());
|
||||
$this->mapSimple(Ids::RED_NETHER_BRICK, fn() => Blocks::RED_NETHER_BRICKS());
|
||||
$this->mapSimple(Ids::RED_SAND, fn() => Blocks::RED_SAND());
|
||||
$this->mapSimple(Ids::RED_SANDSTONE, fn() => Blocks::RED_SANDSTONE());
|
||||
$this->mapSimple(Ids::REDSTONE_BLOCK, fn() => Blocks::REDSTONE());
|
||||
$this->mapSimple(Ids::REINFORCED_DEEPSLATE, fn() => Blocks::REINFORCED_DEEPSLATE());
|
||||
$this->mapSimple(Ids::RESERVED6, fn() => Blocks::RESERVED6());
|
||||
$this->mapSimple(Ids::SAND, fn() => Blocks::SAND());
|
||||
$this->mapSimple(Ids::SANDSTONE, fn() => Blocks::SANDSTONE());
|
||||
$this->mapSimple(Ids::SCULK, fn() => Blocks::SCULK());
|
||||
$this->mapSimple(Ids::SEA_LANTERN, fn() => Blocks::SEA_LANTERN());
|
||||
$this->mapSimple(Ids::SHORT_GRASS, fn() => Blocks::TALL_GRASS()); //no, this is not a typo - tall_grass is now the double block, just to be confusing :(
|
||||
@ -897,23 +966,29 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->mapSimple(Ids::SLIME, fn() => Blocks::SLIME());
|
||||
$this->mapSimple(Ids::SMITHING_TABLE, fn() => Blocks::SMITHING_TABLE());
|
||||
$this->mapSimple(Ids::SMOOTH_BASALT, fn() => Blocks::SMOOTH_BASALT());
|
||||
$this->mapSimple(Ids::SMOOTH_RED_SANDSTONE, fn() => Blocks::SMOOTH_RED_SANDSTONE());
|
||||
$this->mapSimple(Ids::SMOOTH_SANDSTONE, fn() => Blocks::SMOOTH_SANDSTONE());
|
||||
$this->mapSimple(Ids::SMOOTH_STONE, fn() => Blocks::SMOOTH_STONE());
|
||||
$this->mapSimple(Ids::SNOW, fn() => Blocks::SNOW());
|
||||
$this->mapSimple(Ids::SOUL_SAND, fn() => Blocks::SOUL_SAND());
|
||||
$this->mapSimple(Ids::SOUL_SOIL, fn() => Blocks::SOUL_SOIL());
|
||||
$this->mapSimple(Ids::SPORE_BLOSSOM, fn() => Blocks::SPORE_BLOSSOM());
|
||||
$this->mapSimple(Ids::SPONGE, fn() => Blocks::SPONGE());
|
||||
$this->mapSimple(Ids::STONE, fn() => Blocks::STONE());
|
||||
$this->mapSimple(Ids::STONECUTTER, fn() => Blocks::LEGACY_STONECUTTER());
|
||||
$this->mapSimple(Ids::STONE_BRICKS, fn() => Blocks::STONE_BRICKS());
|
||||
$this->mapSimple(Ids::TINTED_GLASS, fn() => Blocks::TINTED_GLASS());
|
||||
$this->mapSimple(Ids::TORCHFLOWER, fn() => Blocks::TORCHFLOWER());
|
||||
$this->mapSimple(Ids::TUFF, fn() => Blocks::TUFF());
|
||||
$this->mapSimple(Ids::TUFF_BRICKS, fn() => Blocks::TUFF_BRICKS());
|
||||
$this->mapSimple(Ids::UNDYED_SHULKER_BOX, fn() => Blocks::SHULKER_BOX());
|
||||
$this->mapSimple(Ids::WARPED_WART_BLOCK, fn() => Blocks::WARPED_WART_BLOCK());
|
||||
$this->mapSimple(Ids::WARPED_ROOTS, fn() => Blocks::WARPED_ROOTS());
|
||||
$this->mapSimple(Ids::WATERLILY, fn() => Blocks::LILY_PAD());
|
||||
$this->mapSimple(Ids::WEB, fn() => Blocks::COBWEB());
|
||||
$this->mapSimple(Ids::WET_SPONGE, fn() => Blocks::SPONGE()->setWet(true));
|
||||
$this->mapSimple(Ids::WITHER_ROSE, fn() => Blocks::WITHER_ROSE());
|
||||
$this->mapSimple(Ids::YELLOW_FLOWER, fn() => Blocks::DANDELION());
|
||||
$this->mapSimple(Ids::DANDELION, fn() => Blocks::DANDELION());
|
||||
|
||||
$this->mapSimple(Ids::ALLIUM, fn() => Blocks::ALLIUM());
|
||||
$this->mapSimple(Ids::CORNFLOWER, fn() => Blocks::CORNFLOWER());
|
||||
@ -939,16 +1014,22 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
->setStage(AmethystCluster::STAGE_CLUSTER)
|
||||
->setFacing($in->readBlockFace());
|
||||
});
|
||||
$this->mapSlab(Ids::ANDESITE_SLAB, Ids::ANDESITE_DOUBLE_SLAB, fn() => Blocks::ANDESITE_SLAB());
|
||||
$this->mapStairs(Ids::ANDESITE_STAIRS, fn() => Blocks::ANDESITE_STAIRS());
|
||||
$this->map(Ids::ANDESITE_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::ANDESITE_WALL(), $in));
|
||||
$this->map(Ids::ANVIL, function(Reader $in) : Block{
|
||||
return Blocks::ANVIL()
|
||||
->setDamage(match($value = $in->readString(StateNames::DAMAGE)){
|
||||
StringValues::DAMAGE_UNDAMAGED => 0,
|
||||
StringValues::DAMAGE_SLIGHTLY_DAMAGED => 1,
|
||||
StringValues::DAMAGE_VERY_DAMAGED => 2,
|
||||
StringValues::DAMAGE_BROKEN => 0,
|
||||
default => throw $in->badValueException(StateNames::DAMAGE, $value),
|
||||
})
|
||||
->setDamage(Anvil::UNDAMAGED)
|
||||
->setFacing($in->readCardinalHorizontalFacing());
|
||||
});
|
||||
$this->map(Ids::CHIPPED_ANVIL, function(Reader $in) : Block{
|
||||
return Blocks::ANVIL()
|
||||
->setDamage(Anvil::SLIGHTLY_DAMAGED)
|
||||
->setFacing($in->readCardinalHorizontalFacing());
|
||||
});
|
||||
$this->map(Ids::DAMAGED_ANVIL, function(Reader $in) : Block{
|
||||
return Blocks::ANVIL()
|
||||
->setDamage(Anvil::VERY_DAMAGED)
|
||||
->setFacing($in->readCardinalHorizontalFacing());
|
||||
});
|
||||
$this->map(Ids::BAMBOO, function(Reader $in) : Block{
|
||||
@ -1029,7 +1110,14 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
->setSlot(BrewingStandSlot::SOUTHWEST, $in->readBool(StateNames::BREWING_STAND_SLOT_B_BIT))
|
||||
->setSlot(BrewingStandSlot::NORTHWEST, $in->readBool(StateNames::BREWING_STAND_SLOT_C_BIT));
|
||||
});
|
||||
$this->mapSlab(Ids::BRICK_SLAB, Ids::BRICK_DOUBLE_SLAB, fn() => Blocks::BRICK_SLAB());
|
||||
$this->mapStairs(Ids::BRICK_STAIRS, fn() => Blocks::BRICK_STAIRS());
|
||||
$this->map(Ids::BRICK_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::BRICK_WALL(), $in));
|
||||
$this->map(Ids::MUSHROOM_STEM, fn(Reader $in) => match($in->readBoundedInt(StateNames::HUGE_MUSHROOM_BITS, 0, 15)){
|
||||
BlockLegacyMetadata::MUSHROOM_BLOCK_ALL_STEM => Blocks::ALL_SIDED_MUSHROOM_STEM(),
|
||||
BlockLegacyMetadata::MUSHROOM_BLOCK_STEM => Blocks::MUSHROOM_STEM(),
|
||||
default => throw new BlockStateDeserializeException("This state does not exist"),
|
||||
});
|
||||
$this->map(Ids::BROWN_MUSHROOM_BLOCK, fn(Reader $in) => Helper::decodeMushroomBlock(Blocks::BROWN_MUSHROOM_BLOCK(), $in));
|
||||
$this->map(Ids::CACTUS, function(Reader $in) : Block{
|
||||
return Blocks::CACTUS()
|
||||
@ -1039,6 +1127,11 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
return Blocks::CAKE()
|
||||
->setBites($in->readBoundedInt(StateNames::BITE_COUNTER, 0, 6));
|
||||
});
|
||||
$this->map(Ids::CAMPFIRE, function(Reader $in) : Block{
|
||||
return Blocks::CAMPFIRE()
|
||||
->setFacing($in->readCardinalHorizontalFacing())
|
||||
->setLit(!$in->readBool(StateNames::EXTINGUISHED));
|
||||
});
|
||||
$this->map(Ids::CARROTS, fn(Reader $in) => Helper::decodeCrops(Blocks::CARROTS(), $in));
|
||||
$this->map(Ids::CARVED_PUMPKIN, function(Reader $in) : Block{
|
||||
return Blocks::CARVED_PUMPKIN()
|
||||
@ -1078,14 +1171,10 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
|
||||
return $block;
|
||||
});
|
||||
$this->map(Ids::CHEMISTRY_TABLE, function(Reader $in) : Block{
|
||||
return (match($type = $in->readString(StateNames::CHEMISTRY_TABLE_TYPE)){
|
||||
StringValues::CHEMISTRY_TABLE_TYPE_COMPOUND_CREATOR => Blocks::COMPOUND_CREATOR(),
|
||||
StringValues::CHEMISTRY_TABLE_TYPE_ELEMENT_CONSTRUCTOR => Blocks::ELEMENT_CONSTRUCTOR(),
|
||||
StringValues::CHEMISTRY_TABLE_TYPE_LAB_TABLE => Blocks::LAB_TABLE(),
|
||||
StringValues::CHEMISTRY_TABLE_TYPE_MATERIAL_REDUCER => Blocks::MATERIAL_REDUCER(),
|
||||
default => throw $in->badValueException(StateNames::CHEMISTRY_TABLE_TYPE, $type),
|
||||
})->setFacing(Facing::opposite($in->readLegacyHorizontalFacing()));
|
||||
$this->map(Ids::CHISELED_COPPER, fn() => Helper::decodeCopper(Blocks::CHISELED_COPPER(), CopperOxidation::NONE));
|
||||
$this->map(Ids::CHISELED_QUARTZ_BLOCK, function(Reader $in) : Block{
|
||||
return Blocks::CHISELED_QUARTZ()
|
||||
->setAxis($in->readPillarAxis());
|
||||
});
|
||||
$this->map(Ids::CHEST, function(Reader $in) : Block{
|
||||
return Blocks::CHEST()
|
||||
@ -1095,38 +1184,39 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
return Blocks::CHORUS_FLOWER()
|
||||
->setAge($in->readBoundedInt(StateNames::AGE, ChorusFlower::MIN_AGE, ChorusFlower::MAX_AGE));
|
||||
});
|
||||
$this->map(Ids::COARSE_DIRT, fn() => Blocks::DIRT()->setDirtType(DirtType::COARSE));
|
||||
$this->mapSlab(Ids::COBBLED_DEEPSLATE_SLAB, Ids::COBBLED_DEEPSLATE_DOUBLE_SLAB, fn() => Blocks::COBBLED_DEEPSLATE_SLAB());
|
||||
$this->mapStairs(Ids::COBBLED_DEEPSLATE_STAIRS, fn() => Blocks::COBBLED_DEEPSLATE_STAIRS());
|
||||
$this->map(Ids::COBBLED_DEEPSLATE_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::COBBLED_DEEPSLATE_WALL(), $in));
|
||||
$this->map(Ids::COBBLESTONE_WALL, fn(Reader $in) => Helper::mapLegacyWallType($in));
|
||||
$this->mapSlab(Ids::COBBLESTONE_SLAB, Ids::COBBLESTONE_DOUBLE_SLAB, fn() => Blocks::COBBLESTONE_SLAB());
|
||||
$this->map(Ids::COBBLESTONE_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::COBBLESTONE_WALL(), $in));
|
||||
$this->map(Ids::COCOA, function(Reader $in) : Block{
|
||||
return Blocks::COCOA_POD()
|
||||
->setAge($in->readBoundedInt(StateNames::AGE, 0, 2))
|
||||
->setFacing(Facing::opposite($in->readLegacyHorizontalFacing()));
|
||||
});
|
||||
$this->map(Ids::COLORED_TORCH_BP, function(Reader $in) : Block{
|
||||
return $in->readBool(StateNames::COLOR_BIT) ?
|
||||
Blocks::PURPLE_TORCH()->setFacing($in->readTorchFacing()) :
|
||||
Blocks::BLUE_TORCH()->setFacing($in->readTorchFacing());
|
||||
});
|
||||
$this->map(Ids::COLORED_TORCH_RG, function(Reader $in) : Block{
|
||||
return $in->readBool(StateNames::COLOR_BIT) ?
|
||||
Blocks::GREEN_TORCH()->setFacing($in->readTorchFacing()) :
|
||||
Blocks::RED_TORCH()->setFacing($in->readTorchFacing());
|
||||
});
|
||||
$this->map(Ids::COLORED_TORCH_BLUE, fn(Reader $in) => Blocks::BLUE_TORCH()->setFacing($in->readTorchFacing()));
|
||||
$this->map(Ids::COLORED_TORCH_GREEN, fn(Reader $in) => Blocks::GREEN_TORCH()->setFacing($in->readTorchFacing()));
|
||||
$this->map(Ids::COLORED_TORCH_PURPLE, fn(Reader $in) => Blocks::PURPLE_TORCH()->setFacing($in->readTorchFacing()));
|
||||
$this->map(Ids::COLORED_TORCH_RED, fn(Reader $in) => Blocks::RED_TORCH()->setFacing($in->readTorchFacing()));
|
||||
$this->map(Ids::COMPOUND_CREATOR, fn(Reader $in) => Blocks::COMPOUND_CREATOR()
|
||||
->setFacing(Facing::opposite($in->readLegacyHorizontalFacing()))
|
||||
);
|
||||
$this->map(Ids::COPPER_BLOCK, fn() => Helper::decodeCopper(Blocks::COPPER(), CopperOxidation::NONE));
|
||||
$this->map(Ids::COPPER_BULB, function(Reader $in) : Block{
|
||||
return Helper::decodeCopper(Blocks::COPPER_BULB(), CopperOxidation::NONE)
|
||||
->setLit($in->readBool(StateNames::LIT))
|
||||
->setPowered($in->readBool(StateNames::POWERED_BIT));
|
||||
});
|
||||
$this->map(Ids::COPPER_DOOR, fn(Reader $in) => Helper::decodeDoor(Helper::decodeCopper(Blocks::COPPER_DOOR(), CopperOxidation::NONE), $in));
|
||||
$this->map(Ids::COPPER_GRATE, fn() => Helper::decodeCopper(Blocks::COPPER_GRATE(), CopperOxidation::NONE));
|
||||
$this->map(Ids::COPPER_TRAPDOOR, fn(Reader $in) => Helper::decodeTrapdoor(Helper::decodeCopper(Blocks::COPPER_TRAPDOOR(), CopperOxidation::NONE), $in));
|
||||
$this->map(Ids::CUT_COPPER, fn() => Helper::decodeCopper(Blocks::CUT_COPPER(), CopperOxidation::NONE));
|
||||
$this->mapSlab(Ids::CUT_COPPER_SLAB, Ids::DOUBLE_CUT_COPPER_SLAB, fn() => Helper::decodeCopper(Blocks::CUT_COPPER_SLAB(), CopperOxidation::NONE));
|
||||
$this->mapStairs(Ids::CUT_COPPER_STAIRS, fn() => Helper::decodeCopper(Blocks::CUT_COPPER_STAIRS(), CopperOxidation::NONE));
|
||||
$this->map(Ids::CORAL_FAN_HANG, fn(Reader $in) => Helper::decodeWallCoralFan(Blocks::WALL_CORAL_FAN(), $in)
|
||||
->setCoralType($in->readBool(StateNames::CORAL_HANG_TYPE_BIT) ? CoralType::BRAIN : CoralType::TUBE));
|
||||
$this->map(Ids::CORAL_FAN_HANG2, fn(Reader $in) => Helper::decodeWallCoralFan(Blocks::WALL_CORAL_FAN(), $in)
|
||||
->setCoralType($in->readBool(StateNames::CORAL_HANG_TYPE_BIT) ? CoralType::FIRE : CoralType::BUBBLE));
|
||||
$this->map(Ids::CORAL_FAN_HANG3, function(Reader $in) : Block{
|
||||
$in->ignored(StateNames::CORAL_HANG_TYPE_BIT); //the game always writes this, even though it's not used
|
||||
return Helper::decodeWallCoralFan(Blocks::WALL_CORAL_FAN(), $in)
|
||||
->setCoralType(CoralType::HORN);
|
||||
});
|
||||
$this->mapSlab(Ids::CUT_RED_SANDSTONE_SLAB, Ids::CUT_RED_SANDSTONE_DOUBLE_SLAB, fn() => Blocks::CUT_RED_SANDSTONE_SLAB());
|
||||
$this->mapSlab(Ids::CUT_SANDSTONE_SLAB, Ids::CUT_SANDSTONE_DOUBLE_SLAB, fn() => Blocks::CUT_SANDSTONE_SLAB());
|
||||
$this->mapSlab(Ids::DARK_PRISMARINE_SLAB, Ids::DARK_PRISMARINE_DOUBLE_SLAB, fn() => Blocks::DARK_PRISMARINE_SLAB());
|
||||
$this->mapStairs(Ids::DARK_PRISMARINE_STAIRS, fn() => Blocks::DARK_PRISMARINE_STAIRS());
|
||||
$this->map(Ids::DAYLIGHT_DETECTOR, fn(Reader $in) => Helper::decodeDaylightSensor(Blocks::DAYLIGHT_SENSOR(), $in)
|
||||
->setInverted(false));
|
||||
@ -1148,15 +1238,10 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
->setActivated($in->readBool(StateNames::RAIL_DATA_BIT))
|
||||
->setShape($in->readBoundedInt(StateNames::RAIL_DIRECTION, 0, 5));
|
||||
});
|
||||
$this->mapSlab(Ids::DIORITE_SLAB, Ids::DIORITE_DOUBLE_SLAB, fn() => Blocks::DIORITE_SLAB());
|
||||
$this->mapStairs(Ids::DIORITE_STAIRS, fn() => Blocks::DIORITE_STAIRS());
|
||||
$this->map(Ids::DIRT, function(Reader $in) : Block{
|
||||
return Blocks::DIRT()
|
||||
->setDirtType(match($value = $in->readString(StateNames::DIRT_TYPE)){
|
||||
StringValues::DIRT_TYPE_NORMAL => DirtType::NORMAL,
|
||||
StringValues::DIRT_TYPE_COARSE => DirtType::COARSE,
|
||||
default => throw $in->badValueException(StateNames::DIRT_TYPE, $value),
|
||||
});
|
||||
});
|
||||
$this->map(Ids::DIORITE_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::DIORITE_WALL(), $in));
|
||||
$this->map(Ids::DIRT, fn() => Blocks::DIRT()->setDirtType(DirtType::NORMAL));
|
||||
$this->map(Ids::DIRT_WITH_ROOTS, fn() => Blocks::DIRT()->setDirtType(DirtType::ROOTED));
|
||||
$this->map(Ids::LARGE_FERN, fn(Reader $in) => Helper::decodeDoublePlant(Blocks::LARGE_FERN(), $in));
|
||||
$this->map(Ids::TALL_GRASS, fn(Reader $in) => Helper::decodeDoublePlant(Blocks::DOUBLE_TALLGRASS(), $in));
|
||||
@ -1164,7 +1249,11 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->map(Ids::ROSE_BUSH, fn(Reader $in) => Helper::decodeDoublePlant(Blocks::ROSE_BUSH(), $in));
|
||||
$this->map(Ids::SUNFLOWER, fn(Reader $in) => Helper::decodeDoublePlant(Blocks::SUNFLOWER(), $in));
|
||||
$this->map(Ids::LILAC, fn(Reader $in) => Helper::decodeDoublePlant(Blocks::LILAC(), $in));
|
||||
$this->map(Ids::ELEMENT_CONSTRUCTOR, fn(Reader $in) => Blocks::ELEMENT_CONSTRUCTOR()
|
||||
->setFacing(Facing::opposite($in->readLegacyHorizontalFacing()))
|
||||
);
|
||||
$this->mapStairs(Ids::END_BRICK_STAIRS, fn() => Blocks::END_STONE_BRICK_STAIRS());
|
||||
$this->map(Ids::END_STONE_BRICK_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::END_STONE_BRICK_WALL(), $in));
|
||||
$this->map(Ids::END_PORTAL_FRAME, function(Reader $in) : Block{
|
||||
return Blocks::END_PORTAL_FRAME()
|
||||
->setEye($in->readBool(StateNames::END_PORTAL_EYE_BIT))
|
||||
@ -1174,14 +1263,24 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
return Blocks::END_ROD()
|
||||
->setFacing($in->readEndRodFacingDirection());
|
||||
});
|
||||
$this->mapSlab(Ids::END_STONE_BRICK_SLAB, Ids::END_STONE_BRICK_DOUBLE_SLAB, fn() => Blocks::END_STONE_BRICK_SLAB());
|
||||
$this->map(Ids::ENDER_CHEST, function(Reader $in) : Block{
|
||||
return Blocks::ENDER_CHEST()
|
||||
->setFacing($in->readCardinalHorizontalFacing());
|
||||
});
|
||||
$this->map(Ids::EXPOSED_COPPER, fn() => Helper::decodeCopper(Blocks::COPPER(), CopperOxidation::EXPOSED));
|
||||
$this->map(Ids::EXPOSED_CHISELED_COPPER, fn() => Helper::decodeCopper(Blocks::CHISELED_COPPER(), CopperOxidation::EXPOSED));
|
||||
$this->map(Ids::EXPOSED_COPPER_GRATE, fn() => Helper::decodeCopper(Blocks::COPPER_GRATE(), CopperOxidation::EXPOSED));
|
||||
$this->map(Ids::EXPOSED_CUT_COPPER, fn() => Helper::decodeCopper(Blocks::CUT_COPPER(), CopperOxidation::EXPOSED));
|
||||
$this->mapSlab(Ids::EXPOSED_CUT_COPPER_SLAB, Ids::EXPOSED_DOUBLE_CUT_COPPER_SLAB, fn() => Helper::decodeCopper(Blocks::CUT_COPPER_SLAB(), CopperOxidation::EXPOSED));
|
||||
$this->mapStairs(Ids::EXPOSED_CUT_COPPER_STAIRS, fn() => Helper::decodeCopper(Blocks::CUT_COPPER_STAIRS(), CopperOxidation::EXPOSED));
|
||||
$this->map(Ids::EXPOSED_COPPER_BULB, function(Reader $in) : Block{
|
||||
return Helper::decodeCopper(Blocks::COPPER_BULB(), CopperOxidation::EXPOSED)
|
||||
->setLit($in->readBool(StateNames::LIT))
|
||||
->setPowered($in->readBool(StateNames::POWERED_BIT));
|
||||
});
|
||||
$this->map(Ids::EXPOSED_COPPER_DOOR, fn(Reader $in) => Helper::decodeDoor(Helper::decodeCopper(Blocks::COPPER_DOOR(), CopperOxidation::EXPOSED), $in));
|
||||
$this->map(Ids::EXPOSED_COPPER_TRAPDOOR, fn(Reader $in) => Helper::decodeTrapdoor(Helper::decodeCopper(Blocks::COPPER_TRAPDOOR(), CopperOxidation::EXPOSED), $in));
|
||||
$this->map(Ids::FARMLAND, function(Reader $in) : Block{
|
||||
return Blocks::FARMLAND()
|
||||
->setWetness($in->readBoundedInt(StateNames::MOISTURIZED_AMOUNT, 0, 7));
|
||||
@ -1213,7 +1312,9 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
->setPowered($in->readBool(StateNames::RAIL_DATA_BIT))
|
||||
->setShape($in->readBoundedInt(StateNames::RAIL_DIRECTION, 0, 5));
|
||||
});
|
||||
$this->mapSlab(Ids::GRANITE_SLAB, Ids::GRANITE_DOUBLE_SLAB, fn() => Blocks::GRANITE_SLAB());
|
||||
$this->mapStairs(Ids::GRANITE_STAIRS, fn() => Blocks::GRANITE_STAIRS());
|
||||
$this->map(Ids::GRANITE_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::GRANITE_WALL(), $in));
|
||||
$this->map(Ids::HAY_BLOCK, function(Reader $in) : Block{
|
||||
$in->ignored(StateNames::DEPRECATED);
|
||||
return Blocks::HAY_BALE()->setAxis($in->readPillarAxis());
|
||||
@ -1226,6 +1327,9 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
});
|
||||
$this->map(Ids::IRON_DOOR, fn(Reader $in) => Helper::decodeDoor(Blocks::IRON_DOOR(), $in));
|
||||
$this->map(Ids::IRON_TRAPDOOR, fn(Reader $in) => Helper::decodeTrapdoor(Blocks::IRON_TRAPDOOR(), $in));
|
||||
$this->map(Ids::LAB_TABLE, fn(Reader $in) => Blocks::LAB_TABLE()
|
||||
->setFacing(Facing::opposite($in->readLegacyHorizontalFacing()))
|
||||
);
|
||||
$this->map(Ids::LADDER, function(Reader $in) : Block{
|
||||
return Blocks::LADDER()
|
||||
->setFacing($in->readHorizontalFacing());
|
||||
@ -1260,10 +1364,6 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
default => throw $in->badValueException(StateNames::LEVER_DIRECTION, $value),
|
||||
});
|
||||
});
|
||||
$this->map(Ids::LIGHT_BLOCK, function(Reader $in) : Block{
|
||||
return Blocks::LIGHT()
|
||||
->setLightLevel($in->readBoundedInt(StateNames::BLOCK_LIGHT_LEVEL, Light::MIN_LIGHT_LEVEL, Light::MAX_LIGHT_LEVEL));
|
||||
});
|
||||
$this->map(Ids::LIGHTNING_ROD, function(Reader $in) : Block{
|
||||
return Blocks::LIGHTNING_ROD()
|
||||
->setFacing($in->readFacingDirection());
|
||||
@ -1301,25 +1401,21 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
return Blocks::LOOM()
|
||||
->setFacing($in->readLegacyHorizontalFacing());
|
||||
});
|
||||
$this->map(Ids::MATERIAL_REDUCER, fn(Reader $in) => Blocks::MATERIAL_REDUCER()
|
||||
->setFacing(Facing::opposite($in->readLegacyHorizontalFacing()))
|
||||
);
|
||||
$this->map(Ids::MEDIUM_AMETHYST_BUD, function(Reader $in) : Block{
|
||||
return Blocks::AMETHYST_CLUSTER()
|
||||
->setStage(AmethystCluster::STAGE_MEDIUM_BUD)
|
||||
->setFacing($in->readBlockFace());
|
||||
});
|
||||
$this->map(Ids::MELON_STEM, fn(Reader $in) => Helper::decodeStem(Blocks::MELON_STEM(), $in));
|
||||
$this->map(Ids::MONSTER_EGG, function(Reader $in) : Block{
|
||||
return match($type = $in->readString(StateNames::MONSTER_EGG_STONE_TYPE)){
|
||||
StringValues::MONSTER_EGG_STONE_TYPE_CHISELED_STONE_BRICK => Blocks::INFESTED_CHISELED_STONE_BRICK(),
|
||||
StringValues::MONSTER_EGG_STONE_TYPE_COBBLESTONE => Blocks::INFESTED_COBBLESTONE(),
|
||||
StringValues::MONSTER_EGG_STONE_TYPE_CRACKED_STONE_BRICK => Blocks::INFESTED_CRACKED_STONE_BRICK(),
|
||||
StringValues::MONSTER_EGG_STONE_TYPE_MOSSY_STONE_BRICK => Blocks::INFESTED_MOSSY_STONE_BRICK(),
|
||||
StringValues::MONSTER_EGG_STONE_TYPE_STONE => Blocks::INFESTED_STONE(),
|
||||
StringValues::MONSTER_EGG_STONE_TYPE_STONE_BRICK => Blocks::INFESTED_STONE_BRICK(),
|
||||
default => throw $in->badValueException(StateNames::MONSTER_EGG_STONE_TYPE, $type),
|
||||
};
|
||||
});
|
||||
$this->mapSlab(Ids::MOSSY_COBBLESTONE_SLAB, Ids::MOSSY_COBBLESTONE_DOUBLE_SLAB, fn() => Blocks::MOSSY_COBBLESTONE_SLAB());
|
||||
$this->mapStairs(Ids::MOSSY_COBBLESTONE_STAIRS, fn() => Blocks::MOSSY_COBBLESTONE_STAIRS());
|
||||
$this->map(Ids::MOSSY_COBBLESTONE_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::MOSSY_COBBLESTONE_WALL(), $in));
|
||||
$this->mapSlab(Ids::MOSSY_STONE_BRICK_SLAB, Ids::MOSSY_STONE_BRICK_DOUBLE_SLAB, fn() => Blocks::MOSSY_STONE_BRICK_SLAB());
|
||||
$this->mapStairs(Ids::MOSSY_STONE_BRICK_STAIRS, fn() => Blocks::MOSSY_STONE_BRICK_STAIRS());
|
||||
$this->map(Ids::MOSSY_STONE_BRICK_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::MOSSY_STONE_BRICK_WALL(), $in));
|
||||
$this->mapSlab(Ids::MUD_BRICK_SLAB, Ids::MUD_BRICK_DOUBLE_SLAB, fn() => Blocks::MUD_BRICK_SLAB());
|
||||
$this->mapStairs(Ids::MUD_BRICK_STAIRS, fn() => Blocks::MUD_BRICK_STAIRS());
|
||||
$this->map(Ids::MUD_BRICK_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::MUD_BRICK_WALL(), $in));
|
||||
@ -1327,18 +1423,31 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
return Blocks::MUDDY_MANGROVE_ROOTS()
|
||||
->setAxis($in->readPillarAxis());
|
||||
});
|
||||
$this->mapSlab(Ids::NETHER_BRICK_SLAB, Ids::NETHER_BRICK_DOUBLE_SLAB, fn() => Blocks::NETHER_BRICK_SLAB());
|
||||
$this->mapStairs(Ids::NETHER_BRICK_STAIRS, fn() => Blocks::NETHER_BRICK_STAIRS());
|
||||
$this->map(Ids::NETHER_BRICK_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::NETHER_BRICK_WALL(), $in));
|
||||
$this->map(Ids::NETHER_WART, function(Reader $in) : Block{
|
||||
return Blocks::NETHER_WART()
|
||||
->setAge($in->readBoundedInt(StateNames::AGE, 0, 3));
|
||||
});
|
||||
$this->mapSlab(Ids::NORMAL_STONE_SLAB, Ids::NORMAL_STONE_DOUBLE_SLAB, fn() => Blocks::STONE_SLAB());
|
||||
$this->mapStairs(Ids::NORMAL_STONE_STAIRS, fn() => Blocks::STONE_STAIRS());
|
||||
$this->map(Ids::OCHRE_FROGLIGHT, fn(Reader $in) => Blocks::FROGLIGHT()->setFroglightType(FroglightType::OCHRE)->setAxis($in->readPillarAxis()));
|
||||
$this->map(Ids::OXIDIZED_COPPER, fn() => Helper::decodeCopper(Blocks::COPPER(), CopperOxidation::OXIDIZED));
|
||||
$this->map(Ids::OXIDIZED_CHISELED_COPPER, fn() => Helper::decodeCopper(Blocks::CHISELED_COPPER(), CopperOxidation::OXIDIZED));
|
||||
$this->map(Ids::OXIDIZED_COPPER_GRATE, fn() => Helper::decodeCopper(Blocks::COPPER_GRATE(), CopperOxidation::OXIDIZED));
|
||||
$this->map(Ids::OXIDIZED_CUT_COPPER, fn() => Helper::decodeCopper(Blocks::CUT_COPPER(), CopperOxidation::OXIDIZED));
|
||||
$this->mapSlab(Ids::OXIDIZED_CUT_COPPER_SLAB, Ids::OXIDIZED_DOUBLE_CUT_COPPER_SLAB, fn() => Helper::decodeCopper(Blocks::CUT_COPPER_SLAB(), CopperOxidation::OXIDIZED));
|
||||
$this->mapStairs(Ids::OXIDIZED_CUT_COPPER_STAIRS, fn() => Helper::decodeCopper(Blocks::CUT_COPPER_STAIRS(), CopperOxidation::OXIDIZED));
|
||||
$this->map(Ids::OXIDIZED_COPPER_BULB, function(Reader $in) : Block{
|
||||
return Helper::decodeCopper(Blocks::COPPER_BULB(), CopperOxidation::OXIDIZED)
|
||||
->setLit($in->readBool(StateNames::LIT))
|
||||
->setPowered($in->readBool(StateNames::POWERED_BIT));
|
||||
});
|
||||
$this->map(Ids::OXIDIZED_COPPER_DOOR, fn(Reader $in) => Helper::decodeDoor(Helper::decodeCopper(Blocks::COPPER_DOOR(), CopperOxidation::OXIDIZED), $in));
|
||||
$this->map(Ids::OXIDIZED_COPPER_TRAPDOOR, fn(Reader $in) => Helper::decodeTrapdoor(Helper::decodeCopper(Blocks::COPPER_TRAPDOOR(), CopperOxidation::OXIDIZED), $in));
|
||||
$this->map(Ids::PEARLESCENT_FROGLIGHT, fn(Reader $in) => Blocks::FROGLIGHT()->setFroglightType(FroglightType::PEARLESCENT)->setAxis($in->readPillarAxis()));
|
||||
$this->mapSlab(Ids::PETRIFIED_OAK_SLAB, Ids::PETRIFIED_OAK_DOUBLE_SLAB, fn() => Blocks::FAKE_WOODEN_SLAB());
|
||||
$this->map(Ids::PINK_PETALS, function(Reader $in) : Block{
|
||||
//Pink petals only uses 0-3, but GROWTH state can go up to 7
|
||||
$growth = $in->readBoundedInt(StateNames::GROWTH, 0, 7);
|
||||
@ -1362,6 +1471,7 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
return Blocks::PITCHER_PLANT()
|
||||
->setTop($in->readBool(StateNames::UPPER_BLOCK_BIT));
|
||||
});
|
||||
$this->mapSlab(Ids::POLISHED_ANDESITE_SLAB, Ids::POLISHED_ANDESITE_DOUBLE_SLAB, fn() => Blocks::POLISHED_ANDESITE_SLAB());
|
||||
$this->mapStairs(Ids::POLISHED_ANDESITE_STAIRS, fn() => Blocks::POLISHED_ANDESITE_STAIRS());
|
||||
$this->map(Ids::POLISHED_BASALT, function(Reader $in) : Block{
|
||||
return Blocks::POLISHED_BASALT()
|
||||
@ -1378,8 +1488,13 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->mapSlab(Ids::POLISHED_DEEPSLATE_SLAB, Ids::POLISHED_DEEPSLATE_DOUBLE_SLAB, fn() => Blocks::POLISHED_DEEPSLATE_SLAB());
|
||||
$this->mapStairs(Ids::POLISHED_DEEPSLATE_STAIRS, fn() => Blocks::POLISHED_DEEPSLATE_STAIRS());
|
||||
$this->map(Ids::POLISHED_DEEPSLATE_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::POLISHED_DEEPSLATE_WALL(), $in));
|
||||
$this->mapSlab(Ids::POLISHED_DIORITE_SLAB, Ids::POLISHED_DIORITE_DOUBLE_SLAB, fn() => Blocks::POLISHED_DIORITE_SLAB());
|
||||
$this->mapStairs(Ids::POLISHED_DIORITE_STAIRS, fn() => Blocks::POLISHED_DIORITE_STAIRS());
|
||||
$this->mapSlab(Ids::POLISHED_GRANITE_SLAB, Ids::POLISHED_GRANITE_DOUBLE_SLAB, fn() => Blocks::POLISHED_GRANITE_SLAB());
|
||||
$this->mapStairs(Ids::POLISHED_GRANITE_STAIRS, fn() => Blocks::POLISHED_GRANITE_STAIRS());
|
||||
$this->mapSlab(Ids::POLISHED_TUFF_SLAB, Ids::POLISHED_TUFF_DOUBLE_SLAB, fn() => Blocks::POLISHED_TUFF_SLAB());
|
||||
$this->mapStairs(Ids::POLISHED_TUFF_STAIRS, fn() => Blocks::POLISHED_TUFF_STAIRS());
|
||||
$this->map(Ids::POLISHED_TUFF_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::POLISHED_TUFF_WALL(), $in));
|
||||
$this->map(Ids::PORTAL, function(Reader $in) : Block{
|
||||
return Blocks::NETHER_PORTAL()
|
||||
->setAxis(match($value = $in->readString(StateNames::PORTAL_AXIS)){
|
||||
@ -1393,15 +1508,10 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->map(Ids::POWERED_COMPARATOR, fn(Reader $in) => Helper::decodeComparator(Blocks::REDSTONE_COMPARATOR(), $in));
|
||||
$this->map(Ids::POWERED_REPEATER, fn(Reader $in) => Helper::decodeRepeater(Blocks::REDSTONE_REPEATER(), $in)
|
||||
->setPowered(true));
|
||||
$this->map(Ids::PRISMARINE, function(Reader $in) : Block{
|
||||
return match($type = $in->readString(StateNames::PRISMARINE_BLOCK_TYPE)){
|
||||
StringValues::PRISMARINE_BLOCK_TYPE_BRICKS => Blocks::PRISMARINE_BRICKS(),
|
||||
StringValues::PRISMARINE_BLOCK_TYPE_DARK => Blocks::DARK_PRISMARINE(),
|
||||
StringValues::PRISMARINE_BLOCK_TYPE_DEFAULT => Blocks::PRISMARINE(),
|
||||
default => throw $in->badValueException(StateNames::PRISMARINE_BLOCK_TYPE, $type),
|
||||
};
|
||||
});
|
||||
$this->mapSlab(Ids::PRISMARINE_BRICK_SLAB, Ids::PRISMARINE_BRICK_DOUBLE_SLAB, fn() => Blocks::PRISMARINE_BRICKS_SLAB());
|
||||
$this->mapStairs(Ids::PRISMARINE_BRICKS_STAIRS, fn() => Blocks::PRISMARINE_BRICKS_STAIRS());
|
||||
$this->map(Ids::PRISMARINE_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::PRISMARINE_WALL(), $in));
|
||||
$this->mapSlab(Ids::PRISMARINE_SLAB, Ids::PRISMARINE_DOUBLE_SLAB, fn() => Blocks::PRISMARINE_SLAB());
|
||||
$this->mapStairs(Ids::PRISMARINE_STAIRS, fn() => Blocks::PRISMARINE_STAIRS());
|
||||
$this->map(Ids::PUMPKIN, function(Reader $in) : Block{
|
||||
$in->ignored(StateNames::MC_CARDINAL_DIRECTION); //obsolete
|
||||
@ -1409,53 +1519,33 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
});
|
||||
$this->map(Ids::PUMPKIN_STEM, fn(Reader $in) => Helper::decodeStem(Blocks::PUMPKIN_STEM(), $in));
|
||||
$this->map(Ids::PURPUR_BLOCK, function(Reader $in) : Block{
|
||||
$type = $in->readString(StateNames::CHISEL_TYPE);
|
||||
if($type === StringValues::CHISEL_TYPE_LINES){
|
||||
return Blocks::PURPUR_PILLAR()->setAxis($in->readPillarAxis());
|
||||
}else{
|
||||
$in->ignored(StateNames::PILLAR_AXIS); //axis only applies to pillars
|
||||
return match($type){
|
||||
StringValues::CHISEL_TYPE_CHISELED, //TODO: bug in MCPE
|
||||
StringValues::CHISEL_TYPE_SMOOTH, //TODO: bug in MCPE
|
||||
StringValues::CHISEL_TYPE_DEFAULT => Blocks::PURPUR(),
|
||||
default => throw $in->badValueException(StateNames::CHISEL_TYPE, $type),
|
||||
};
|
||||
}
|
||||
$in->ignored(StateNames::PILLAR_AXIS); //???
|
||||
return Blocks::PURPUR();
|
||||
});
|
||||
$this->map(Ids::PURPUR_PILLAR, fn(Reader $in) => Blocks::PURPUR_PILLAR()->setAxis($in->readPillarAxis()));
|
||||
$this->mapSlab(Ids::PURPUR_SLAB, Ids::PURPUR_DOUBLE_SLAB, fn() => Blocks::PURPUR_SLAB());
|
||||
$this->mapStairs(Ids::PURPUR_STAIRS, fn() => Blocks::PURPUR_STAIRS());
|
||||
$this->map(Ids::QUARTZ_BLOCK, function(Reader $in) : Block{
|
||||
switch($type = $in->readString(StateNames::CHISEL_TYPE)){
|
||||
case StringValues::CHISEL_TYPE_CHISELED:
|
||||
return Blocks::CHISELED_QUARTZ()->setAxis($in->readPillarAxis());
|
||||
case StringValues::CHISEL_TYPE_DEFAULT:
|
||||
$in->ignored(StateNames::PILLAR_AXIS);
|
||||
return Blocks::QUARTZ();
|
||||
case StringValues::CHISEL_TYPE_LINES:
|
||||
return Blocks::QUARTZ_PILLAR()->setAxis($in->readPillarAxis());
|
||||
case StringValues::CHISEL_TYPE_SMOOTH:
|
||||
$in->ignored(StateNames::PILLAR_AXIS);
|
||||
return Blocks::SMOOTH_QUARTZ();
|
||||
default:
|
||||
throw $in->badValueException(StateNames::CHISEL_TYPE, $type);
|
||||
}
|
||||
$this->map(Ids::QUARTZ_BLOCK, function(Reader $in) : Opaque{
|
||||
$in->ignored(StateNames::PILLAR_AXIS);
|
||||
return Blocks::QUARTZ();
|
||||
});
|
||||
$this->map(Ids::QUARTZ_PILLAR, function(Reader $in) : Block{
|
||||
return Blocks::QUARTZ_PILLAR()
|
||||
->setAxis($in->readPillarAxis());
|
||||
});
|
||||
$this->mapSlab(Ids::QUARTZ_SLAB, Ids::QUARTZ_DOUBLE_SLAB, fn() => Blocks::QUARTZ_SLAB());
|
||||
$this->mapStairs(Ids::QUARTZ_STAIRS, fn() => Blocks::QUARTZ_STAIRS());
|
||||
$this->map(Ids::RAIL, function(Reader $in) : Block{
|
||||
return Blocks::RAIL()
|
||||
->setShape($in->readBoundedInt(StateNames::RAIL_DIRECTION, 0, 9));
|
||||
});
|
||||
$this->map(Ids::RED_MUSHROOM_BLOCK, fn(Reader $in) => Helper::decodeMushroomBlock(Blocks::RED_MUSHROOM_BLOCK(), $in));
|
||||
$this->mapSlab(Ids::RED_NETHER_BRICK_SLAB, Ids::RED_NETHER_BRICK_DOUBLE_SLAB, fn() => Blocks::RED_NETHER_BRICK_SLAB());
|
||||
$this->mapStairs(Ids::RED_NETHER_BRICK_STAIRS, fn() => Blocks::RED_NETHER_BRICK_STAIRS());
|
||||
$this->map(Ids::RED_SANDSTONE, function(Reader $in) : Block{
|
||||
return match($type = $in->readString(StateNames::SAND_STONE_TYPE)){
|
||||
StringValues::SAND_STONE_TYPE_CUT => Blocks::CUT_RED_SANDSTONE(),
|
||||
StringValues::SAND_STONE_TYPE_DEFAULT => Blocks::RED_SANDSTONE(),
|
||||
StringValues::SAND_STONE_TYPE_HEIROGLYPHS => Blocks::CHISELED_RED_SANDSTONE(),
|
||||
StringValues::SAND_STONE_TYPE_SMOOTH => Blocks::SMOOTH_RED_SANDSTONE(),
|
||||
default => throw $in->badValueException(StateNames::SAND_STONE_TYPE, $type),
|
||||
};
|
||||
});
|
||||
$this->map(Ids::RED_NETHER_BRICK_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::RED_NETHER_BRICK_WALL(), $in));
|
||||
$this->mapSlab(Ids::RED_SANDSTONE_SLAB, Ids::RED_SANDSTONE_DOUBLE_SLAB, fn() => Blocks::RED_SANDSTONE_SLAB());
|
||||
$this->mapStairs(Ids::RED_SANDSTONE_STAIRS, fn() => Blocks::RED_SANDSTONE_STAIRS());
|
||||
$this->map(Ids::RED_SANDSTONE_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::RED_SANDSTONE_WALL(), $in));
|
||||
$this->map(Ids::REDSTONE_LAMP, function() : Block{
|
||||
return Blocks::REDSTONE_LAMP()
|
||||
->setPowered(false);
|
||||
@ -1477,32 +1567,14 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
return Blocks::SUGARCANE()
|
||||
->setAge($in->readBoundedInt(StateNames::AGE, 0, 15));
|
||||
});
|
||||
$this->map(Ids::SAND, function(Reader $in) : Block{
|
||||
return match($value = $in->readString(StateNames::SAND_TYPE)){
|
||||
StringValues::SAND_TYPE_NORMAL => Blocks::SAND(),
|
||||
StringValues::SAND_TYPE_RED => Blocks::RED_SAND(),
|
||||
default => throw $in->badValueException(StateNames::SAND_TYPE, $value),
|
||||
};
|
||||
});
|
||||
$this->map(Ids::SANDSTONE, function(Reader $in) : Block{
|
||||
return match($type = $in->readString(StateNames::SAND_STONE_TYPE)){
|
||||
StringValues::SAND_STONE_TYPE_CUT => Blocks::CUT_SANDSTONE(),
|
||||
StringValues::SAND_STONE_TYPE_DEFAULT => Blocks::SANDSTONE(),
|
||||
StringValues::SAND_STONE_TYPE_HEIROGLYPHS => Blocks::CHISELED_SANDSTONE(),
|
||||
StringValues::SAND_STONE_TYPE_SMOOTH => Blocks::SMOOTH_SANDSTONE(),
|
||||
default => throw $in->badValueException(StateNames::SAND_STONE_TYPE, $type),
|
||||
};
|
||||
});
|
||||
$this->mapSlab(Ids::SANDSTONE_SLAB, Ids::SANDSTONE_DOUBLE_SLAB, fn() => Blocks::SANDSTONE_SLAB());
|
||||
$this->mapStairs(Ids::SANDSTONE_STAIRS, fn() => Blocks::SANDSTONE_STAIRS());
|
||||
$this->map(Ids::SANDSTONE_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::SANDSTONE_WALL(), $in));
|
||||
$this->map(Ids::SEA_PICKLE, function(Reader $in) : Block{
|
||||
return Blocks::SEA_PICKLE()
|
||||
->setCount($in->readBoundedInt(StateNames::CLUSTER_COUNT, 0, 3) + 1)
|
||||
->setUnderwater(!$in->readBool(StateNames::DEAD_BIT));
|
||||
});
|
||||
$this->map(Ids::SKULL, function(Reader $in) : Block{
|
||||
return Blocks::MOB_HEAD()
|
||||
->setFacing($in->readFacingWithoutDown());
|
||||
});
|
||||
$this->map(Ids::SMOKER, function(Reader $in) : Block{
|
||||
return Blocks::SMOKER()
|
||||
->setFacing($in->readCardinalHorizontalFacing())
|
||||
@ -1518,13 +1590,26 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
->setFacing($in->readCardinalHorizontalFacing())
|
||||
->setTop($in->readBool(StateNames::UPPER_BLOCK_BIT));
|
||||
});
|
||||
$this->map(Ids::SMOOTH_QUARTZ, function(Reader $in) : Block{
|
||||
$in->ignored(StateNames::PILLAR_AXIS);
|
||||
return Blocks::SMOOTH_QUARTZ();
|
||||
});
|
||||
$this->mapSlab(Ids::SMOOTH_QUARTZ_SLAB, Ids::SMOOTH_QUARTZ_DOUBLE_SLAB, fn() => Blocks::SMOOTH_QUARTZ_SLAB());
|
||||
$this->mapStairs(Ids::SMOOTH_QUARTZ_STAIRS, fn() => Blocks::SMOOTH_QUARTZ_STAIRS());
|
||||
$this->mapSlab(Ids::SMOOTH_RED_SANDSTONE_SLAB, Ids::SMOOTH_RED_SANDSTONE_DOUBLE_SLAB, fn() => Blocks::SMOOTH_RED_SANDSTONE_SLAB());
|
||||
$this->mapStairs(Ids::SMOOTH_RED_SANDSTONE_STAIRS, fn() => Blocks::SMOOTH_RED_SANDSTONE_STAIRS());
|
||||
$this->mapSlab(Ids::SMOOTH_SANDSTONE_SLAB, Ids::SMOOTH_SANDSTONE_DOUBLE_SLAB, fn() => Blocks::SMOOTH_SANDSTONE_SLAB());
|
||||
$this->mapStairs(Ids::SMOOTH_SANDSTONE_STAIRS, fn() => Blocks::SMOOTH_SANDSTONE_STAIRS());
|
||||
$this->mapSlab(Ids::SMOOTH_STONE_SLAB, Ids::SMOOTH_STONE_DOUBLE_SLAB, fn() => Blocks::SMOOTH_STONE_SLAB());
|
||||
$this->map(Ids::SNOW_LAYER, function(Reader $in) : Block{
|
||||
$in->ignored(StateNames::COVERED_BIT); //seems to be useless
|
||||
return Blocks::SNOW_LAYER()->setLayers($in->readBoundedInt(StateNames::HEIGHT, 0, 7) + 1);
|
||||
});
|
||||
$this->map(Ids::SOUL_CAMPFIRE, function(Reader $in) : Block{
|
||||
return Blocks::SOUL_CAMPFIRE()
|
||||
->setFacing($in->readCardinalHorizontalFacing())
|
||||
->setLit(!$in->readBool(StateNames::EXTINGUISHED));
|
||||
});
|
||||
$this->map(Ids::SOUL_FIRE, function(Reader $in) : Block{
|
||||
$in->ignored(StateNames::AGE); //this is useless for soul fire, since it doesn't have the logic associated
|
||||
return Blocks::SOUL_FIRE();
|
||||
@ -1537,46 +1622,16 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
return Blocks::SOUL_TORCH()
|
||||
->setFacing($in->readTorchFacing());
|
||||
});
|
||||
$this->map(Ids::SPONGE, function(Reader $in) : Block{
|
||||
return Blocks::SPONGE()->setWet(match($type = $in->readString(StateNames::SPONGE_TYPE)){
|
||||
StringValues::SPONGE_TYPE_DRY => false,
|
||||
StringValues::SPONGE_TYPE_WET => true,
|
||||
default => throw $in->badValueException(StateNames::SPONGE_TYPE, $type),
|
||||
});
|
||||
});
|
||||
$this->map(Ids::STANDING_BANNER, function(Reader $in) : Block{
|
||||
return Blocks::BANNER()
|
||||
->setRotation($in->readBoundedInt(StateNames::GROUND_SIGN_DIRECTION, 0, 15));
|
||||
});
|
||||
$this->mapSlab(Ids::STONE_BRICK_SLAB, Ids::STONE_BRICK_DOUBLE_SLAB, fn() => Blocks::STONE_BRICK_SLAB());
|
||||
$this->mapStairs(Ids::STONE_BRICK_STAIRS, fn() => Blocks::STONE_BRICK_STAIRS());
|
||||
$this->map(Ids::STONE_BRICK_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::STONE_BRICK_WALL(), $in));
|
||||
$this->map(Ids::STONE_BUTTON, fn(Reader $in) => Helper::decodeButton(Blocks::STONE_BUTTON(), $in));
|
||||
$this->map(Ids::STONE_PRESSURE_PLATE, fn(Reader $in) => Helper::decodeSimplePressurePlate(Blocks::STONE_PRESSURE_PLATE(), $in));
|
||||
|
||||
//mess for partially flattened slabs - the single IDs were flattened but not the double ones
|
||||
$this->map(Ids::DOUBLE_STONE_BLOCK_SLAB, fn(Reader $in) => Helper::decodeDoubleSlab(Helper::mapStoneSlab1Type($in), $in));
|
||||
$this->map(Ids::BRICK_SLAB, fn(Reader $in) => Helper::decodeSingleSlab(Blocks::BRICK_SLAB(), $in));
|
||||
$this->map(Ids::COBBLESTONE_SLAB, fn(Reader $in) => Helper::decodeSingleSlab(Blocks::COBBLESTONE_SLAB(), $in));
|
||||
$this->map(Ids::NETHER_BRICK_SLAB, fn(Reader $in) => Helper::decodeSingleSlab(Blocks::NETHER_BRICK_SLAB(), $in));
|
||||
$this->map(Ids::PETRIFIED_OAK_SLAB, fn(Reader $in) => Helper::decodeSingleSlab(Blocks::FAKE_WOODEN_SLAB(), $in));
|
||||
$this->map(Ids::QUARTZ_SLAB, fn(Reader $in) => Helper::decodeSingleSlab(Blocks::QUARTZ_SLAB(), $in));
|
||||
$this->map(Ids::SANDSTONE_SLAB, fn(Reader $in) => Helper::decodeSingleSlab(Blocks::SANDSTONE_SLAB(), $in));
|
||||
$this->map(Ids::SMOOTH_STONE_SLAB, fn(Reader $in) => Helper::decodeSingleSlab(Blocks::SMOOTH_STONE_SLAB(), $in));
|
||||
$this->map(Ids::STONE_BRICK_SLAB, fn(Reader $in) => Helper::decodeSingleSlab(Blocks::STONE_BRICK_SLAB(), $in));
|
||||
|
||||
$this->mapSlab(Ids::STONE_BLOCK_SLAB2, Ids::DOUBLE_STONE_BLOCK_SLAB2, fn(Reader $in) => Helper::mapStoneSlab2Type($in));
|
||||
$this->mapSlab(Ids::STONE_BLOCK_SLAB3, Ids::DOUBLE_STONE_BLOCK_SLAB3, fn(Reader $in) => Helper::mapStoneSlab3Type($in));
|
||||
$this->mapSlab(Ids::STONE_BLOCK_SLAB4, Ids::DOUBLE_STONE_BLOCK_SLAB4, fn(Reader $in) => Helper::mapStoneSlab4Type($in));
|
||||
$this->mapStairs(Ids::STONE_STAIRS, fn() => Blocks::COBBLESTONE_STAIRS());
|
||||
$this->map(Ids::STONEBRICK, function(Reader $in) : Block{
|
||||
return match($type = $in->readString(StateNames::STONE_BRICK_TYPE)){
|
||||
StringValues::STONE_BRICK_TYPE_SMOOTH, //TODO: bug in vanilla
|
||||
StringValues::STONE_BRICK_TYPE_DEFAULT => Blocks::STONE_BRICKS(),
|
||||
StringValues::STONE_BRICK_TYPE_CHISELED => Blocks::CHISELED_STONE_BRICKS(),
|
||||
StringValues::STONE_BRICK_TYPE_CRACKED => Blocks::CRACKED_STONE_BRICKS(),
|
||||
StringValues::STONE_BRICK_TYPE_MOSSY => Blocks::MOSSY_STONE_BRICKS(),
|
||||
default => throw $in->badValueException(StateNames::STONE_BRICK_TYPE, $type),
|
||||
};
|
||||
});
|
||||
$this->map(Ids::STONECUTTER_BLOCK, function(Reader $in) : Block{
|
||||
return Blocks::STONECUTTER()
|
||||
->setFacing($in->readCardinalHorizontalFacing());
|
||||
@ -1590,7 +1645,7 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
$this->map(Ids::TNT, function(Reader $in) : Block{
|
||||
return Blocks::TNT()
|
||||
->setUnstable($in->readBool(StateNames::EXPLODE_BIT))
|
||||
->setWorksUnderwater($in->readBool(StateNames::ALLOW_UNDERWATER_BIT));
|
||||
->setWorksUnderwater(false);
|
||||
});
|
||||
$this->map(Ids::TORCH, function(Reader $in) : Block{
|
||||
return Blocks::TORCH()
|
||||
@ -1618,10 +1673,21 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
->setFacing($in->readLegacyHorizontalFacing())
|
||||
->setPowered($in->readBool(StateNames::POWERED_BIT));
|
||||
});
|
||||
$this->mapSlab(Ids::TUFF_BRICK_SLAB, Ids::TUFF_BRICK_DOUBLE_SLAB, fn() => Blocks::TUFF_BRICK_SLAB());
|
||||
$this->mapStairs(Ids::TUFF_BRICK_STAIRS, fn() => Blocks::TUFF_BRICK_STAIRS());
|
||||
$this->map(Ids::TUFF_BRICK_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::TUFF_BRICK_WALL(), $in));
|
||||
$this->mapSlab(Ids::TUFF_SLAB, Ids::TUFF_DOUBLE_SLAB, fn() => Blocks::TUFF_SLAB());
|
||||
$this->mapStairs(Ids::TUFF_STAIRS, fn() => Blocks::TUFF_STAIRS());
|
||||
$this->map(Ids::TUFF_WALL, fn(Reader $in) => Helper::decodeWall(Blocks::TUFF_WALL(), $in));
|
||||
$this->map(Ids::TWISTING_VINES, function(Reader $in) : Block{
|
||||
return Blocks::TWISTING_VINES()
|
||||
->setAge($in->readBoundedInt(StateNames::TWISTING_VINES_AGE, 0, 25));
|
||||
});
|
||||
$this->map(Ids::UNDERWATER_TNT, function(Reader $in) : Block{
|
||||
return Blocks::TNT()
|
||||
->setUnstable($in->readBool(StateNames::EXPLODE_BIT))
|
||||
->setWorksUnderwater(true);
|
||||
});
|
||||
$this->map(Ids::UNDERWATER_TORCH, function(Reader $in) : Block{
|
||||
return Blocks::UNDERWATER_TORCH()
|
||||
->setFacing($in->readTorchFacing());
|
||||
@ -1649,25 +1715,70 @@ final class BlockStateToObjectDeserializer implements BlockStateDeserializer{
|
||||
});
|
||||
$this->map(Ids::WATER, fn(Reader $in) => Helper::decodeStillLiquid(Blocks::WATER(), $in));
|
||||
$this->map(Ids::WAXED_COPPER, fn() => Helper::decodeWaxedCopper(Blocks::COPPER(), CopperOxidation::NONE));
|
||||
$this->map(Ids::WAXED_CHISELED_COPPER, fn() => Helper::decodeWaxedCopper(Blocks::CHISELED_COPPER(), CopperOxidation::NONE));
|
||||
$this->map(Ids::WAXED_COPPER_GRATE, fn() => Helper::decodeWaxedCopper(Blocks::COPPER_GRATE(), CopperOxidation::NONE));
|
||||
$this->map(Ids::WAXED_CUT_COPPER, fn() => Helper::decodeWaxedCopper(Blocks::CUT_COPPER(), CopperOxidation::NONE));
|
||||
$this->mapSlab(Ids::WAXED_CUT_COPPER_SLAB, Ids::WAXED_DOUBLE_CUT_COPPER_SLAB, fn() => Helper::decodeWaxedCopper(Blocks::CUT_COPPER_SLAB(), CopperOxidation::NONE));
|
||||
$this->mapStairs(Ids::WAXED_CUT_COPPER_STAIRS, fn() => Helper::decodeWaxedCopper(Blocks::CUT_COPPER_STAIRS(), CopperOxidation::NONE));
|
||||
$this->map(Ids::WAXED_COPPER_BULB, function(Reader $in) : Block{
|
||||
return Helper::decodeWaxedCopper(Blocks::COPPER_BULB(), CopperOxidation::NONE)
|
||||
->setLit($in->readBool(StateNames::LIT))
|
||||
->setPowered($in->readBool(StateNames::POWERED_BIT));
|
||||
});
|
||||
$this->map(Ids::WAXED_COPPER_DOOR, fn(Reader $in) => Helper::decodeDoor(Helper::decodeWaxedCopper(Blocks::COPPER_DOOR(), CopperOxidation::NONE), $in));
|
||||
$this->map(Ids::WAXED_COPPER_TRAPDOOR, fn(Reader $in) => Helper::decodeTrapdoor(Helper::decodeWaxedCopper(Blocks::COPPER_TRAPDOOR(), CopperOxidation::NONE), $in));
|
||||
$this->map(Ids::WAXED_EXPOSED_COPPER, fn() => Helper::decodeWaxedCopper(Blocks::COPPER(), CopperOxidation::EXPOSED));
|
||||
$this->map(Ids::WAXED_EXPOSED_CHISELED_COPPER, fn() => Helper::decodeWaxedCopper(Blocks::CHISELED_COPPER(), CopperOxidation::EXPOSED));
|
||||
$this->map(Ids::WAXED_EXPOSED_COPPER_GRATE, fn() => Helper::decodeWaxedCopper(Blocks::COPPER_GRATE(), CopperOxidation::EXPOSED));
|
||||
$this->map(Ids::WAXED_EXPOSED_CUT_COPPER, fn() => Helper::decodeWaxedCopper(Blocks::CUT_COPPER(), CopperOxidation::EXPOSED));
|
||||
$this->mapSlab(Ids::WAXED_EXPOSED_CUT_COPPER_SLAB, Ids::WAXED_EXPOSED_DOUBLE_CUT_COPPER_SLAB, fn() => Helper::decodeWaxedCopper(Blocks::CUT_COPPER_SLAB(), CopperOxidation::EXPOSED));
|
||||
$this->mapStairs(Ids::WAXED_EXPOSED_CUT_COPPER_STAIRS, fn() => Helper::decodeWaxedCopper(Blocks::CUT_COPPER_STAIRS(), CopperOxidation::EXPOSED));
|
||||
$this->map(Ids::WAXED_EXPOSED_COPPER_BULB, function(Reader $in) : Block{
|
||||
return Helper::decodeWaxedCopper(Blocks::COPPER_BULB(), CopperOxidation::EXPOSED)
|
||||
->setLit($in->readBool(StateNames::LIT))
|
||||
->setPowered($in->readBool(StateNames::POWERED_BIT));
|
||||
});
|
||||
$this->map(Ids::WAXED_EXPOSED_COPPER_DOOR, fn(Reader $in) => Helper::decodeDoor(Helper::decodeWaxedCopper(Blocks::COPPER_DOOR(), CopperOxidation::EXPOSED), $in));
|
||||
$this->map(Ids::WAXED_EXPOSED_COPPER_TRAPDOOR, fn(Reader $in) => Helper::decodeTrapdoor(Helper::decodeWaxedCopper(Blocks::COPPER_TRAPDOOR(), CopperOxidation::EXPOSED), $in));
|
||||
$this->map(Ids::WAXED_OXIDIZED_COPPER, fn() => Helper::decodeWaxedCopper(Blocks::COPPER(), CopperOxidation::OXIDIZED));
|
||||
$this->map(Ids::WAXED_OXIDIZED_CHISELED_COPPER, fn() => Helper::decodeWaxedCopper(Blocks::CHISELED_COPPER(), CopperOxidation::OXIDIZED));
|
||||
$this->map(Ids::WAXED_OXIDIZED_COPPER_GRATE, fn() => Helper::decodeWaxedCopper(Blocks::COPPER_GRATE(), CopperOxidation::OXIDIZED));
|
||||
$this->map(Ids::WAXED_OXIDIZED_CUT_COPPER, fn() => Helper::decodeWaxedCopper(Blocks::CUT_COPPER(), CopperOxidation::OXIDIZED));
|
||||
$this->mapSlab(Ids::WAXED_OXIDIZED_CUT_COPPER_SLAB, Ids::WAXED_OXIDIZED_DOUBLE_CUT_COPPER_SLAB, fn() => Helper::decodeWaxedCopper(Blocks::CUT_COPPER_SLAB(), CopperOxidation::OXIDIZED));
|
||||
$this->mapStairs(Ids::WAXED_OXIDIZED_CUT_COPPER_STAIRS, fn() => Helper::decodeWaxedCopper(Blocks::CUT_COPPER_STAIRS(), CopperOxidation::OXIDIZED));
|
||||
$this->map(Ids::WAXED_OXIDIZED_COPPER_BULB, function(Reader $in) : Block{
|
||||
return Helper::decodeWaxedCopper(Blocks::COPPER_BULB(), CopperOxidation::OXIDIZED)
|
||||
->setLit($in->readBool(StateNames::LIT))
|
||||
->setPowered($in->readBool(StateNames::POWERED_BIT));
|
||||
});
|
||||
$this->map(Ids::WAXED_OXIDIZED_COPPER_DOOR, fn(Reader $in) => Helper::decodeDoor(Helper::decodeWaxedCopper(Blocks::COPPER_DOOR(), CopperOxidation::OXIDIZED), $in));
|
||||
$this->map(Ids::WAXED_OXIDIZED_COPPER_TRAPDOOR, fn(Reader $in) => Helper::decodeTrapdoor(Helper::decodeWaxedCopper(Blocks::COPPER_TRAPDOOR(), CopperOxidation::OXIDIZED), $in));
|
||||
$this->map(Ids::WAXED_WEATHERED_COPPER, fn() => Helper::decodeWaxedCopper(Blocks::COPPER(), CopperOxidation::WEATHERED));
|
||||
$this->map(Ids::WAXED_WEATHERED_CHISELED_COPPER, fn() => Helper::decodeWaxedCopper(Blocks::CHISELED_COPPER(), CopperOxidation::WEATHERED));
|
||||
$this->map(Ids::WAXED_WEATHERED_COPPER_GRATE, fn() => Helper::decodeWaxedCopper(Blocks::COPPER_GRATE(), CopperOxidation::WEATHERED));
|
||||
$this->map(Ids::WAXED_WEATHERED_CUT_COPPER, fn() => Helper::decodeWaxedCopper(Blocks::CUT_COPPER(), CopperOxidation::WEATHERED));
|
||||
$this->mapSlab(Ids::WAXED_WEATHERED_CUT_COPPER_SLAB, Ids::WAXED_WEATHERED_DOUBLE_CUT_COPPER_SLAB, fn() => Helper::decodeWaxedCopper(Blocks::CUT_COPPER_SLAB(), CopperOxidation::WEATHERED));
|
||||
$this->mapStairs(Ids::WAXED_WEATHERED_CUT_COPPER_STAIRS, fn() => Helper::decodeWaxedCopper(Blocks::CUT_COPPER_STAIRS(), CopperOxidation::WEATHERED));
|
||||
$this->map(Ids::WAXED_WEATHERED_COPPER_BULB, function(Reader $in) : Block{
|
||||
return Helper::decodeWaxedCopper(Blocks::COPPER_BULB(), CopperOxidation::WEATHERED)
|
||||
->setLit($in->readBool(StateNames::LIT))
|
||||
->setPowered($in->readBool(StateNames::POWERED_BIT));
|
||||
});
|
||||
$this->map(Ids::WAXED_WEATHERED_COPPER_DOOR, fn(Reader $in) => Helper::decodeDoor(Helper::decodeWaxedCopper(Blocks::COPPER_DOOR(), CopperOxidation::WEATHERED), $in));
|
||||
$this->map(Ids::WAXED_WEATHERED_COPPER_TRAPDOOR, fn(Reader $in) => Helper::decodeTrapdoor(Helper::decodeWaxedCopper(Blocks::COPPER_TRAPDOOR(), CopperOxidation::WEATHERED), $in));
|
||||
$this->map(Ids::WEATHERED_COPPER, fn() => Helper::decodeCopper(Blocks::COPPER(), CopperOxidation::WEATHERED));
|
||||
$this->map(Ids::WEATHERED_CHISELED_COPPER, fn() => Helper::decodeCopper(Blocks::CHISELED_COPPER(), CopperOxidation::WEATHERED));
|
||||
$this->map(Ids::WEATHERED_COPPER_GRATE, fn() => Helper::decodeCopper(Blocks::COPPER_GRATE(), CopperOxidation::WEATHERED));
|
||||
$this->map(Ids::WEATHERED_CUT_COPPER, fn() => Helper::decodeCopper(Blocks::CUT_COPPER(), CopperOxidation::WEATHERED));
|
||||
$this->mapSlab(Ids::WEATHERED_CUT_COPPER_SLAB, Ids::WEATHERED_DOUBLE_CUT_COPPER_SLAB, fn() => Helper::decodeCopper(Blocks::CUT_COPPER_SLAB(), CopperOxidation::WEATHERED));
|
||||
$this->mapStairs(Ids::WEATHERED_CUT_COPPER_STAIRS, fn() => Helper::decodeCopper(Blocks::CUT_COPPER_STAIRS(), CopperOxidation::WEATHERED));
|
||||
$this->map(Ids::WEATHERED_COPPER_BULB, function(Reader $in) : Block{
|
||||
return Helper::decodeCopper(Blocks::COPPER_BULB(), CopperOxidation::WEATHERED)
|
||||
->setLit($in->readBool(StateNames::LIT))
|
||||
->setPowered($in->readBool(StateNames::POWERED_BIT));
|
||||
});
|
||||
$this->map(Ids::WEATHERED_COPPER_DOOR, fn(Reader $in) => Helper::decodeDoor(Helper::decodeCopper(Blocks::COPPER_DOOR(), CopperOxidation::WEATHERED), $in));
|
||||
$this->map(Ids::WEATHERED_COPPER_TRAPDOOR, fn(Reader $in) => Helper::decodeTrapdoor(Helper::decodeCopper(Blocks::COPPER_TRAPDOOR(), CopperOxidation::WEATHERED), $in));
|
||||
$this->map(Ids::WEEPING_VINES, function(Reader $in) : Block{
|
||||
return Blocks::WEEPING_VINES()
|
||||
->setAge($in->readBoundedInt(StateNames::WEEPING_VINES_AGE, 0, 25));
|
||||
|
@ -23,6 +23,7 @@ declare(strict_types=1);
|
||||
|
||||
namespace pocketmine\data\bedrock\block\upgrade;
|
||||
|
||||
use pocketmine\data\bedrock\block\upgrade\BlockStateUpgradeSchemaFlattenInfo as FlattenInfo;
|
||||
use pocketmine\data\bedrock\block\upgrade\BlockStateUpgradeSchemaValueRemap as ValueRemap;
|
||||
use pocketmine\nbt\tag\Tag;
|
||||
use function count;
|
||||
@ -58,6 +59,12 @@ final class BlockStateUpgradeSchema{
|
||||
*/
|
||||
public array $remappedPropertyValues = [];
|
||||
|
||||
/**
|
||||
* @var FlattenInfo[]
|
||||
* @phpstan-var array<string, FlattenInfo>
|
||||
*/
|
||||
public array $flattenedProperties = [];
|
||||
|
||||
/**
|
||||
* @var BlockStateUpgradeSchemaBlockRemap[][]
|
||||
* @phpstan-var array<string, list<BlockStateUpgradeSchemaBlockRemap>>
|
||||
@ -93,6 +100,7 @@ final class BlockStateUpgradeSchema{
|
||||
$this->removedProperties,
|
||||
$this->renamedProperties,
|
||||
$this->remappedPropertyValues,
|
||||
$this->flattenedProperties,
|
||||
$this->remappedStates,
|
||||
] as $list){
|
||||
if(count($list) !== 0){
|
||||
|
@ -40,7 +40,7 @@ final class BlockStateUpgradeSchemaBlockRemap{
|
||||
*/
|
||||
public function __construct(
|
||||
public array $oldState,
|
||||
public string|BlockStateUpgradeSchemaFlattenedName $newName,
|
||||
public string|BlockStateUpgradeSchemaFlattenInfo $newName,
|
||||
public array $newState,
|
||||
public array $copiedState
|
||||
){}
|
||||
@ -48,8 +48,8 @@ final class BlockStateUpgradeSchemaBlockRemap{
|
||||
public function equals(self $that) : bool{
|
||||
$sameName = $this->newName === $that->newName ||
|
||||
(
|
||||
$this->newName instanceof BlockStateUpgradeSchemaFlattenedName &&
|
||||
$that->newName instanceof BlockStateUpgradeSchemaFlattenedName &&
|
||||
$this->newName instanceof BlockStateUpgradeSchemaFlattenInfo &&
|
||||
$that->newName instanceof BlockStateUpgradeSchemaFlattenInfo &&
|
||||
$this->newName->equals($that->newName)
|
||||
);
|
||||
if(!$sameName){
|
||||
|
@ -23,20 +23,25 @@ declare(strict_types=1);
|
||||
|
||||
namespace pocketmine\data\bedrock\block\upgrade;
|
||||
|
||||
use pocketmine\nbt\tag\ByteTag;
|
||||
use pocketmine\nbt\tag\IntTag;
|
||||
use pocketmine\nbt\tag\StringTag;
|
||||
use function ksort;
|
||||
use const SORT_STRING;
|
||||
|
||||
final class BlockStateUpgradeSchemaFlattenedName{
|
||||
final class BlockStateUpgradeSchemaFlattenInfo{
|
||||
|
||||
/**
|
||||
* @param string[] $flattenedValueRemaps
|
||||
* @phpstan-param array<string, string> $flattenedValueRemaps
|
||||
* @phpstan-param ?class-string<ByteTag|IntTag|StringTag> $flattenedPropertyType
|
||||
*/
|
||||
public function __construct(
|
||||
public string $prefix,
|
||||
public string $flattenedProperty,
|
||||
public string $suffix,
|
||||
public array $flattenedValueRemaps
|
||||
public array $flattenedValueRemaps,
|
||||
public ?string $flattenedPropertyType = null
|
||||
){
|
||||
ksort($this->flattenedValueRemaps, SORT_STRING);
|
||||
}
|
||||
@ -45,6 +50,7 @@ final class BlockStateUpgradeSchemaFlattenedName{
|
||||
return $this->prefix === $that->prefix &&
|
||||
$this->flattenedProperty === $that->flattenedProperty &&
|
||||
$this->suffix === $that->suffix &&
|
||||
$this->flattenedValueRemaps === $that->flattenedValueRemaps;
|
||||
$this->flattenedValueRemaps === $that->flattenedValueRemaps &&
|
||||
$this->flattenedPropertyType === $that->flattenedPropertyType;
|
||||
}
|
||||
}
|
@ -25,7 +25,7 @@ namespace pocketmine\data\bedrock\block\upgrade;
|
||||
|
||||
use pocketmine\data\bedrock\block\upgrade\model\BlockStateUpgradeSchemaModel;
|
||||
use pocketmine\data\bedrock\block\upgrade\model\BlockStateUpgradeSchemaModelBlockRemap;
|
||||
use pocketmine\data\bedrock\block\upgrade\model\BlockStateUpgradeSchemaModelFlattenedName;
|
||||
use pocketmine\data\bedrock\block\upgrade\model\BlockStateUpgradeSchemaModelFlattenInfo;
|
||||
use pocketmine\data\bedrock\block\upgrade\model\BlockStateUpgradeSchemaModelTag;
|
||||
use pocketmine\data\bedrock\block\upgrade\model\BlockStateUpgradeSchemaModelValueRemap;
|
||||
use pocketmine\nbt\tag\ByteTag;
|
||||
@ -155,20 +155,24 @@ final class BlockStateUpgradeSchemaUtils{
|
||||
}
|
||||
}
|
||||
|
||||
foreach(Utils::stringifyKeys($model->flattenedProperties ?? []) as $blockName => $flattenRule){
|
||||
$result->flattenedProperties[$blockName] = self::jsonModelToFlattenRule($flattenRule);
|
||||
}
|
||||
|
||||
foreach(Utils::stringifyKeys($model->remappedStates ?? []) as $oldBlockName => $remaps){
|
||||
foreach($remaps as $remap){
|
||||
if(isset($remap->newName) === isset($remap->newFlattenedName)){
|
||||
if(isset($remap->newName)){
|
||||
$remapName = $remap->newName;
|
||||
}elseif(isset($remap->newFlattenedName)){
|
||||
$flattenRule = $remap->newFlattenedName;
|
||||
$remapName = self::jsonModelToFlattenRule($flattenRule);
|
||||
}else{
|
||||
throw new \UnexpectedValueException("Expected exactly one of 'newName' or 'newFlattenedName' properties to be set");
|
||||
}
|
||||
|
||||
$result->remappedStates[$oldBlockName][] = new BlockStateUpgradeSchemaBlockRemap(
|
||||
array_map(fn(BlockStateUpgradeSchemaModelTag $tag) => self::jsonModelToTag($tag), $remap->oldState ?? []),
|
||||
$remap->newName ?? new BlockStateUpgradeSchemaFlattenedName(
|
||||
$remap->newFlattenedName->prefix,
|
||||
$remap->newFlattenedName->flattenedProperty,
|
||||
$remap->newFlattenedName->suffix,
|
||||
$remap->newFlattenedName->flattenedValueRemaps ?? [],
|
||||
),
|
||||
$remapName,
|
||||
array_map(fn(BlockStateUpgradeSchemaModelTag $tag) => self::jsonModelToTag($tag), $remap->newState ?? []),
|
||||
$remap->copiedState ?? []
|
||||
);
|
||||
@ -254,6 +258,36 @@ final class BlockStateUpgradeSchemaUtils{
|
||||
$model->remappedPropertyValues = $modelDedupMapping;
|
||||
}
|
||||
|
||||
private static function flattenRuleToJsonModel(BlockStateUpgradeSchemaFlattenInfo $flattenRule) : BlockStateUpgradeSchemaModelFlattenInfo{
|
||||
return new BlockStateUpgradeSchemaModelFlattenInfo(
|
||||
$flattenRule->prefix,
|
||||
$flattenRule->flattenedProperty,
|
||||
$flattenRule->suffix,
|
||||
$flattenRule->flattenedValueRemaps,
|
||||
match($flattenRule->flattenedPropertyType){
|
||||
StringTag::class => null, //omit for TAG_String, as this is the common case
|
||||
ByteTag::class => "byte",
|
||||
IntTag::class => "int",
|
||||
default => throw new \LogicException("Unexpected tag type " . $flattenRule->flattenedPropertyType . " in flattened property type")
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
private static function jsonModelToFlattenRule(BlockStateUpgradeSchemaModelFlattenInfo $flattenRule) : BlockStateUpgradeSchemaFlattenInfo{
|
||||
return new BlockStateUpgradeSchemaFlattenInfo(
|
||||
$flattenRule->prefix,
|
||||
$flattenRule->flattenedProperty,
|
||||
$flattenRule->suffix,
|
||||
$flattenRule->flattenedValueRemaps ?? [],
|
||||
match ($flattenRule->flattenedPropertyType) {
|
||||
"string", null => StringTag::class,
|
||||
"int" => IntTag::class,
|
||||
"byte" => ByteTag::class,
|
||||
default => throw new \UnexpectedValueException("Unexpected flattened property type $flattenRule->flattenedPropertyType, expected 'string', 'int' or 'byte'")
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
public static function toJsonModel(BlockStateUpgradeSchema $schema) : BlockStateUpgradeSchemaModel{
|
||||
$result = new BlockStateUpgradeSchemaModel();
|
||||
$result->maxVersionMajor = $schema->maxVersionMajor;
|
||||
@ -292,19 +326,19 @@ final class BlockStateUpgradeSchemaUtils{
|
||||
|
||||
self::buildRemappedValuesIndex($schema, $result);
|
||||
|
||||
foreach(Utils::stringifyKeys($schema->flattenedProperties) as $blockName => $flattenRule){
|
||||
$result->flattenedProperties[$blockName] = self::flattenRuleToJsonModel($flattenRule);
|
||||
}
|
||||
if(isset($result->flattenedProperties)){
|
||||
ksort($result->flattenedProperties);
|
||||
}
|
||||
|
||||
foreach(Utils::stringifyKeys($schema->remappedStates) as $oldBlockName => $remaps){
|
||||
$keyedRemaps = [];
|
||||
foreach($remaps as $remap){
|
||||
$modelRemap = new BlockStateUpgradeSchemaModelBlockRemap(
|
||||
array_map(fn(Tag $tag) => self::tagToJsonModel($tag), $remap->oldState),
|
||||
is_string($remap->newName) ?
|
||||
$remap->newName :
|
||||
new BlockStateUpgradeSchemaModelFlattenedName(
|
||||
$remap->newName->prefix,
|
||||
$remap->newName->flattenedProperty,
|
||||
$remap->newName->suffix,
|
||||
$remap->newName->flattenedValueRemaps
|
||||
),
|
||||
is_string($remap->newName) ? $remap->newName : self::flattenRuleToJsonModel($remap->newName),
|
||||
array_map(fn(Tag $tag) => self::tagToJsonModel($tag), $remap->newState),
|
||||
$remap->copiedState
|
||||
);
|
||||
|
@ -24,10 +24,14 @@ declare(strict_types=1);
|
||||
namespace pocketmine\data\bedrock\block\upgrade;
|
||||
|
||||
use pocketmine\data\bedrock\block\BlockStateData;
|
||||
use pocketmine\nbt\tag\ByteTag;
|
||||
use pocketmine\nbt\tag\IntTag;
|
||||
use pocketmine\nbt\tag\StringTag;
|
||||
use pocketmine\nbt\tag\Tag;
|
||||
use pocketmine\utils\AssumptionFailedError;
|
||||
use pocketmine\utils\Utils;
|
||||
use function count;
|
||||
use function get_class;
|
||||
use function is_string;
|
||||
use function ksort;
|
||||
use function max;
|
||||
@ -79,6 +83,8 @@ final class BlockStateUpgrader{
|
||||
* version doesn't tell us which of the schemas have already been applied.
|
||||
* If there's only one schema for a version (the norm), we can safely assume it's already been applied if
|
||||
* the version is the same, and skip over it.
|
||||
* TODO: this causes issues when testing isolated schemas since there will only be one schema for a version.
|
||||
* The second check should be disabled for that case.
|
||||
*/
|
||||
if($version > $resultVersion || (count($schemaList) === 1 && $version === $resultVersion)){
|
||||
continue;
|
||||
@ -104,10 +110,21 @@ final class BlockStateUpgrader{
|
||||
}
|
||||
|
||||
$oldName = $blockStateData->getName();
|
||||
$newName = $schema->renamedIds[$oldName] ?? null;
|
||||
$states = $blockStateData->getStates();
|
||||
|
||||
if(isset($schema->renamedIds[$oldName]) && isset($schema->flattenedProperties[$oldName])){
|
||||
//TODO: this probably ought to be validated when the schema is constructed
|
||||
throw new AssumptionFailedError("Both renamedIds and flattenedProperties are set for the same block ID \"$oldName\" - don't know what to do");
|
||||
}
|
||||
if(isset($schema->renamedIds[$oldName])){
|
||||
$newName = $schema->renamedIds[$oldName] ?? null;
|
||||
}elseif(isset($schema->flattenedProperties[$oldName])){
|
||||
[$newName, $states] = $this->applyPropertyFlattened($schema->flattenedProperties[$oldName], $oldName, $states);
|
||||
}else{
|
||||
$newName = null;
|
||||
}
|
||||
|
||||
$stateChanges = 0;
|
||||
$states = $blockStateData->getStates();
|
||||
|
||||
$states = $this->applyPropertyAdded($schema, $oldName, $states, $stateChanges);
|
||||
$states = $this->applyPropertyRemoved($schema, $oldName, $states, $stateChanges);
|
||||
@ -140,15 +157,8 @@ final class BlockStateUpgrader{
|
||||
if(is_string($remap->newName)){
|
||||
$newName = $remap->newName;
|
||||
}else{
|
||||
$flattenedValue = $oldState[$remap->newName->flattenedProperty] ?? null;
|
||||
if($flattenedValue instanceof StringTag){
|
||||
$embedValue = $remap->newName->flattenedValueRemaps[$flattenedValue->getValue()] ?? $flattenedValue->getValue();
|
||||
$newName = sprintf("%s%s%s", $remap->newName->prefix, $embedValue, $remap->newName->suffix);
|
||||
unset($oldState[$remap->newName->flattenedProperty]);
|
||||
}else{
|
||||
//flattened property is not a TAG_String, so this transformation is not applicable
|
||||
continue;
|
||||
}
|
||||
//discard flatten modifications to state - the remap newState and copiedState will take care of it
|
||||
[$newName, ] = $this->applyPropertyFlattened($remap->newName, $oldName, $oldState);
|
||||
}
|
||||
|
||||
$newState = $remap->newState;
|
||||
@ -266,4 +276,32 @@ final class BlockStateUpgrader{
|
||||
|
||||
return $states;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param Tag[] $states
|
||||
* @phpstan-param array<string, Tag> $states
|
||||
*
|
||||
* @return (string|Tag[])[]
|
||||
* @phpstan-return array{0: string, 1: array<string, Tag>}
|
||||
*/
|
||||
private function applyPropertyFlattened(BlockStateUpgradeSchemaFlattenInfo $flattenInfo, string $oldName, array $states) : array{
|
||||
$flattenedValue = $states[$flattenInfo->flattenedProperty] ?? null;
|
||||
$expectedType = $flattenInfo->flattenedPropertyType;
|
||||
if(!$flattenedValue instanceof $expectedType){
|
||||
//flattened property is not of the expected type, so this transformation is not applicable
|
||||
return [$oldName, $states];
|
||||
}
|
||||
$embedKey = match(get_class($flattenedValue)){
|
||||
StringTag::class => $flattenedValue->getValue(),
|
||||
ByteTag::class => (string) $flattenedValue->getValue(),
|
||||
IntTag::class => (string) $flattenedValue->getValue(),
|
||||
//flattenedPropertyType is always one of these three types, but PHPStan doesn't know that
|
||||
default => throw new AssumptionFailedError("flattenedPropertyType should be one of these three types, but have " . get_class($flattenedValue)),
|
||||
};
|
||||
$embedValue = $flattenInfo->flattenedValueRemaps[$embedKey] ?? $embedKey;
|
||||
$newName = sprintf("%s%s%s", $flattenInfo->prefix, $embedValue, $flattenInfo->suffix);
|
||||
unset($states[$flattenInfo->flattenedProperty]);
|
||||
|
||||
return [$newName, $states];
|
||||
}
|
||||
}
|
||||
|
@ -75,6 +75,12 @@ final class BlockStateUpgradeSchemaModel implements \JsonSerializable{
|
||||
*/
|
||||
public array $remappedPropertyValuesIndex;
|
||||
|
||||
/**
|
||||
* @var BlockStateUpgradeSchemaModelFlattenInfo[]
|
||||
* @phpstan-var array<string, BlockStateUpgradeSchemaModelFlattenInfo>
|
||||
*/
|
||||
public array $flattenedProperties;
|
||||
|
||||
/**
|
||||
* @var BlockStateUpgradeSchemaModelBlockRemap[][]
|
||||
* @phpstan-var array<string, list<BlockStateUpgradeSchemaModelBlockRemap>>
|
||||
|
@ -43,7 +43,7 @@ final class BlockStateUpgradeSchemaModelBlockRemap{
|
||||
* Either this or newName must be present
|
||||
* Due to technical limitations of jsonmapper, we can't use a union type here
|
||||
*/
|
||||
public BlockStateUpgradeSchemaModelFlattenedName $newFlattenedName;
|
||||
public BlockStateUpgradeSchemaModelFlattenInfo $newFlattenedName;
|
||||
|
||||
/**
|
||||
* @var BlockStateUpgradeSchemaModelTag[]|null
|
||||
@ -67,9 +67,9 @@ final class BlockStateUpgradeSchemaModelBlockRemap{
|
||||
* @phpstan-param array<string, BlockStateUpgradeSchemaModelTag> $newState
|
||||
* @phpstan-param list<string> $copiedState
|
||||
*/
|
||||
public function __construct(array $oldState, string|BlockStateUpgradeSchemaModelFlattenedName $newNameRule, array $newState, array $copiedState){
|
||||
public function __construct(array $oldState, string|BlockStateUpgradeSchemaModelFlattenInfo $newNameRule, array $newState, array $copiedState){
|
||||
$this->oldState = count($oldState) === 0 ? null : $oldState;
|
||||
if($newNameRule instanceof BlockStateUpgradeSchemaModelFlattenedName){
|
||||
if($newNameRule instanceof BlockStateUpgradeSchemaModelFlattenInfo){
|
||||
$this->newFlattenedName = $newNameRule;
|
||||
}else{
|
||||
$this->newName = $newNameRule;
|
||||
|
@ -25,12 +25,13 @@ namespace pocketmine\data\bedrock\block\upgrade\model;
|
||||
|
||||
use function count;
|
||||
|
||||
final class BlockStateUpgradeSchemaModelFlattenedName implements \JsonSerializable{
|
||||
final class BlockStateUpgradeSchemaModelFlattenInfo implements \JsonSerializable{
|
||||
|
||||
/** @required */
|
||||
public string $prefix;
|
||||
/** @required */
|
||||
public string $flattenedProperty;
|
||||
public ?string $flattenedPropertyType = null;
|
||||
/** @required */
|
||||
public string $suffix;
|
||||
/**
|
||||
@ -43,11 +44,12 @@ final class BlockStateUpgradeSchemaModelFlattenedName implements \JsonSerializab
|
||||
* @param string[] $flattenedValueRemaps
|
||||
* @phpstan-param array<string, string> $flattenedValueRemaps
|
||||
*/
|
||||
public function __construct(string $prefix, string $flattenedProperty, string $suffix, array $flattenedValueRemaps){
|
||||
public function __construct(string $prefix, string $flattenedProperty, string $suffix, array $flattenedValueRemaps, ?string $flattenedPropertyType = null){
|
||||
$this->prefix = $prefix;
|
||||
$this->flattenedProperty = $flattenedProperty;
|
||||
$this->suffix = $suffix;
|
||||
$this->flattenedValueRemaps = $flattenedValueRemaps;
|
||||
$this->flattenedPropertyType = $flattenedPropertyType;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -58,6 +60,9 @@ final class BlockStateUpgradeSchemaModelFlattenedName implements \JsonSerializab
|
||||
if(count($this->flattenedValueRemaps) === 0){
|
||||
unset($result["flattenedValueRemaps"]);
|
||||
}
|
||||
if($this->flattenedPropertyType === null){
|
||||
unset($result["flattenedPropertyType"]);
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
}
|
@ -25,7 +25,8 @@ namespace pocketmine\data\bedrock\item;
|
||||
|
||||
use pocketmine\block\Bed;
|
||||
use pocketmine\block\Block;
|
||||
use pocketmine\block\MobHead;
|
||||
use pocketmine\block\CopperDoor;
|
||||
use pocketmine\block\utils\CopperOxidation;
|
||||
use pocketmine\block\utils\DyeColor;
|
||||
use pocketmine\block\VanillaBlocks as Blocks;
|
||||
use pocketmine\data\bedrock\CompoundTypeIds;
|
||||
@ -33,7 +34,6 @@ use pocketmine\data\bedrock\DyeColorIdMap;
|
||||
use pocketmine\data\bedrock\item\ItemTypeNames as Ids;
|
||||
use pocketmine\data\bedrock\item\SavedItemData as Data;
|
||||
use pocketmine\data\bedrock\MedicineTypeIdMap;
|
||||
use pocketmine\data\bedrock\MobHeadTypeIdMap;
|
||||
use pocketmine\data\bedrock\PotionTypeIdMap;
|
||||
use pocketmine\data\bedrock\SuspiciousStewTypeIdMap;
|
||||
use pocketmine\item\Banner;
|
||||
@ -56,6 +56,7 @@ final class ItemSerializerDeserializerRegistrar{
|
||||
$this->register1to1BlockWithMetaMappings();
|
||||
$this->register1to1ItemWithMetaMappings();
|
||||
$this->register1ToNItemMappings();
|
||||
$this->registerMiscBlockMappings();
|
||||
$this->registerMiscItemMappings();
|
||||
}
|
||||
|
||||
@ -133,6 +134,7 @@ final class ItemSerializerDeserializerRegistrar{
|
||||
$this->map1to1Block(Ids::BIRCH_DOOR, Blocks::BIRCH_DOOR());
|
||||
$this->map1to1Block(Ids::BREWING_STAND, Blocks::BREWING_STAND());
|
||||
$this->map1to1Block(Ids::CAKE, Blocks::CAKE());
|
||||
$this->map1to1Block(Ids::CAMPFIRE, Blocks::CAMPFIRE());
|
||||
$this->map1to1Block(Ids::CAULDRON, Blocks::CAULDRON());
|
||||
$this->map1to1Block(Ids::CHAIN, Blocks::CHAIN());
|
||||
$this->map1to1Block(Ids::CHERRY_DOOR, Blocks::CHERRY_DOOR());
|
||||
@ -148,6 +150,7 @@ final class ItemSerializerDeserializerRegistrar{
|
||||
$this->map1to1Block(Ids::MANGROVE_DOOR, Blocks::MANGROVE_DOOR());
|
||||
$this->map1to1Block(Ids::NETHER_WART, Blocks::NETHER_WART());
|
||||
$this->map1to1Block(Ids::REPEATER, Blocks::REDSTONE_REPEATER());
|
||||
$this->map1to1Block(Ids::SOUL_CAMPFIRE, Blocks::SOUL_CAMPFIRE());
|
||||
$this->map1to1Block(Ids::SPRUCE_DOOR, Blocks::SPRUCE_DOOR());
|
||||
$this->map1to1Block(Ids::SUGAR_CANE, Blocks::SUGARCANE());
|
||||
$this->map1to1Block(Ids::WARPED_DOOR, Blocks::WARPED_DOOR());
|
||||
@ -464,14 +467,6 @@ final class ItemSerializerDeserializerRegistrar{
|
||||
},
|
||||
fn(Bed $block) => DyeColorIdMap::getInstance()->toId($block->getColor())
|
||||
);
|
||||
$this->map1to1BlockWithMeta(
|
||||
Ids::SKULL,
|
||||
Blocks::MOB_HEAD(),
|
||||
function(MobHead $block, int $meta) : void{
|
||||
$block->setMobHeadType(MobHeadTypeIdMap::getInstance()->fromId($meta) ?? throw new ItemTypeDeserializeException("Unknown mob head type ID $meta"));
|
||||
},
|
||||
fn(MobHead $block) => MobHeadTypeIdMap::getInstance()->toId($block->getMobHeadType())
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -536,4 +531,29 @@ final class ItemSerializerDeserializerRegistrar{
|
||||
}
|
||||
$this->serializer?->map(Items::DYE(), fn(Dye $item) => new Data(DyeColorIdMap::getInstance()->toItemId($item->getColor())));
|
||||
}
|
||||
|
||||
/**
|
||||
* Registers serializers and deserializers for PocketMine-MP blockitems that don't fit any other pattern.
|
||||
* Ideally we want to get rid of this completely, if possible.
|
||||
*
|
||||
* Most of these are single PocketMine-MP blocks which map to multiple IDs depending on their properties, which is
|
||||
* complex to implement in a generic way.
|
||||
*/
|
||||
private function registerMiscBlockMappings() : void{
|
||||
$copperDoorStateIdMap = [];
|
||||
foreach ([
|
||||
[Ids::COPPER_DOOR, CopperOxidation::NONE, false],
|
||||
[Ids::EXPOSED_COPPER_DOOR, CopperOxidation::EXPOSED, false],
|
||||
[Ids::WEATHERED_COPPER_DOOR, CopperOxidation::WEATHERED, false],
|
||||
[Ids::OXIDIZED_COPPER_DOOR, CopperOxidation::OXIDIZED, false],
|
||||
[Ids::WAXED_COPPER_DOOR, CopperOxidation::NONE, true],
|
||||
[Ids::WAXED_EXPOSED_COPPER_DOOR, CopperOxidation::EXPOSED, true],
|
||||
[Ids::WAXED_WEATHERED_COPPER_DOOR, CopperOxidation::WEATHERED, true],
|
||||
[Ids::WAXED_OXIDIZED_COPPER_DOOR, CopperOxidation::OXIDIZED, true]
|
||||
] as [$id, $oxidation, $waxed]) {
|
||||
$copperDoorStateIdMap[$oxidation->value][$waxed ? 1 : 0] = $id;
|
||||
$this->deserializer?->mapBlock($id, fn() => Blocks::COPPER_DOOR()->setOxidation($oxidation)->setWaxed($waxed));
|
||||
}
|
||||
$this->serializer?->mapBlock(Blocks::COPPER_DOOR(), fn(CopperDoor $block) => new Data($copperDoorStateIdMap[$block->getOxidation()->value][$block->isWaxed() ? 1 : 0]));
|
||||
}
|
||||
}
|
||||
|
@ -66,12 +66,14 @@ final class ItemTypeNames{
|
||||
public const BIRCH_DOOR = "minecraft:birch_door";
|
||||
public const BIRCH_HANGING_SIGN = "minecraft:birch_hanging_sign";
|
||||
public const BIRCH_SIGN = "minecraft:birch_sign";
|
||||
public const BLACK_BUNDLE = "minecraft:black_bundle";
|
||||
public const BLACK_DYE = "minecraft:black_dye";
|
||||
public const BLADE_POTTERY_SHERD = "minecraft:blade_pottery_sherd";
|
||||
public const BLAZE_POWDER = "minecraft:blaze_powder";
|
||||
public const BLAZE_ROD = "minecraft:blaze_rod";
|
||||
public const BLAZE_SPAWN_EGG = "minecraft:blaze_spawn_egg";
|
||||
public const BLEACH = "minecraft:bleach";
|
||||
public const BLUE_BUNDLE = "minecraft:blue_bundle";
|
||||
public const BLUE_DYE = "minecraft:blue_dye";
|
||||
public const BOAT = "minecraft:boat";
|
||||
public const BOGGED_SPAWN_EGG = "minecraft:bogged_spawn_egg";
|
||||
@ -88,9 +90,11 @@ final class ItemTypeNames{
|
||||
public const BREWER_POTTERY_SHERD = "minecraft:brewer_pottery_sherd";
|
||||
public const BREWING_STAND = "minecraft:brewing_stand";
|
||||
public const BRICK = "minecraft:brick";
|
||||
public const BROWN_BUNDLE = "minecraft:brown_bundle";
|
||||
public const BROWN_DYE = "minecraft:brown_dye";
|
||||
public const BRUSH = "minecraft:brush";
|
||||
public const BUCKET = "minecraft:bucket";
|
||||
public const BUNDLE = "minecraft:bundle";
|
||||
public const BURN_POTTERY_SHERD = "minecraft:burn_pottery_sherd";
|
||||
public const CAKE = "minecraft:cake";
|
||||
public const CAMEL_SPAWN_EGG = "minecraft:camel_spawn_egg";
|
||||
@ -108,6 +112,7 @@ final class ItemTypeNames{
|
||||
public const CHAINMAIL_HELMET = "minecraft:chainmail_helmet";
|
||||
public const CHAINMAIL_LEGGINGS = "minecraft:chainmail_leggings";
|
||||
public const CHARCOAL = "minecraft:charcoal";
|
||||
public const CHEMISTRY_TABLE = "minecraft:chemistry_table";
|
||||
public const CHERRY_BOAT = "minecraft:cherry_boat";
|
||||
public const CHERRY_CHEST_BOAT = "minecraft:cherry_chest_boat";
|
||||
public const CHERRY_DOOR = "minecraft:cherry_door";
|
||||
@ -126,6 +131,8 @@ final class ItemTypeNames{
|
||||
public const COD = "minecraft:cod";
|
||||
public const COD_BUCKET = "minecraft:cod_bucket";
|
||||
public const COD_SPAWN_EGG = "minecraft:cod_spawn_egg";
|
||||
public const COLORED_TORCH_BP = "minecraft:colored_torch_bp";
|
||||
public const COLORED_TORCH_RG = "minecraft:colored_torch_rg";
|
||||
public const COMMAND_BLOCK_MINECART = "minecraft:command_block_minecart";
|
||||
public const COMPARATOR = "minecraft:comparator";
|
||||
public const COMPASS = "minecraft:compass";
|
||||
@ -153,6 +160,7 @@ final class ItemTypeNames{
|
||||
public const CRIMSON_HANGING_SIGN = "minecraft:crimson_hanging_sign";
|
||||
public const CRIMSON_SIGN = "minecraft:crimson_sign";
|
||||
public const CROSSBOW = "minecraft:crossbow";
|
||||
public const CYAN_BUNDLE = "minecraft:cyan_bundle";
|
||||
public const CYAN_DYE = "minecraft:cyan_dye";
|
||||
public const DANGER_POTTERY_SHERD = "minecraft:danger_pottery_sherd";
|
||||
public const DARK_OAK_BOAT = "minecraft:dark_oak_boat";
|
||||
@ -160,6 +168,7 @@ final class ItemTypeNames{
|
||||
public const DARK_OAK_DOOR = "minecraft:dark_oak_door";
|
||||
public const DARK_OAK_HANGING_SIGN = "minecraft:dark_oak_hanging_sign";
|
||||
public const DARK_OAK_SIGN = "minecraft:dark_oak_sign";
|
||||
public const DEBUG_STICK = "minecraft:debug_stick";
|
||||
public const DIAMOND = "minecraft:diamond";
|
||||
public const DIAMOND_AXE = "minecraft:diamond_axe";
|
||||
public const DIAMOND_BOOTS = "minecraft:diamond_boots";
|
||||
@ -175,6 +184,10 @@ final class ItemTypeNames{
|
||||
public const DOLPHIN_SPAWN_EGG = "minecraft:dolphin_spawn_egg";
|
||||
public const DONKEY_SPAWN_EGG = "minecraft:donkey_spawn_egg";
|
||||
public const DOUBLE_PLANT = "minecraft:double_plant";
|
||||
public const DOUBLE_STONE_BLOCK_SLAB = "minecraft:double_stone_block_slab";
|
||||
public const DOUBLE_STONE_BLOCK_SLAB2 = "minecraft:double_stone_block_slab2";
|
||||
public const DOUBLE_STONE_BLOCK_SLAB3 = "minecraft:double_stone_block_slab3";
|
||||
public const DOUBLE_STONE_BLOCK_SLAB4 = "minecraft:double_stone_block_slab4";
|
||||
public const DRAGON_BREATH = "minecraft:dragon_breath";
|
||||
public const DRIED_KELP = "minecraft:dried_kelp";
|
||||
public const DROWNED_SPAWN_EGG = "minecraft:drowned_spawn_egg";
|
||||
@ -246,7 +259,9 @@ final class ItemTypeNames{
|
||||
public const GOLDEN_PICKAXE = "minecraft:golden_pickaxe";
|
||||
public const GOLDEN_SHOVEL = "minecraft:golden_shovel";
|
||||
public const GOLDEN_SWORD = "minecraft:golden_sword";
|
||||
public const GRAY_BUNDLE = "minecraft:gray_bundle";
|
||||
public const GRAY_DYE = "minecraft:gray_dye";
|
||||
public const GREEN_BUNDLE = "minecraft:green_bundle";
|
||||
public const GREEN_DYE = "minecraft:green_dye";
|
||||
public const GUARDIAN_SPAWN_EGG = "minecraft:guardian_spawn_egg";
|
||||
public const GUNPOWDER = "minecraft:gunpowder";
|
||||
@ -299,8 +314,12 @@ final class ItemTypeNames{
|
||||
public const LEATHER_LEGGINGS = "minecraft:leather_leggings";
|
||||
public const LEAVES = "minecraft:leaves";
|
||||
public const LEAVES2 = "minecraft:leaves2";
|
||||
public const LIGHT_BLOCK = "minecraft:light_block";
|
||||
public const LIGHT_BLUE_BUNDLE = "minecraft:light_blue_bundle";
|
||||
public const LIGHT_BLUE_DYE = "minecraft:light_blue_dye";
|
||||
public const LIGHT_GRAY_BUNDLE = "minecraft:light_gray_bundle";
|
||||
public const LIGHT_GRAY_DYE = "minecraft:light_gray_dye";
|
||||
public const LIME_BUNDLE = "minecraft:lime_bundle";
|
||||
public const LIME_DYE = "minecraft:lime_dye";
|
||||
public const LINGERING_POTION = "minecraft:lingering_potion";
|
||||
public const LLAMA_SPAWN_EGG = "minecraft:llama_spawn_egg";
|
||||
@ -308,6 +327,7 @@ final class ItemTypeNames{
|
||||
public const LOG = "minecraft:log";
|
||||
public const LOG2 = "minecraft:log2";
|
||||
public const MACE = "minecraft:mace";
|
||||
public const MAGENTA_BUNDLE = "minecraft:magenta_bundle";
|
||||
public const MAGENTA_DYE = "minecraft:magenta_dye";
|
||||
public const MAGMA_CREAM = "minecraft:magma_cream";
|
||||
public const MAGMA_CUBE_SPAWN_EGG = "minecraft:magma_cube_spawn_egg";
|
||||
@ -323,6 +343,7 @@ final class ItemTypeNames{
|
||||
public const MINECART = "minecraft:minecart";
|
||||
public const MINER_POTTERY_SHERD = "minecraft:miner_pottery_sherd";
|
||||
public const MOJANG_BANNER_PATTERN = "minecraft:mojang_banner_pattern";
|
||||
public const MONSTER_EGG = "minecraft:monster_egg";
|
||||
public const MOOSHROOM_SPAWN_EGG = "minecraft:mooshroom_spawn_egg";
|
||||
public const MOURNER_POTTERY_SHERD = "minecraft:mourner_pottery_sherd";
|
||||
public const MULE_SPAWN_EGG = "minecraft:mule_spawn_egg";
|
||||
@ -373,6 +394,7 @@ final class ItemTypeNames{
|
||||
public const OCELOT_SPAWN_EGG = "minecraft:ocelot_spawn_egg";
|
||||
public const OMINOUS_BOTTLE = "minecraft:ominous_bottle";
|
||||
public const OMINOUS_TRIAL_KEY = "minecraft:ominous_trial_key";
|
||||
public const ORANGE_BUNDLE = "minecraft:orange_bundle";
|
||||
public const ORANGE_DYE = "minecraft:orange_dye";
|
||||
public const OXIDIZED_COPPER_DOOR = "minecraft:oxidized_copper_door";
|
||||
public const PAINTING = "minecraft:painting";
|
||||
@ -386,6 +408,7 @@ final class ItemTypeNames{
|
||||
public const PIGLIN_BRUTE_SPAWN_EGG = "minecraft:piglin_brute_spawn_egg";
|
||||
public const PIGLIN_SPAWN_EGG = "minecraft:piglin_spawn_egg";
|
||||
public const PILLAGER_SPAWN_EGG = "minecraft:pillager_spawn_egg";
|
||||
public const PINK_BUNDLE = "minecraft:pink_bundle";
|
||||
public const PINK_DYE = "minecraft:pink_dye";
|
||||
public const PITCHER_POD = "minecraft:pitcher_pod";
|
||||
public const PLANKS = "minecraft:planks";
|
||||
@ -405,6 +428,7 @@ final class ItemTypeNames{
|
||||
public const PUFFERFISH_SPAWN_EGG = "minecraft:pufferfish_spawn_egg";
|
||||
public const PUMPKIN_PIE = "minecraft:pumpkin_pie";
|
||||
public const PUMPKIN_SEEDS = "minecraft:pumpkin_seeds";
|
||||
public const PURPLE_BUNDLE = "minecraft:purple_bundle";
|
||||
public const PURPLE_DYE = "minecraft:purple_dye";
|
||||
public const QUARTZ = "minecraft:quartz";
|
||||
public const RABBIT = "minecraft:rabbit";
|
||||
@ -419,6 +443,7 @@ final class ItemTypeNames{
|
||||
public const RAW_GOLD = "minecraft:raw_gold";
|
||||
public const RAW_IRON = "minecraft:raw_iron";
|
||||
public const RECOVERY_COMPASS = "minecraft:recovery_compass";
|
||||
public const RED_BUNDLE = "minecraft:red_bundle";
|
||||
public const RED_DYE = "minecraft:red_dye";
|
||||
public const RED_FLOWER = "minecraft:red_flower";
|
||||
public const REDSTONE = "minecraft:redstone";
|
||||
@ -475,10 +500,14 @@ final class ItemTypeNames{
|
||||
public const STICK = "minecraft:stick";
|
||||
public const STONE_AXE = "minecraft:stone_axe";
|
||||
public const STONE_BLOCK_SLAB = "minecraft:stone_block_slab";
|
||||
public const STONE_BLOCK_SLAB2 = "minecraft:stone_block_slab2";
|
||||
public const STONE_BLOCK_SLAB3 = "minecraft:stone_block_slab3";
|
||||
public const STONE_BLOCK_SLAB4 = "minecraft:stone_block_slab4";
|
||||
public const STONE_HOE = "minecraft:stone_hoe";
|
||||
public const STONE_PICKAXE = "minecraft:stone_pickaxe";
|
||||
public const STONE_SHOVEL = "minecraft:stone_shovel";
|
||||
public const STONE_SWORD = "minecraft:stone_sword";
|
||||
public const STONEBRICK = "minecraft:stonebrick";
|
||||
public const STRAY_SPAWN_EGG = "minecraft:stray_spawn_egg";
|
||||
public const STRIDER_SPAWN_EGG = "minecraft:strider_spawn_egg";
|
||||
public const STRING = "minecraft:string";
|
||||
@ -522,6 +551,7 @@ final class ItemTypeNames{
|
||||
public const WEATHERED_COPPER_DOOR = "minecraft:weathered_copper_door";
|
||||
public const WHEAT = "minecraft:wheat";
|
||||
public const WHEAT_SEEDS = "minecraft:wheat_seeds";
|
||||
public const WHITE_BUNDLE = "minecraft:white_bundle";
|
||||
public const WHITE_DYE = "minecraft:white_dye";
|
||||
public const WILD_ARMOR_TRIM_SMITHING_TEMPLATE = "minecraft:wild_armor_trim_smithing_template";
|
||||
public const WIND_CHARGE = "minecraft:wind_charge";
|
||||
@ -541,6 +571,7 @@ final class ItemTypeNames{
|
||||
public const WOOL = "minecraft:wool";
|
||||
public const WRITABLE_BOOK = "minecraft:writable_book";
|
||||
public const WRITTEN_BOOK = "minecraft:written_book";
|
||||
public const YELLOW_BUNDLE = "minecraft:yellow_bundle";
|
||||
public const YELLOW_DYE = "minecraft:yellow_dye";
|
||||
public const ZOGLIN_SPAWN_EGG = "minecraft:zoglin_spawn_egg";
|
||||
public const ZOMBIE_HORSE_SPAWN_EGG = "minecraft:zombie_horse_spawn_egg";
|
||||
|
@ -25,6 +25,7 @@ namespace pocketmine\data\bedrock\item\upgrade;
|
||||
|
||||
use pocketmine\data\bedrock\block\BlockStateDeserializeException;
|
||||
use pocketmine\data\bedrock\block\upgrade\BlockDataUpgrader;
|
||||
use pocketmine\data\bedrock\item\BlockItemIdMap;
|
||||
use pocketmine\data\bedrock\item\SavedItemData;
|
||||
use pocketmine\data\bedrock\item\SavedItemStackData;
|
||||
use pocketmine\data\SavedDataLoadingException;
|
||||
@ -35,6 +36,7 @@ use pocketmine\nbt\tag\CompoundTag;
|
||||
use pocketmine\nbt\tag\ListTag;
|
||||
use pocketmine\nbt\tag\ShortTag;
|
||||
use pocketmine\nbt\tag\StringTag;
|
||||
use pocketmine\network\mcpe\convert\BlockStateDictionary;
|
||||
use pocketmine\utils\Binary;
|
||||
use function assert;
|
||||
|
||||
@ -46,6 +48,8 @@ final class ItemDataUpgrader{
|
||||
private LegacyItemIdToStringIdMap $legacyIntToStringIdMap,
|
||||
private R12ItemIdToBlockIdMap $r12ItemIdToBlockIdMap,
|
||||
private BlockDataUpgrader $blockDataUpgrader,
|
||||
private BlockItemIdMap $blockItemIdMap,
|
||||
private BlockStateDictionary $blockStateDictionary
|
||||
){}
|
||||
|
||||
/**
|
||||
@ -148,6 +152,17 @@ final class ItemDataUpgrader{
|
||||
|
||||
[$newNameId, $newMeta] = $this->idMetaUpgrader->upgrade($rawNameId, $meta);
|
||||
|
||||
//TODO: Dirty hack to load old skulls from disk: Put this into item upgrade schema's before Mojang makes something with a non 0 default state
|
||||
if($blockStateData === null && ($blockId = $this->blockItemIdMap->lookupBlockId($newNameId)) !== null){
|
||||
$networkRuntimeId = $this->blockStateDictionary->lookupStateIdFromIdMeta($blockId, 0);
|
||||
|
||||
if($networkRuntimeId === null){
|
||||
throw new SavedDataLoadingException("Failed to find blockstate for blockitem $newNameId");
|
||||
}
|
||||
|
||||
$blockStateData = $this->blockStateDictionary->generateDataFromStateId($networkRuntimeId);
|
||||
}
|
||||
|
||||
//TODO: this won't account for spawn eggs from before 1.16.100 - perhaps we're lucky and they just left the meta in there anyway?
|
||||
//TODO: read version from VersionInfo::TAG_WORLD_DATA_VERSION - we may need it to fix up old items
|
||||
|
||||
|
@ -68,6 +68,7 @@ use function atan2;
|
||||
use function ceil;
|
||||
use function count;
|
||||
use function floor;
|
||||
use function ksort;
|
||||
use function lcg_value;
|
||||
use function max;
|
||||
use function min;
|
||||
@ -76,6 +77,7 @@ use function mt_rand;
|
||||
use function round;
|
||||
use function sqrt;
|
||||
use const M_PI;
|
||||
use const SORT_NUMERIC;
|
||||
|
||||
abstract class Living extends Entity{
|
||||
protected const DEFAULT_BREATH_TICKS = 300;
|
||||
@ -883,8 +885,30 @@ abstract class Living extends Entity{
|
||||
protected function syncNetworkData(EntityMetadataCollection $properties) : void{
|
||||
parent::syncNetworkData($properties);
|
||||
|
||||
$properties->setByte(EntityMetadataProperties::POTION_AMBIENT, $this->effectManager->hasOnlyAmbientEffects() ? 1 : 0);
|
||||
$properties->setInt(EntityMetadataProperties::POTION_COLOR, Binary::signInt($this->effectManager->getBubbleColor()->toARGB()));
|
||||
$visibleEffects = [];
|
||||
foreach ($this->effectManager->all() as $effect) {
|
||||
if (!$effect->isVisible() || !$effect->getType()->hasBubbles()) {
|
||||
continue;
|
||||
}
|
||||
$visibleEffects[EffectIdMap::getInstance()->toId($effect->getType())] = $effect->isAmbient();
|
||||
}
|
||||
|
||||
//TODO: HACK! the client may not be able to identify effects if they are not sorted.
|
||||
ksort($visibleEffects, SORT_NUMERIC);
|
||||
|
||||
$effectsData = 0;
|
||||
$packedEffectsCount = 0;
|
||||
foreach ($visibleEffects as $effectId => $isAmbient) {
|
||||
$effectsData = ($effectsData << 7) |
|
||||
(($effectId & 0x3f) << 1) | //Why not use 7 bits instead of only 6? mojang...
|
||||
($isAmbient ? 1 : 0);
|
||||
|
||||
if (++$packedEffectsCount >= 8) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
$properties->setLong(EntityMetadataProperties::VISIBLE_MOB_EFFECTS, $effectsData);
|
||||
|
||||
$properties->setShort(EntityMetadataProperties::AIR, $this->breathTicks);
|
||||
$properties->setShort(EntityMetadataProperties::MAX_AIR, $this->maxBreathTicks);
|
||||
|
||||
|
@ -37,9 +37,11 @@ class PaintingMotive{
|
||||
new PaintingMotive(1, 1, "Aztec2"),
|
||||
new PaintingMotive(1, 1, "Bomb"),
|
||||
new PaintingMotive(1, 1, "Kebab"),
|
||||
new PaintingMotive(1, 1, "meditative"),
|
||||
new PaintingMotive(1, 1, "Plant"),
|
||||
new PaintingMotive(1, 1, "Wasteland"),
|
||||
new PaintingMotive(1, 2, "Graham"),
|
||||
new PaintingMotive(1, 2, "prairie_ride"),
|
||||
new PaintingMotive(1, 2, "Wanderer"),
|
||||
new PaintingMotive(2, 1, "Courbet"),
|
||||
new PaintingMotive(2, 1, "Creebet"),
|
||||
@ -47,8 +49,10 @@ class PaintingMotive{
|
||||
new PaintingMotive(2, 1, "Sea"),
|
||||
new PaintingMotive(2, 1, "Sunset"),
|
||||
new PaintingMotive(2, 2, "Bust"),
|
||||
new PaintingMotive(2, 2, "baroque"),
|
||||
new PaintingMotive(2, 2, "Earth"),
|
||||
new PaintingMotive(2, 2, "Fire"),
|
||||
new PaintingMotive(2, 2, "humble"),
|
||||
new PaintingMotive(2, 2, "Match"),
|
||||
new PaintingMotive(2, 2, "SkullAndRoses"),
|
||||
new PaintingMotive(2, 2, "Stage"),
|
||||
@ -56,12 +60,28 @@ class PaintingMotive{
|
||||
new PaintingMotive(2, 2, "Water"),
|
||||
new PaintingMotive(2, 2, "Wind"),
|
||||
new PaintingMotive(2, 2, "Wither"),
|
||||
new PaintingMotive(3, 3, "bouquet"),
|
||||
new PaintingMotive(3, 3, "cavebird"),
|
||||
new PaintingMotive(3, 3, "cotan"),
|
||||
new PaintingMotive(3, 3, "endboss"),
|
||||
new PaintingMotive(3, 3, "fern"),
|
||||
new PaintingMotive(3, 3, "owlemons"),
|
||||
new PaintingMotive(3, 3, "sunflowers"),
|
||||
new PaintingMotive(3, 3, "tides"),
|
||||
new PaintingMotive(3, 4, "backyard"),
|
||||
new PaintingMotive(3, 4, "pond"),
|
||||
new PaintingMotive(4, 2, "changing"),
|
||||
new PaintingMotive(4, 2, "Fighters"),
|
||||
new PaintingMotive(4, 2, "finding"),
|
||||
new PaintingMotive(4, 2, "lowmist"),
|
||||
new PaintingMotive(4, 2, "passage"),
|
||||
new PaintingMotive(4, 3, "DonkeyKong"),
|
||||
new PaintingMotive(4, 3, "Skeleton"),
|
||||
new PaintingMotive(4, 4, "BurningSkull"),
|
||||
new PaintingMotive(4, 4, "orb"),
|
||||
new PaintingMotive(4, 4, "Pigscene"),
|
||||
new PaintingMotive(4, 4, "Pointer")
|
||||
new PaintingMotive(4, 4, "Pointer"),
|
||||
new PaintingMotive(4, 4, "unpacked")
|
||||
] as $motive){
|
||||
self::registerMotive($motive);
|
||||
}
|
||||
|
63
src/event/block/CampfireCookEvent.php
Normal file
63
src/event/block/CampfireCookEvent.php
Normal file
@ -0,0 +1,63 @@
|
||||
<?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\event\block;
|
||||
|
||||
use pocketmine\block\Campfire;
|
||||
use pocketmine\event\Cancellable;
|
||||
use pocketmine\event\CancellableTrait;
|
||||
use pocketmine\item\Item;
|
||||
|
||||
class CampfireCookEvent extends BlockEvent implements Cancellable{
|
||||
use CancellableTrait;
|
||||
|
||||
public function __construct(
|
||||
private Campfire $campfire,
|
||||
private int $slot,
|
||||
private Item $input,
|
||||
private Item $result
|
||||
){
|
||||
parent::__construct($campfire);
|
||||
$this->input = clone $input;
|
||||
}
|
||||
|
||||
public function getCampfire() : Campfire{
|
||||
return $this->campfire;
|
||||
}
|
||||
|
||||
public function getSlot() : int{
|
||||
return $this->slot;
|
||||
}
|
||||
|
||||
public function getInput() : Item{
|
||||
return $this->input;
|
||||
}
|
||||
|
||||
public function getResult() : Item{
|
||||
return $this->result;
|
||||
}
|
||||
|
||||
public function setResult(Item $result) : void{
|
||||
$this->result = $result;
|
||||
}
|
||||
}
|
@ -57,7 +57,7 @@ class EntityDamageByEntityEvent extends EntityDamageEvent{
|
||||
$this->setModifier($this->getBaseDamage() * 0.3 * $strength->getEffectLevel(), self::MODIFIER_STRENGTH);
|
||||
}
|
||||
|
||||
if(($weakness = $effects->get(VanillaEffects::WEAKNESS())) !== null){
|
||||
if(($weakness = $effects->get(VanillaEffects::WEAKNESS())) !== null && $this->getCause() === EntityDamageEvent::CAUSE_ENTITY_ATTACK){
|
||||
$this->setModifier(-($this->getBaseDamage() * 0.2 * $weakness->getEffectLevel()), self::MODIFIER_WEAKNESS);
|
||||
}
|
||||
}
|
||||
|
@ -23,8 +23,13 @@ declare(strict_types=1);
|
||||
|
||||
namespace pocketmine\inventory;
|
||||
|
||||
use pocketmine\block\BlockTypeIds;
|
||||
use pocketmine\entity\Living;
|
||||
use pocketmine\inventory\transaction\action\validator\CallbackSlotValidator;
|
||||
use pocketmine\inventory\transaction\TransactionValidationException;
|
||||
use pocketmine\item\Armor;
|
||||
use pocketmine\item\Item;
|
||||
use pocketmine\item\ItemBlock;
|
||||
|
||||
class ArmorInventory extends SimpleInventory{
|
||||
public const SLOT_HEAD = 0;
|
||||
@ -36,6 +41,8 @@ class ArmorInventory extends SimpleInventory{
|
||||
protected Living $holder
|
||||
){
|
||||
parent::__construct(4);
|
||||
|
||||
$this->validators->add(new CallbackSlotValidator(self::validate(...)));
|
||||
}
|
||||
|
||||
public function getHolder() : Living{
|
||||
@ -73,4 +80,20 @@ class ArmorInventory extends SimpleInventory{
|
||||
public function setBoots(Item $boots) : void{
|
||||
$this->setItem(self::SLOT_FEET, $boots);
|
||||
}
|
||||
|
||||
private static function validate(Inventory $inventory, Item $item, int $slot) : ?TransactionValidationException{
|
||||
if($item instanceof Armor){
|
||||
if($item->getArmorSlot() !== $slot){
|
||||
return new TransactionValidationException("Armor item is in wrong slot");
|
||||
}
|
||||
}else{
|
||||
if(!($slot === ArmorInventory::SLOT_HEAD && $item instanceof ItemBlock && (
|
||||
$item->getBlock()->getTypeId() === BlockTypeIds::CARVED_PUMPKIN ||
|
||||
$item->getBlock()->getTypeId() === BlockTypeIds::MOB_HEAD
|
||||
))){
|
||||
return new TransactionValidationException("Item is not accepted in an armor slot");
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
@ -36,8 +36,10 @@ use function spl_object_id;
|
||||
|
||||
/**
|
||||
* This class provides everything needed to implement an inventory, minus the underlying storage system.
|
||||
*
|
||||
* @phpstan-import-type SlotValidators from SlotValidatedInventory
|
||||
*/
|
||||
abstract class BaseInventory implements Inventory{
|
||||
abstract class BaseInventory implements Inventory, SlotValidatedInventory{
|
||||
protected int $maxStackSize = Inventory::MAX_STACK;
|
||||
/** @var Player[] */
|
||||
protected array $viewers = [];
|
||||
@ -46,9 +48,12 @@ abstract class BaseInventory implements Inventory{
|
||||
* @phpstan-var ObjectSet<InventoryListener>
|
||||
*/
|
||||
protected ObjectSet $listeners;
|
||||
/** @phpstan-var SlotValidators */
|
||||
protected ObjectSet $validators;
|
||||
|
||||
public function __construct(){
|
||||
$this->listeners = new ObjectSet();
|
||||
$this->validators = new ObjectSet();
|
||||
}
|
||||
|
||||
public function getMaxStackSize() : int{
|
||||
@ -398,4 +403,8 @@ abstract class BaseInventory implements Inventory{
|
||||
public function getListeners() : ObjectSet{
|
||||
return $this->listeners;
|
||||
}
|
||||
|
||||
public function getSlotValidators() : ObjectSet{
|
||||
return $this->validators;
|
||||
}
|
||||
}
|
||||
|
46
src/inventory/SlotValidatedInventory.php
Normal file
46
src/inventory/SlotValidatedInventory.php
Normal file
@ -0,0 +1,46 @@
|
||||
<?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\inventory;
|
||||
|
||||
use pocketmine\inventory\transaction\action\validator\SlotValidator;
|
||||
use pocketmine\utils\ObjectSet;
|
||||
|
||||
/**
|
||||
* A "slot validated inventory" has validators which may restrict items
|
||||
* from being placed in particular slots of the inventory when transactions are executed.
|
||||
*
|
||||
* @phpstan-type SlotValidators ObjectSet<SlotValidator>
|
||||
*/
|
||||
interface SlotValidatedInventory{
|
||||
/**
|
||||
* Returns a set of validators that will be used to determine whether an item can be placed in a particular slot.
|
||||
* All validators need to return null for the transaction to be allowed.
|
||||
* If one of the validators returns an exception, the transaction will be cancelled.
|
||||
*
|
||||
* There is no guarantee that the validators will be called in any particular order.
|
||||
*
|
||||
* @phpstan-return SlotValidators
|
||||
*/
|
||||
public function getSlotValidators() : ObjectSet;
|
||||
}
|
@ -24,6 +24,7 @@ declare(strict_types=1);
|
||||
namespace pocketmine\inventory\transaction\action;
|
||||
|
||||
use pocketmine\inventory\Inventory;
|
||||
use pocketmine\inventory\SlotValidatedInventory;
|
||||
use pocketmine\inventory\transaction\InventoryTransaction;
|
||||
use pocketmine\inventory\transaction\TransactionValidationException;
|
||||
use pocketmine\item\Item;
|
||||
@ -74,6 +75,14 @@ class SlotChangeAction extends InventoryAction{
|
||||
if($this->targetItem->getCount() > $this->inventory->getMaxStackSize()){
|
||||
throw new TransactionValidationException("Target item exceeds inventory max stack size");
|
||||
}
|
||||
if($this->inventory instanceof SlotValidatedInventory && !$this->targetItem->isNull()){
|
||||
foreach($this->inventory->getSlotValidators() as $validator){
|
||||
$ret = $validator->validate($this->inventory, $this->targetItem, $this->inventorySlot);
|
||||
if($ret !== null){
|
||||
throw new TransactionValidationException("Target item is not accepted by the inventory at slot #" . $this->inventorySlot . ": " . $ret->getMessage(), 0, $ret);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -0,0 +1,44 @@
|
||||
<?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\inventory\transaction\action\validator;
|
||||
|
||||
use pocketmine\inventory\Inventory;
|
||||
use pocketmine\inventory\transaction\TransactionValidationException;
|
||||
use pocketmine\item\Item;
|
||||
use pocketmine\utils\Utils;
|
||||
|
||||
class CallbackSlotValidator implements SlotValidator{
|
||||
/**
|
||||
* @phpstan-param \Closure(Inventory, Item, int) : ?TransactionValidationException $validate
|
||||
*/
|
||||
public function __construct(
|
||||
private \Closure $validate
|
||||
){
|
||||
Utils::validateCallableSignature(function(Inventory $inventory, Item $item, int $slot) : ?TransactionValidationException{ return null; }, $validate);
|
||||
}
|
||||
|
||||
public function validate(Inventory $inventory, Item $item, int $slot) : ?TransactionValidationException{
|
||||
return ($this->validate)($inventory, $item, $slot);
|
||||
}
|
||||
}
|
38
src/inventory/transaction/action/validator/SlotValidator.php
Normal file
38
src/inventory/transaction/action/validator/SlotValidator.php
Normal file
@ -0,0 +1,38 @@
|
||||
<?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\inventory\transaction\action\validator;
|
||||
|
||||
use pocketmine\inventory\Inventory;
|
||||
use pocketmine\inventory\transaction\TransactionValidationException;
|
||||
use pocketmine\item\Item;
|
||||
|
||||
/**
|
||||
* Validates a slot placement in an inventory.
|
||||
*/
|
||||
interface SlotValidator{
|
||||
/**
|
||||
* Returns null if the slot placement is valid, or a TransactionValidationException if it is not.
|
||||
*/
|
||||
public function validate(Inventory $inventory, Item $item, int $slot) : ?TransactionValidationException;
|
||||
}
|
@ -25,5 +25,7 @@ namespace pocketmine\item;
|
||||
|
||||
class Bowl extends Item{
|
||||
|
||||
//TODO: check fuel
|
||||
public function getFuelTime() : int{
|
||||
return 200;
|
||||
}
|
||||
}
|
||||
|
@ -88,4 +88,8 @@ class ChorusFruit extends Food{
|
||||
public function getCooldownTicks() : int{
|
||||
return 20;
|
||||
}
|
||||
|
||||
public function getCooldownTag() : ?string{
|
||||
return ItemCooldownTags::CHORUS_FRUIT;
|
||||
}
|
||||
}
|
||||
|
@ -45,4 +45,8 @@ class EnderPearl extends ProjectileItem{
|
||||
public function getCooldownTicks() : int{
|
||||
return 20;
|
||||
}
|
||||
|
||||
public function getCooldownTag() : ?string{
|
||||
return ItemCooldownTags::ENDER_PEARL;
|
||||
}
|
||||
}
|
||||
|
@ -30,7 +30,7 @@ class GoldenAppleEnchanted extends GoldenApple{
|
||||
|
||||
public function getAdditionalEffects() : array{
|
||||
return [
|
||||
new EffectInstance(VanillaEffects::REGENERATION(), 600, 4),
|
||||
new EffectInstance(VanillaEffects::REGENERATION(), 600, 1),
|
||||
new EffectInstance(VanillaEffects::ABSORPTION(), 2400, 3),
|
||||
new EffectInstance(VanillaEffects::RESISTANCE(), 6000),
|
||||
new EffectInstance(VanillaEffects::FIRE_RESISTANCE(), 6000)
|
||||
|
@ -654,6 +654,20 @@ class Item implements \JsonSerializable{
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a tag that identifies a group of items that should have cooldown at the same time
|
||||
* regardless of their state or type.
|
||||
* When cooldown starts, any other items with the same cooldown tag can't be used until the cooldown expires.
|
||||
* Such behaviour can be seen in goat horns and shields.
|
||||
*
|
||||
* If tag is null, item state id will be used to store cooldown.
|
||||
*
|
||||
* @see ItemCooldownTags
|
||||
*/
|
||||
public function getCooldownTag() : ?string{
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Compares an Item to this Item and check if they match.
|
||||
*
|
||||
|
45
src/item/ItemCooldownTags.php
Normal file
45
src/item/ItemCooldownTags.php
Normal file
@ -0,0 +1,45 @@
|
||||
<?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\item;
|
||||
|
||||
/**
|
||||
* Tags used by items to determine their cooldown group.
|
||||
*
|
||||
* These tag values are not related to Minecraft internal IDs.
|
||||
* They only share a visual similarity because these are the most obvious values to use.
|
||||
* Any arbitrary string can be used.
|
||||
*
|
||||
* @see Item::getCooldownTag()
|
||||
*/
|
||||
final class ItemCooldownTags{
|
||||
|
||||
private function __construct(){
|
||||
//NOOP
|
||||
}
|
||||
|
||||
public const CHORUS_FRUIT = "chorus_fruit";
|
||||
public const ENDER_PEARL = "ender_pearl";
|
||||
public const SHIELD = "shield";
|
||||
public const GOAT_HORN = "goat_horn";
|
||||
}
|
@ -26,6 +26,7 @@ namespace pocketmine\item;
|
||||
use pocketmine\data\runtime\RuntimeDataDescriber;
|
||||
use pocketmine\entity\Living;
|
||||
use pocketmine\player\Player;
|
||||
use pocketmine\world\sound\BottleEmptySound;
|
||||
|
||||
class Potion extends Item implements ConsumableItem{
|
||||
|
||||
@ -50,7 +51,7 @@ class Potion extends Item implements ConsumableItem{
|
||||
}
|
||||
|
||||
public function onConsume(Living $consumer) : void{
|
||||
|
||||
$consumer->broadcastSound(new BottleEmptySound());
|
||||
}
|
||||
|
||||
public function getAdditionalEffects() : array{
|
||||
|
@ -98,9 +98,14 @@ final class StringToItemParser extends StringToTParser{
|
||||
foreach(["" => false, "waxed_" => true] as $waxedPrefix => $waxed){
|
||||
$register = fn(string $name, \Closure $callback) => $result->registerBlock($waxedPrefix . $oxPrefix . $name, $callback);
|
||||
$register("copper_block", fn() => Blocks::COPPER()->setOxidation($oxidation)->setWaxed($waxed));
|
||||
$register("chiseled_copper", fn() => Blocks::CHISELED_COPPER()->setOxidation($oxidation)->setWaxed($waxed));
|
||||
$register("copper_grate", fn() => Blocks::COPPER_GRATE()->setOxidation($oxidation)->setWaxed($waxed));
|
||||
$register("cut_copper_block", fn() => Blocks::CUT_COPPER()->setOxidation($oxidation)->setWaxed($waxed));
|
||||
$register("cut_copper_stairs", fn() => Blocks::CUT_COPPER_STAIRS()->setOxidation($oxidation)->setWaxed($waxed));
|
||||
$register("cut_copper_slab", fn() => Blocks::CUT_COPPER_SLAB()->setOxidation($oxidation)->setWaxed($waxed));
|
||||
$register("copper_bulb", fn() => Blocks::COPPER_BULB()->setOxidation($oxidation)->setWaxed($waxed));
|
||||
$register("copper_door", fn() => Blocks::COPPER_DOOR()->setOxidation($oxidation)->setWaxed($waxed));
|
||||
$register("copper_trapdoor", fn() => Blocks::COPPER_TRAPDOOR()->setOxidation($oxidation)->setWaxed($waxed));
|
||||
}
|
||||
}
|
||||
|
||||
@ -205,6 +210,7 @@ final class StringToItemParser extends StringToTParser{
|
||||
$result->registerBlock("cake", fn() => Blocks::CAKE());
|
||||
$result->registerBlock("cake_block", fn() => Blocks::CAKE());
|
||||
$result->registerBlock("calcite", fn() => Blocks::CALCITE());
|
||||
$result->registerBlock("campfire", fn() => Blocks::CAMPFIRE());
|
||||
$result->registerBlock("candle", fn() => Blocks::CANDLE());
|
||||
$result->registerBlock("carpet", fn() => Blocks::CARPET());
|
||||
$result->registerBlock("carrot_block", fn() => Blocks::CARROTS());
|
||||
@ -239,6 +245,8 @@ final class StringToItemParser extends StringToTParser{
|
||||
$result->registerBlock("chiseled_red_sandstone", fn() => Blocks::CHISELED_RED_SANDSTONE());
|
||||
$result->registerBlock("chiseled_sandstone", fn() => Blocks::CHISELED_SANDSTONE());
|
||||
$result->registerBlock("chiseled_stone_bricks", fn() => Blocks::CHISELED_STONE_BRICKS());
|
||||
$result->registerBlock("chiseled_tuff", fn() => Blocks::CHISELED_TUFF());
|
||||
$result->registerBlock("chiseled_tuff_bricks", fn() => Blocks::CHISELED_TUFF_BRICKS());
|
||||
$result->registerBlock("chorus_flower", fn() => Blocks::CHORUS_FLOWER());
|
||||
$result->registerBlock("chorus_plant", fn() => Blocks::CHORUS_PLANT());
|
||||
$result->registerBlock("clay_block", fn() => Blocks::CLAY());
|
||||
@ -897,6 +905,10 @@ final class StringToItemParser extends StringToTParser{
|
||||
$result->registerBlock("polished_granite", fn() => Blocks::POLISHED_GRANITE());
|
||||
$result->registerBlock("polished_granite_slab", fn() => Blocks::POLISHED_GRANITE_SLAB());
|
||||
$result->registerBlock("polished_granite_stairs", fn() => Blocks::POLISHED_GRANITE_STAIRS());
|
||||
$result->registerBlock("polished_tuff", fn() => Blocks::POLISHED_TUFF());
|
||||
$result->registerBlock("polished_tuff_slab", fn() => Blocks::POLISHED_TUFF_SLAB());
|
||||
$result->registerBlock("polished_tuff_stairs", fn() => Blocks::POLISHED_TUFF_STAIRS());
|
||||
$result->registerBlock("polished_tuff_wall", fn() => Blocks::POLISHED_TUFF_WALL());
|
||||
$result->registerBlock("poppy", fn() => Blocks::POPPY());
|
||||
$result->registerBlock("portal", fn() => Blocks::NETHER_PORTAL());
|
||||
$result->registerBlock("portal_block", fn() => Blocks::NETHER_PORTAL());
|
||||
@ -1003,6 +1015,7 @@ final class StringToItemParser extends StringToTParser{
|
||||
$result->registerBlock("snow", fn() => Blocks::SNOW());
|
||||
$result->registerBlock("snow_block", fn() => Blocks::SNOW());
|
||||
$result->registerBlock("snow_layer", fn() => Blocks::SNOW_LAYER());
|
||||
$result->registerBlock("soul_campfire", fn() => Blocks::SOUL_CAMPFIRE());
|
||||
$result->registerBlock("soul_lantern", fn() => Blocks::SOUL_LANTERN());
|
||||
$result->registerBlock("soul_sand", fn() => Blocks::SOUL_SAND());
|
||||
$result->registerBlock("soul_soil", fn() => Blocks::SOUL_SOIL());
|
||||
@ -1096,6 +1109,13 @@ final class StringToItemParser extends StringToTParser{
|
||||
$result->registerBlock("trunk", fn() => Blocks::OAK_PLANKS());
|
||||
$result->registerBlock("trunk2", fn() => Blocks::ACACIA_LOG()->setStripped(false));
|
||||
$result->registerBlock("tuff", fn() => Blocks::TUFF());
|
||||
$result->registerBlock("tuff_bricks", fn() => Blocks::TUFF_BRICKS());
|
||||
$result->registerBlock("tuff_brick_slab", fn() => Blocks::TUFF_BRICK_SLAB());
|
||||
$result->registerBlock("tuff_brick_stairs", fn() => Blocks::TUFF_BRICK_STAIRS());
|
||||
$result->registerBlock("tuff_brick_wall", fn() => Blocks::TUFF_BRICK_WALL());
|
||||
$result->registerBlock("tuff_slab", fn() => Blocks::TUFF_SLAB());
|
||||
$result->registerBlock("tuff_stairs", fn() => Blocks::TUFF_STAIRS());
|
||||
$result->registerBlock("tuff_wall", fn() => Blocks::TUFF_WALL());
|
||||
$result->registerBlock("twisting_vines", fn() => Blocks::TWISTING_VINES());
|
||||
$result->registerBlock("underwater_tnt", fn() => Blocks::TNT()->setWorksUnderwater(true));
|
||||
$result->registerBlock("underwater_torch", fn() => Blocks::UNDERWATER_TORCH());
|
||||
|
@ -56,6 +56,7 @@ final class AvailableEnchantmentRegistry{
|
||||
$this->register(Enchantments::PROJECTILE_PROTECTION(), [Tags::ARMOR], []);
|
||||
$this->register(Enchantments::THORNS(), [Tags::CHESTPLATE], [Tags::HELMET, Tags::LEGGINGS, Tags::BOOTS]);
|
||||
$this->register(Enchantments::RESPIRATION(), [Tags::HELMET], []);
|
||||
$this->register(Enchantments::AQUA_AFFINITY(), [Tags::HELMET], []);
|
||||
$this->register(Enchantments::SHARPNESS(), [Tags::SWORD, Tags::AXE], []);
|
||||
$this->register(Enchantments::KNOCKBACK(), [Tags::SWORD], []);
|
||||
$this->register(Enchantments::FIRE_ASPECT(), [Tags::SWORD], []);
|
||||
|
@ -52,6 +52,7 @@ final class StringToEnchantmentParser extends StringToTParser{
|
||||
$result->register("protection", fn() => VanillaEnchantments::PROTECTION());
|
||||
$result->register("punch", fn() => VanillaEnchantments::PUNCH());
|
||||
$result->register("respiration", fn() => VanillaEnchantments::RESPIRATION());
|
||||
$result->register("aqua_affinity", fn() => VanillaEnchantments::AQUA_AFFINITY());
|
||||
$result->register("sharpness", fn() => VanillaEnchantments::SHARPNESS());
|
||||
$result->register("silk_touch", fn() => VanillaEnchantments::SILK_TOUCH());
|
||||
$result->register("swift_sneak", fn() => VanillaEnchantments::SWIFT_SNEAK());
|
||||
|
@ -33,6 +33,7 @@ use pocketmine\utils\RegistryTrait;
|
||||
* @see build/generate-registry-annotations.php
|
||||
* @generate-registry-docblock
|
||||
*
|
||||
* @method static Enchantment AQUA_AFFINITY()
|
||||
* @method static ProtectionEnchantment BLAST_PROTECTION()
|
||||
* @method static Enchantment EFFICIENCY()
|
||||
* @method static ProtectionEnchantment FEATHER_FALLING()
|
||||
@ -144,6 +145,15 @@ final class VanillaEnchantments{
|
||||
fn(int $level) : int => 10 * $level,
|
||||
30
|
||||
));
|
||||
self::register("AQUA_AFFINITY", new Enchantment(
|
||||
KnownTranslationFactory::enchantment_waterWorker(),
|
||||
Rarity::RARE,
|
||||
0,
|
||||
0,
|
||||
1,
|
||||
null,
|
||||
40
|
||||
));
|
||||
|
||||
self::register("SHARPNESS", new SharpnessEnchantment(
|
||||
KnownTranslationFactory::enchantment_damage_all(),
|
||||
|
@ -54,6 +54,7 @@ use pocketmine\network\mcpe\protocol\types\BlockPosition;
|
||||
use pocketmine\network\mcpe\protocol\types\Enchant;
|
||||
use pocketmine\network\mcpe\protocol\types\EnchantOption as ProtocolEnchantOption;
|
||||
use pocketmine\network\mcpe\protocol\types\inventory\ContainerIds;
|
||||
use pocketmine\network\mcpe\protocol\types\inventory\FullContainerName;
|
||||
use pocketmine\network\mcpe\protocol\types\inventory\ItemStack;
|
||||
use pocketmine\network\mcpe\protocol\types\inventory\ItemStackWrapper;
|
||||
use pocketmine\network\mcpe\protocol\types\inventory\NetworkInventoryAction;
|
||||
@ -363,6 +364,7 @@ class InventoryManager{
|
||||
FurnaceType::FURNACE => WindowTypes::FURNACE,
|
||||
FurnaceType::BLAST_FURNACE => WindowTypes::BLAST_FURNACE,
|
||||
FurnaceType::SMOKER => WindowTypes::SMOKER,
|
||||
FurnaceType::CAMPFIRE, FurnaceType::SOUL_CAMPFIRE => throw new \LogicException("Campfire inventory cannot be displayed to a player")
|
||||
},
|
||||
$inv instanceof EnchantInventory => WindowTypes::ENCHANTMENT,
|
||||
$inv instanceof BrewingStandInventory => WindowTypes::BREWING_STAND,
|
||||
@ -500,6 +502,8 @@ class InventoryManager{
|
||||
$this->session->sendDataPacket(InventorySlotPacket::create(
|
||||
$windowId,
|
||||
$netSlot,
|
||||
new FullContainerName($this->lastInventoryNetworkId),
|
||||
new ItemStackWrapper(0, ItemStack::null()),
|
||||
new ItemStackWrapper(0, ItemStack::null())
|
||||
));
|
||||
}
|
||||
@ -507,6 +511,8 @@ class InventoryManager{
|
||||
$this->session->sendDataPacket(InventorySlotPacket::create(
|
||||
$windowId,
|
||||
$netSlot,
|
||||
new FullContainerName($this->lastInventoryNetworkId),
|
||||
new ItemStackWrapper(0, ItemStack::null()),
|
||||
$itemStackWrapper
|
||||
));
|
||||
}
|
||||
@ -525,10 +531,12 @@ class InventoryManager{
|
||||
*/
|
||||
$this->session->sendDataPacket(InventoryContentPacket::create(
|
||||
$windowId,
|
||||
array_fill_keys(array_keys($itemStackWrappers), new ItemStackWrapper(0, ItemStack::null()))
|
||||
array_fill_keys(array_keys($itemStackWrappers), new ItemStackWrapper(0, ItemStack::null())),
|
||||
new FullContainerName($this->lastInventoryNetworkId),
|
||||
new ItemStackWrapper(0, ItemStack::null())
|
||||
));
|
||||
//now send the real contents
|
||||
$this->session->sendDataPacket(InventoryContentPacket::create($windowId, $itemStackWrappers));
|
||||
$this->session->sendDataPacket(InventoryContentPacket::create($windowId, $itemStackWrappers, new FullContainerName($this->lastInventoryNetworkId), new ItemStackWrapper(0, ItemStack::null())));
|
||||
}
|
||||
|
||||
public function syncSlot(Inventory $inventory, int $slot, ItemStack $itemStack) : void{
|
||||
|
@ -30,6 +30,7 @@ use pocketmine\event\server\DataPacketDecodeEvent;
|
||||
use pocketmine\event\server\DataPacketReceiveEvent;
|
||||
use pocketmine\event\server\DataPacketSendEvent;
|
||||
use pocketmine\form\Form;
|
||||
use pocketmine\item\Item;
|
||||
use pocketmine\lang\KnownTranslationFactory;
|
||||
use pocketmine\lang\Translatable;
|
||||
use pocketmine\math\Vector3;
|
||||
@ -54,6 +55,7 @@ use pocketmine\network\mcpe\handler\SessionStartPacketHandler;
|
||||
use pocketmine\network\mcpe\handler\SpawnResponsePacketHandler;
|
||||
use pocketmine\network\mcpe\protocol\AvailableCommandsPacket;
|
||||
use pocketmine\network\mcpe\protocol\ChunkRadiusUpdatedPacket;
|
||||
use pocketmine\network\mcpe\protocol\ClientboundCloseFormPacket;
|
||||
use pocketmine\network\mcpe\protocol\ClientboundPacket;
|
||||
use pocketmine\network\mcpe\protocol\DisconnectPacket;
|
||||
use pocketmine\network\mcpe\protocol\ModalFormRequestPacket;
|
||||
@ -64,6 +66,7 @@ use pocketmine\network\mcpe\protocol\Packet;
|
||||
use pocketmine\network\mcpe\protocol\PacketDecodeException;
|
||||
use pocketmine\network\mcpe\protocol\PacketPool;
|
||||
use pocketmine\network\mcpe\protocol\PlayerListPacket;
|
||||
use pocketmine\network\mcpe\protocol\PlayerStartItemCooldownPacket;
|
||||
use pocketmine\network\mcpe\protocol\PlayStatusPacket;
|
||||
use pocketmine\network\mcpe\protocol\ProtocolInfo;
|
||||
use pocketmine\network\mcpe\protocol\serializer\PacketBatch;
|
||||
@ -110,6 +113,7 @@ use pocketmine\utils\BinaryDataException;
|
||||
use pocketmine\utils\BinaryStream;
|
||||
use pocketmine\utils\ObjectSet;
|
||||
use pocketmine\utils\TextFormat;
|
||||
use pocketmine\world\format\io\GlobalItemDataHandlers;
|
||||
use pocketmine\world\Position;
|
||||
use pocketmine\YmlServerProperties;
|
||||
use function array_map;
|
||||
@ -742,7 +746,7 @@ class NetworkSession{
|
||||
}else{
|
||||
$translated = $message;
|
||||
}
|
||||
$this->sendDataPacket(DisconnectPacket::create(0, $translated));
|
||||
$this->sendDataPacket(DisconnectPacket::create(0, $translated, ""));
|
||||
}
|
||||
|
||||
/**
|
||||
@ -786,7 +790,7 @@ class NetworkSession{
|
||||
public function transfer(string $ip, int $port, Translatable|string|null $reason = null) : void{
|
||||
$reason ??= KnownTranslationFactory::pocketmine_disconnect_transfer();
|
||||
$this->tryDisconnect(function() use ($ip, $port, $reason) : void{
|
||||
$this->sendDataPacket(TransferPacket::create($ip, $port), true);
|
||||
$this->sendDataPacket(TransferPacket::create($ip, $port, false), true);
|
||||
if($this->player !== null){
|
||||
$this->player->onPostDisconnect($reason, null);
|
||||
}
|
||||
@ -1170,6 +1174,10 @@ class NetworkSession{
|
||||
return $this->sendDataPacket(ModalFormRequestPacket::create($id, json_encode($form, JSON_THROW_ON_ERROR)));
|
||||
}
|
||||
|
||||
public function onCloseAllForms() : void{
|
||||
$this->sendDataPacket(ClientboundCloseFormPacket::create());
|
||||
}
|
||||
|
||||
/**
|
||||
* Instructs the networksession to start using the chunk at the given coordinates. This may occur asynchronously.
|
||||
* @param \Closure $onCompletion To be called when chunk sending has completed.
|
||||
@ -1284,6 +1292,13 @@ class NetworkSession{
|
||||
$this->sendDataPacket(OpenSignPacket::create(BlockPosition::fromVector3($signPosition), $frontSide));
|
||||
}
|
||||
|
||||
public function onItemCooldownChanged(Item $item, int $ticks) : void{
|
||||
$this->sendDataPacket(PlayerStartItemCooldownPacket::create(
|
||||
GlobalItemDataHandlers::getSerializer()->serializeType($item)->getName(),
|
||||
$ticks
|
||||
));
|
||||
}
|
||||
|
||||
public function tick() : void{
|
||||
if(!$this->isConnected()){
|
||||
$this->dispose();
|
||||
|
@ -38,9 +38,10 @@ use pocketmine\network\mcpe\protocol\MobEquipmentPacket;
|
||||
use pocketmine\network\mcpe\protocol\RemoveActorPacket;
|
||||
use pocketmine\network\mcpe\protocol\SetActorDataPacket;
|
||||
use pocketmine\network\mcpe\protocol\TakeItemActorPacket;
|
||||
use pocketmine\network\mcpe\protocol\types\entity\Attribute as NetworkAttribute;
|
||||
use pocketmine\network\mcpe\protocol\types\entity\PropertySyncData;
|
||||
use pocketmine\network\mcpe\protocol\types\entity\UpdateAttribute;
|
||||
use pocketmine\network\mcpe\protocol\types\inventory\ContainerIds;
|
||||
use pocketmine\network\mcpe\protocol\types\inventory\ItemStack;
|
||||
use pocketmine\network\mcpe\protocol\types\inventory\ItemStackWrapper;
|
||||
use pocketmine\network\mcpe\protocol\UpdateAttributesPacket;
|
||||
use function array_map;
|
||||
@ -66,7 +67,7 @@ final class StandardEntityEventBroadcaster implements EntityEventBroadcaster{
|
||||
if(count($attributes) > 0){
|
||||
$this->sendDataPacket($recipients, UpdateAttributesPacket::create(
|
||||
$entity->getId(),
|
||||
array_map(fn(Attribute $attr) => new NetworkAttribute($attr->getId(), $attr->getMinValue(), $attr->getMaxValue(), $attr->getValue(), $attr->getDefaultValue(), []), $attributes),
|
||||
array_map(fn(Attribute $attr) => new UpdateAttribute($attr->getId(), $attr->getMinValue(), $attr->getMaxValue(), $attr->getValue(), $attr->getMinValue(), $attr->getMaxValue(), $attr->getDefaultValue(), []), $attributes),
|
||||
0
|
||||
));
|
||||
}
|
||||
@ -131,7 +132,8 @@ final class StandardEntityEventBroadcaster implements EntityEventBroadcaster{
|
||||
ItemStackWrapper::legacy($converter->coreItemStackToNet($inv->getHelmet())),
|
||||
ItemStackWrapper::legacy($converter->coreItemStackToNet($inv->getChestplate())),
|
||||
ItemStackWrapper::legacy($converter->coreItemStackToNet($inv->getLeggings())),
|
||||
ItemStackWrapper::legacy($converter->coreItemStackToNet($inv->getBoots()))
|
||||
ItemStackWrapper::legacy($converter->coreItemStackToNet($inv->getBoots())),
|
||||
new ItemStackWrapper(0, ItemStack::null())
|
||||
));
|
||||
}
|
||||
|
||||
@ -140,6 +142,13 @@ final class StandardEntityEventBroadcaster implements EntityEventBroadcaster{
|
||||
}
|
||||
|
||||
public function onEmote(array $recipients, Human $from, string $emoteId) : void{
|
||||
$this->sendDataPacket($recipients, EmotePacket::create($from->getId(), $emoteId, "", "", EmotePacket::FLAG_SERVER | EmotePacket::FLAG_MUTE_ANNOUNCEMENT));
|
||||
$this->sendDataPacket($recipients, EmotePacket::create(
|
||||
$from->getId(),
|
||||
$emoteId,
|
||||
0, //seems to be irrelevant for the client, we cannot risk rebroadcasting random values received
|
||||
"",
|
||||
"",
|
||||
EmotePacket::FLAG_SERVER | EmotePacket::FLAG_MUTE_ANNOUNCEMENT
|
||||
));
|
||||
}
|
||||
}
|
||||
|
2
src/network/mcpe/cache/CraftingDataCache.php
vendored
2
src/network/mcpe/cache/CraftingDataCache.php
vendored
@ -130,6 +130,8 @@ final class CraftingDataCache{
|
||||
FurnaceType::FURNACE => FurnaceRecipeBlockName::FURNACE,
|
||||
FurnaceType::BLAST_FURNACE => FurnaceRecipeBlockName::BLAST_FURNACE,
|
||||
FurnaceType::SMOKER => FurnaceRecipeBlockName::SMOKER,
|
||||
FurnaceType::CAMPFIRE => FurnaceRecipeBlockName::CAMPFIRE,
|
||||
FurnaceType::SOUL_CAMPFIRE => FurnaceRecipeBlockName::SOUL_CAMPFIRE
|
||||
};
|
||||
foreach($manager->getFurnaceRecipeManager($furnaceType)->getAll() as $recipe){
|
||||
$input = $converter->coreRecipeIngredientToNet($recipe->getInput())->getDescriptor();
|
||||
|
@ -112,10 +112,10 @@ class ItemStackRequestExecutor{
|
||||
* @throws ItemStackRequestProcessException
|
||||
*/
|
||||
protected function getBuilderInventoryAndSlot(ItemStackRequestSlotInfo $info) : array{
|
||||
[$windowId, $slotId] = ItemStackContainerIdTranslator::translate($info->getContainerId(), $this->inventoryManager->getCurrentWindowId(), $info->getSlotId());
|
||||
[$windowId, $slotId] = ItemStackContainerIdTranslator::translate($info->getContainerName()->getContainerId(), $this->inventoryManager->getCurrentWindowId(), $info->getSlotId());
|
||||
$windowAndSlot = $this->inventoryManager->locateWindowAndSlot($windowId, $slotId);
|
||||
if($windowAndSlot === null){
|
||||
throw new ItemStackRequestProcessException("No open inventory matches container UI ID: " . $info->getContainerId() . ", slot ID: " . $info->getSlotId());
|
||||
throw new ItemStackRequestProcessException("No open inventory matches container UI ID: " . $info->getContainerName()->getContainerId() . ", slot ID: " . $info->getSlotId());
|
||||
}
|
||||
[$inventory, $slot] = $windowAndSlot;
|
||||
if(!$inventory->slotExists($slot)){
|
||||
@ -142,7 +142,7 @@ class ItemStackRequestExecutor{
|
||||
* @throws ItemStackRequestProcessException
|
||||
*/
|
||||
protected function removeItemFromSlot(ItemStackRequestSlotInfo $slotInfo, int $count) : Item{
|
||||
if($slotInfo->getContainerId() === ContainerUIIds::CREATED_OUTPUT && $slotInfo->getSlotId() === UIInventorySlotOffset::CREATED_ITEM_OUTPUT){
|
||||
if($slotInfo->getContainerName()->getContainerId() === ContainerUIIds::CREATED_OUTPUT && $slotInfo->getSlotId() === UIInventorySlotOffset::CREATED_ITEM_OUTPUT){
|
||||
//special case for the "created item" output slot
|
||||
//TODO: do we need to send a response for this slot info?
|
||||
return $this->takeCreatedItem($count);
|
||||
@ -343,7 +343,7 @@ class ItemStackRequestExecutor{
|
||||
$this->setNextCreatedItem($window->getOutput($optionId));
|
||||
}
|
||||
}else{
|
||||
$this->beginCrafting($action->getRecipeId(), 1);
|
||||
$this->beginCrafting($action->getRecipeId(), $action->getRepetitions());
|
||||
}
|
||||
}elseif($action instanceof CraftRecipeAutoStackRequestAction){
|
||||
$this->beginCrafting($action->getRecipeId(), $action->getRepetitions());
|
||||
@ -391,7 +391,7 @@ class ItemStackRequestExecutor{
|
||||
public function buildItemStackResponse() : ItemStackResponse{
|
||||
$builder = new ItemStackResponseBuilder($this->request->getRequestId(), $this->inventoryManager);
|
||||
foreach($this->requestSlotInfos as $requestInfo){
|
||||
$builder->addSlot($requestInfo->getContainerId(), $requestInfo->getSlotId());
|
||||
$builder->addSlot($requestInfo->getContainerName()->getContainerId(), $requestInfo->getSlotId());
|
||||
}
|
||||
|
||||
return $builder->build();
|
||||
|
@ -27,6 +27,7 @@ use pocketmine\inventory\Inventory;
|
||||
use pocketmine\item\Durable;
|
||||
use pocketmine\network\mcpe\InventoryManager;
|
||||
use pocketmine\network\mcpe\protocol\types\inventory\ContainerUIIds;
|
||||
use pocketmine\network\mcpe\protocol\types\inventory\FullContainerName;
|
||||
use pocketmine\network\mcpe\protocol\types\inventory\stackresponse\ItemStackResponse;
|
||||
use pocketmine\network\mcpe\protocol\types\inventory\stackresponse\ItemStackResponseContainerInfo;
|
||||
use pocketmine\network\mcpe\protocol\types\inventory\stackresponse\ItemStackResponseSlotInfo;
|
||||
@ -99,7 +100,7 @@ final class ItemStackResponseBuilder{
|
||||
|
||||
$responseContainerInfos = [];
|
||||
foreach($responseInfosByContainer as $containerInterfaceId => $responseInfos){
|
||||
$responseContainerInfos[] = new ItemStackResponseContainerInfo($containerInterfaceId, $responseInfos);
|
||||
$responseContainerInfos[] = new ItemStackResponseContainerInfo(new FullContainerName($containerInterfaceId), $responseInfos);
|
||||
}
|
||||
|
||||
return new ItemStackResponse(ItemStackResponse::RESULT_OK, $this->requestId, $responseContainerInfos);
|
||||
|
@ -39,7 +39,7 @@ use pocketmine\network\mcpe\protocol\types\Experiments;
|
||||
use pocketmine\network\mcpe\protocol\types\LevelSettings;
|
||||
use pocketmine\network\mcpe\protocol\types\NetworkPermissions;
|
||||
use pocketmine\network\mcpe\protocol\types\PlayerMovementSettings;
|
||||
use pocketmine\network\mcpe\protocol\types\PlayerMovementType;
|
||||
use pocketmine\network\mcpe\protocol\types\ServerAuthMovementMode;
|
||||
use pocketmine\network\mcpe\protocol\types\SpawnSettings;
|
||||
use pocketmine\player\Player;
|
||||
use pocketmine\Server;
|
||||
@ -98,7 +98,7 @@ class PreSpawnPacketHandler extends PacketHandler{
|
||||
$this->server->getMotd(),
|
||||
"",
|
||||
false,
|
||||
new PlayerMovementSettings(PlayerMovementType::SERVER_AUTHORITATIVE_V1, 0, false),
|
||||
new PlayerMovementSettings(ServerAuthMovementMode::SERVER_AUTHORITATIVE_V2, 0, false),
|
||||
0,
|
||||
0,
|
||||
"",
|
||||
|
@ -115,12 +115,9 @@ class ResourcePacksPacketHandler extends PacketHandler{
|
||||
//TODO: support forcing server packs
|
||||
$this->session->sendDataPacket(ResourcePacksInfoPacket::create(
|
||||
resourcePackEntries: $resourcePackEntries,
|
||||
behaviorPackEntries: [],
|
||||
mustAccept: $this->mustAccept,
|
||||
hasAddons: false,
|
||||
hasScripts: false,
|
||||
forceServerPacks: false,
|
||||
cdnUrls: []
|
||||
hasScripts: false
|
||||
));
|
||||
$this->session->getLogger()->debug("Waiting for client to accept resource packs");
|
||||
}
|
||||
|
@ -283,7 +283,11 @@ class Player extends Human implements CommandSender, ChunkListener, IPlayer{
|
||||
protected string $locale = "en_US";
|
||||
|
||||
protected int $startAction = -1;
|
||||
/** @var int[] ID => ticks map */
|
||||
|
||||
/**
|
||||
* @phpstan-var array<int|string, int>
|
||||
* @var int[] stateId|cooldownTag => ticks map
|
||||
*/
|
||||
protected array $usedItemsCooldown = [];
|
||||
|
||||
private int $lastEmoteTick = 0;
|
||||
@ -697,7 +701,7 @@ class Player extends Human implements CommandSender, ChunkListener, IPlayer{
|
||||
*/
|
||||
public function getItemCooldownExpiry(Item $item) : int{
|
||||
$this->checkItemCooldowns();
|
||||
return $this->usedItemsCooldown[$item->getStateId()] ?? 0;
|
||||
return $this->usedItemsCooldown[$item->getCooldownTag() ?? $item->getStateId()] ?? 0;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -705,7 +709,7 @@ class Player extends Human implements CommandSender, ChunkListener, IPlayer{
|
||||
*/
|
||||
public function hasItemCooldown(Item $item) : bool{
|
||||
$this->checkItemCooldowns();
|
||||
return isset($this->usedItemsCooldown[$item->getStateId()]);
|
||||
return isset($this->usedItemsCooldown[$item->getCooldownTag() ?? $item->getStateId()]);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -714,7 +718,8 @@ class Player extends Human implements CommandSender, ChunkListener, IPlayer{
|
||||
public function resetItemCooldown(Item $item, ?int $ticks = null) : void{
|
||||
$ticks = $ticks ?? $item->getCooldownTicks();
|
||||
if($ticks > 0){
|
||||
$this->usedItemsCooldown[$item->getStateId()] = $this->server->getTick() + $ticks;
|
||||
$this->usedItemsCooldown[$item->getCooldownTag() ?? $item->getStateId()] = $this->server->getTick() + $ticks;
|
||||
$this->getNetworkSession()->onItemCooldownChanged($item, $ticks);
|
||||
}
|
||||
}
|
||||
|
||||
@ -1620,7 +1625,7 @@ class Player extends Human implements CommandSender, ChunkListener, IPlayer{
|
||||
return false;
|
||||
}
|
||||
|
||||
$this->resetItemCooldown($item);
|
||||
$this->resetItemCooldown($oldItem);
|
||||
$this->returnItemsFromAction($oldItem, $item, $returnedItems);
|
||||
|
||||
$this->setUsingItem($item instanceof Releasable && $item->canStartUsingItem($this));
|
||||
@ -1649,7 +1654,7 @@ class Player extends Human implements CommandSender, ChunkListener, IPlayer{
|
||||
}
|
||||
|
||||
$this->setUsingItem(false);
|
||||
$this->resetItemCooldown($slot);
|
||||
$this->resetItemCooldown($oldItem);
|
||||
|
||||
$slot->pop();
|
||||
$this->returnItemsFromAction($oldItem, $slot, [$slot->getResidue()]);
|
||||
@ -1677,7 +1682,7 @@ class Player extends Human implements CommandSender, ChunkListener, IPlayer{
|
||||
$returnedItems = [];
|
||||
$result = $item->onReleaseUsing($this, $returnedItems);
|
||||
if($result === ItemUseResult::SUCCESS){
|
||||
$this->resetItemCooldown($item);
|
||||
$this->resetItemCooldown($oldItem);
|
||||
$this->returnItemsFromAction($oldItem, $item, $returnedItems);
|
||||
return true;
|
||||
}
|
||||
@ -2151,6 +2156,13 @@ class Player extends Human implements CommandSender, ChunkListener, IPlayer{
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Closes the current viewing form and forms in queue.
|
||||
*/
|
||||
public function closeAllForms() : void{
|
||||
$this->getNetworkSession()->onCloseAllForms();
|
||||
}
|
||||
|
||||
/**
|
||||
* Transfers a player to another server.
|
||||
*
|
||||
|
@ -60,6 +60,8 @@ interface ResourcePack{
|
||||
* @param int $start Offset to start reading the chunk from
|
||||
* @param int $length Maximum length of data to return.
|
||||
*
|
||||
* @phpstan-param positive-int $length
|
||||
*
|
||||
* @return string byte-array
|
||||
* @throws \InvalidArgumentException if the chunk does not exist
|
||||
*/
|
||||
|
@ -154,6 +154,9 @@ class ZippedResourcePack implements ResourcePack{
|
||||
}
|
||||
|
||||
public function getPackChunk(int $start, int $length) : string{
|
||||
if($length < 1){
|
||||
throw new \InvalidArgumentException("Pack length must be positive");
|
||||
}
|
||||
fseek($this->fileResource, $start);
|
||||
if(feof($this->fileResource)){
|
||||
throw new \InvalidArgumentException("Requested a resource pack chunk with invalid start offset");
|
||||
|
@ -23,6 +23,7 @@ declare(strict_types=1);
|
||||
|
||||
namespace pocketmine\world\format\io;
|
||||
|
||||
use pocketmine\data\bedrock\item\BlockItemIdMap;
|
||||
use pocketmine\data\bedrock\item\ItemDeserializer;
|
||||
use pocketmine\data\bedrock\item\ItemSerializer;
|
||||
use pocketmine\data\bedrock\item\upgrade\ItemDataUpgrader;
|
||||
@ -30,6 +31,7 @@ use pocketmine\data\bedrock\item\upgrade\ItemIdMetaUpgrader;
|
||||
use pocketmine\data\bedrock\item\upgrade\ItemIdMetaUpgradeSchemaUtils;
|
||||
use pocketmine\data\bedrock\item\upgrade\LegacyItemIdToStringIdMap;
|
||||
use pocketmine\data\bedrock\item\upgrade\R12ItemIdToBlockIdMap;
|
||||
use pocketmine\network\mcpe\convert\TypeConverter;
|
||||
use Symfony\Component\Filesystem\Path;
|
||||
use const PHP_INT_MAX;
|
||||
use const pocketmine\BEDROCK_ITEM_UPGRADE_SCHEMA_PATH;
|
||||
@ -54,7 +56,9 @@ final class GlobalItemDataHandlers{
|
||||
new ItemIdMetaUpgrader(ItemIdMetaUpgradeSchemaUtils::loadSchemas(Path::join(BEDROCK_ITEM_UPGRADE_SCHEMA_PATH, 'id_meta_upgrade_schema'), PHP_INT_MAX)),
|
||||
LegacyItemIdToStringIdMap::getInstance(),
|
||||
R12ItemIdToBlockIdMap::getInstance(),
|
||||
GlobalBlockStateHandlers::getUpgrader()
|
||||
GlobalBlockStateHandlers::getUpgrader(),
|
||||
BlockItemIdMap::getInstance(),
|
||||
TypeConverter::getInstance()->getBlockTranslator()->getBlockStateDictionary()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user