├── .github └── workflows │ └── gradle.yml ├── .gitignore ├── CONTRIBUTING.md ├── LICENSE ├── README.md ├── build.gradle ├── gradle └── wrapper │ ├── gradle-wrapper.jar │ └── gradle-wrapper.properties ├── gradlew ├── gradlew.bat ├── jitpack.yml ├── legacy ├── build.gradle └── src │ └── main │ └── java │ └── me │ └── jumper251 │ └── replay │ └── legacy │ ├── LegacyBlock.java │ ├── LegacyMaterial.java │ └── LegacyUtils.java ├── settings.gradle └── src └── main ├── java ├── com │ └── comphenix │ │ └── packetwrapper │ │ ├── AbstractPacket.java │ │ ├── WrapperPlayClientArmAnimation.java │ │ ├── WrapperPlayClientBlockDig.java │ │ ├── WrapperPlayClientBlockPlace.java │ │ ├── WrapperPlayClientEntityAction.java │ │ ├── WrapperPlayClientHeldItemSlot.java │ │ ├── WrapperPlayClientKeepAlive.java │ │ ├── WrapperPlayClientLook.java │ │ ├── WrapperPlayClientPosition.java │ │ ├── WrapperPlayClientPositionLook.java │ │ ├── WrapperPlayClientSetCreativeSlot.java │ │ ├── WrapperPlayClientSteerVehicle.java │ │ ├── WrapperPlayClientUseEntity.java │ │ ├── WrapperPlayClientVehicleMove.java │ │ ├── WrapperPlayClientWindowClick.java │ │ ├── WrapperPlayServerAnimation.java │ │ ├── WrapperPlayServerBed.java │ │ ├── WrapperPlayServerBlockBreakAnimation.java │ │ ├── WrapperPlayServerCamera.java │ │ ├── WrapperPlayServerEntityDestroy.java │ │ ├── WrapperPlayServerEntityEffect.java │ │ ├── WrapperPlayServerEntityEquipment.java │ │ ├── WrapperPlayServerEntityHeadRotation.java │ │ ├── WrapperPlayServerEntityLook.java │ │ ├── WrapperPlayServerEntityMetadata.java │ │ ├── WrapperPlayServerEntityStatus.java │ │ ├── WrapperPlayServerEntityTeleport.java │ │ ├── WrapperPlayServerEntityVelocity.java │ │ ├── WrapperPlayServerExplosion.java │ │ ├── WrapperPlayServerGameStateChange.java │ │ ├── WrapperPlayServerKeepAlive.java │ │ ├── WrapperPlayServerNamedEntitySpawn.java │ │ ├── WrapperPlayServerPlayerInfo.java │ │ ├── WrapperPlayServerRelEntityMove.java │ │ ├── WrapperPlayServerRelEntityMoveLook.java │ │ ├── WrapperPlayServerScoreboardTeam.java │ │ ├── WrapperPlayServerSpawnEntity.java │ │ ├── WrapperPlayServerSpawnEntityLiving.java │ │ ├── WrapperPlayServerTitle.java │ │ ├── WrapperPlayServerUpdateHealth.java │ │ ├── WrapperStatusClientPing.java │ │ ├── old │ │ ├── WrapperPlayServerEntityEquipment.java │ │ ├── WrapperPlayServerEntityHeadRotation.java │ │ ├── WrapperPlayServerEntityLook.java │ │ ├── WrapperPlayServerEntityMoveLook.java │ │ ├── WrapperPlayServerEntityTeleport.java │ │ ├── WrapperPlayServerNamedEntitySpawn.java │ │ ├── WrapperPlayServerRelEntityMoveLook.java │ │ ├── WrapperPlayServerSpawnEntity.java │ │ └── WrapperPlayServerSpawnEntityLiving.java │ │ └── v15 │ │ ├── WrapperPlayServerRelEntityMove.java │ │ └── WrapperPlayServerRelEntityMoveLook.java └── me │ └── jumper251 │ └── replay │ ├── ReplaySystem.java │ ├── api │ ├── HookManager.java │ ├── IReplayHook.java │ ├── ReplayAPI.java │ └── ReplaySessionFinishEvent.java │ ├── commands │ ├── AbstractCommand.java │ ├── CommandPagination.java │ ├── IPaginationExecutor.java │ ├── MessageFormat.java │ ├── SubCommand.java │ └── replay │ │ ├── ReplayCommand.java │ │ ├── ReplayDeleteCommand.java │ │ ├── ReplayInfoCommand.java │ │ ├── ReplayJumpCommand.java │ │ ├── ReplayLeaveCommand.java │ │ ├── ReplayListCommand.java │ │ ├── ReplayMigrateCommand.java │ │ ├── ReplayPlayCommand.java │ │ ├── ReplayReformatCommand.java │ │ ├── ReplayReloadCommand.java │ │ ├── ReplayStartCommand.java │ │ └── ReplayStopCommand.java │ ├── database │ ├── DatabaseRegistry.java │ ├── MySQLDatabase.java │ ├── MySQLService.java │ └── utils │ │ ├── AutoReconnector.java │ │ ├── Database.java │ │ ├── DatabaseService.java │ │ └── Result.java │ ├── filesystem │ ├── ConfigManager.java │ ├── ConfigMessage.java │ ├── ItemConfig.java │ ├── ItemConfigOption.java │ ├── ItemConfigType.java │ ├── MessageBuilder.java │ ├── Messages.java │ └── saving │ │ ├── DatabaseReplaySaver.java │ │ ├── DefaultReplaySaver.java │ │ ├── IReplaySaver.java │ │ ├── ReplaySaver.java │ │ └── S3ReplaySaver.java │ ├── listener │ ├── AbstractListener.java │ └── ReplayListener.java │ ├── replaysystem │ ├── Replay.java │ ├── data │ │ ├── ActionData.java │ │ ├── ActionType.java │ │ ├── ReplayData.java │ │ ├── ReplayInfo.java │ │ └── types │ │ │ ├── AnimationData.java │ │ │ ├── BedEnterData.java │ │ │ ├── BlockChangeData.java │ │ │ ├── BlockPositionData.java │ │ │ ├── ChatData.java │ │ │ ├── EntityActionData.java │ │ │ ├── EntityAnimationData.java │ │ │ ├── EntityData.java │ │ │ ├── EntityDestroyData.java │ │ │ ├── EntityItemData.java │ │ │ ├── EntityMovingData.java │ │ │ ├── ExplosionData.java │ │ │ ├── FishingData.java │ │ │ ├── InvData.java │ │ │ ├── ItemData.java │ │ │ ├── LocationData.java │ │ │ ├── MetadataUpdate.java │ │ │ ├── MovingData.java │ │ │ ├── PacketData.java │ │ │ ├── ProjectileData.java │ │ │ ├── SerializableItemStack.java │ │ │ ├── SignatureData.java │ │ │ ├── SpawnData.java │ │ │ ├── TNTSpawnData.java │ │ │ ├── VelocityData.java │ │ │ └── WorldChangeData.java │ ├── recording │ │ ├── CompListener.java │ │ ├── PacketRecorder.java │ │ ├── PlayerWatcher.java │ │ ├── Recorder.java │ │ ├── RecordingListener.java │ │ └── optimization │ │ │ ├── ReplayOptimizer.java │ │ │ ├── ReplayQuality.java │ │ │ └── ReplayStats.java │ ├── replaying │ │ ├── ReplayHelper.java │ │ ├── ReplayPacketListener.java │ │ ├── Replayer.java │ │ ├── ReplayingMode.java │ │ ├── ReplayingUtils.java │ │ └── session │ │ │ ├── ReplayProgressType.java │ │ │ ├── ReplayProgression.java │ │ │ └── ReplaySession.java │ └── utils │ │ ├── ItemUtils.java │ │ ├── MetadataBuilder.java │ │ ├── NPCManager.java │ │ ├── ReplayCleanup.java │ │ └── entities │ │ ├── EntityMappings.java │ │ ├── FishingUtils.java │ │ ├── IEntity.java │ │ ├── INPC.java │ │ ├── NPCSpawnPacket.java │ │ ├── PacketEntity.java │ │ ├── PacketEntityOld.java │ │ ├── PacketNPC.java │ │ ├── PacketNPCOld.java │ │ └── SpawnPacket.java │ └── utils │ ├── IntEnum.java │ ├── LogUtils.java │ ├── MathUtils.java │ ├── Metrics.java │ ├── ProtocolLibUtil.java │ ├── ReflectionHelper.java │ ├── ReplayManager.java │ ├── StringUtils.java │ ├── Updater.java │ ├── VersionUtil.java │ ├── fetcher │ ├── Acceptor.java │ ├── Consumer.java │ ├── JsonClass.java │ ├── JsonData.java │ ├── PlayerInfo.java │ ├── SkinInfo.java │ ├── TextureInfo.java │ └── WebsiteFetcher.java │ └── version │ ├── EnchantmentBridge.java │ ├── EntityBridge.java │ └── MaterialBridge.java └── resources └── plugin.yml /.github/workflows/gradle.yml: -------------------------------------------------------------------------------- 1 | 2 | name: Java CI with Gradle 3 | 4 | on: 5 | push: 6 | branches: [ master ] 7 | 8 | jobs: 9 | build: 10 | 11 | runs-on: ubuntu-latest 12 | 13 | steps: 14 | - uses: actions/checkout@v4 15 | - name: Set up JDK 17 16 | uses: actions/setup-java@v4 17 | with: 18 | java-version: '17' 19 | distribution: 'temurin' 20 | - name: Setup Gradle 21 | uses: gradle/actions/setup-gradle@af1da67850ed9a4cedd57bfd976089dd991e2582 # v4.0.0 22 | 23 | - name: Build with Gradle Wrapper 24 | run: ./gradlew build 25 | - name: Upload a Build Artifact 26 | uses: actions/upload-artifact@v4 27 | with: 28 | # Artifact name 29 | name: Replay.jar 30 | # A file, directory or wildcard pattern that describes what to upload 31 | path: build/libs/Replay.jar 32 | # The desired behavior if no files are found using the provided path. 33 | compression-level: 0 -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | /bin/ 2 | 3 | # Compiled class file 4 | *.class 5 | 6 | # Log file 7 | *.log 8 | 9 | # BlueJ files 10 | *.ctxt 11 | 12 | # Mobile Tools for Java (J2ME) 13 | .mtj.tmp/ 14 | 15 | # Package Files # 16 | *.jar 17 | *.war 18 | *.nar 19 | *.ear 20 | *.zip 21 | *.tar.gz 22 | *.rar 23 | 24 | # virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml 25 | hs_err_pid* 26 | 27 | .idea/ 28 | *.iml 29 | 30 | /out/ 31 | 32 | # Maven 33 | target/ 34 | pom.xml.tag 35 | pom.xml.releaseBackup 36 | pom.xml.versionsBackup 37 | pom.xml.next 38 | release.properties 39 | dependency-reduced-pom.xml 40 | buildNumber.properties 41 | .mvn/timing.properties 42 | .mvn/wrapper/maven-wrapper.jar 43 | 44 | .gradle/ 45 | build/ 46 | !gradle/wrapper/gradle-wrapper.jar -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing 2 | All Contributions are welcome! 3 | 4 | For code style, refer to the Google Java Style Guide: 5 | https://google.github.io/styleguide/javaguide.html 6 | Generally, you can use IntelliJ's default formatting (Ctrl+Alt+L). 7 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # AdvancedReplay 2 | 3 | AdvancedReplay is a Minecraft 1.8 & 1.21 Replay plugin. It can record players on your Server and save the recorded data to a file or database, so you can watch the replays at any time. Currently it records almost every action a player does and can be easily controlled with commands or the API. 4 | 5 | ## Downloads 6 | **Modrinth**: https://modrinth.com/plugin/advancedreplay 7 | **Spigot**: https://www.spigotmc.org/resources/advancedreplay-1-8-1-21.52849/ 8 | 9 | ## API 10 | ### Maven 11 | #### Add the repositories: 12 | ```xml 13 | 14 | 15 | 16 | jitpack.io 17 | https://jitpack.io 18 | 19 | 20 | 21 | maven-snapshots 22 | https://s01.oss.sonatype.org/content/repositories/snapshots/ 23 | 24 | ``` 25 | #### Add the dependency: 26 | ```xml 27 | 28 | com.github.Jumper251 29 | AdvancedReplay 30 | VERSION 31 | provided 32 | 33 | ``` 34 | ### Gradle 35 | ```text 36 | repositories { 37 | maven { url 'https://jitpack.io' } 38 | } 39 | 40 | dependencies { 41 | compileOnly 'com.github.Jumper251:AdvancedReplay:VERSION' 42 | } 43 | ``` 44 | 45 | ### API usage 46 | Some examples on how to use the API can be found on the plugins Spigot page. 47 | -------------------------------------------------------------------------------- /build.gradle: -------------------------------------------------------------------------------- 1 | plugins { 2 | id 'java' 3 | id 'com.gradleup.shadow' version '8.3.0' 4 | id 'maven-publish' 5 | } 6 | 7 | 8 | repositories { 9 | mavenCentral() 10 | maven { url = "https://hub.spigotmc.org/nexus/content/repositories/snapshots/" } 11 | // ProtocolLib repo 12 | maven { url "https://repo.dmulloy2.net/repository/public/" } 13 | // Libby repo 14 | maven { url = 'https://s01.oss.sonatype.org/content/repositories/snapshots/' } 15 | } 16 | 17 | dependencies { 18 | implementation project(':legacy') 19 | 20 | compileOnly "org.spigotmc:spigot-api:1.21.5-R0.1-SNAPSHOT" 21 | compileOnly 'com.comphenix.protocol:ProtocolLib:5.3.0' 22 | 23 | // Dependency resolver at runtime 24 | implementation 'com.alessiodp.libby:libby-bukkit:2.0.0-SNAPSHOT' 25 | // S3 storage backend 26 | compileOnly 'io.minio:minio:8.5.12' 27 | } 28 | 29 | allprojects { 30 | group = 'me.jumper251.replay' 31 | version = '1.8.13' 32 | 33 | apply plugin: 'java' 34 | apply plugin: 'maven-publish' 35 | 36 | java { 37 | sourceCompatibility = 1.8 38 | targetCompatibility = 1.8 39 | } 40 | 41 | compileJava { 42 | options.encoding("UTF-8") 43 | } 44 | 45 | publishing { 46 | publications { 47 | maven(MavenPublication) { 48 | groupId project.group 49 | artifactId project.name 50 | version project.version 51 | from components.java 52 | } 53 | } 54 | } 55 | } 56 | 57 | shadowJar { 58 | archiveFileName = 'Replay.jar' 59 | 60 | relocate 'com.alessiodp.libby', 'me.jumper251.replay.libs.com.alessiodp.libby' 61 | relocate 'com.comphenix.packetwrapper', 'me.jumper251.replay.libs.com.comphenix.packetwrapper' 62 | } 63 | 64 | processResources { 65 | def props = [version: version] 66 | inputs.properties props 67 | filteringCharset 'UTF-8' 68 | filesMatching('plugin.yml') { 69 | expand props 70 | } 71 | } 72 | 73 | build { 74 | dependsOn shadowJar 75 | } -------------------------------------------------------------------------------- /gradle/wrapper/gradle-wrapper.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Jumper251/AdvancedReplay/65062f4a0b5326089485c5dfd26f3de0fae858cc/gradle/wrapper/gradle-wrapper.jar -------------------------------------------------------------------------------- /gradle/wrapper/gradle-wrapper.properties: -------------------------------------------------------------------------------- 1 | distributionBase=GRADLE_USER_HOME 2 | distributionPath=wrapper/dists 3 | distributionUrl=https\://services.gradle.org/distributions/gradle-8.5-bin.zip 4 | networkTimeout=10000 5 | validateDistributionUrl=true 6 | zipStoreBase=GRADLE_USER_HOME 7 | zipStorePath=wrapper/dists 8 | -------------------------------------------------------------------------------- /gradlew.bat: -------------------------------------------------------------------------------- 1 | @rem 2 | @rem Copyright 2015 the original author or authors. 3 | @rem 4 | @rem Licensed under the Apache License, Version 2.0 (the "License"); 5 | @rem you may not use this file except in compliance with the License. 6 | @rem You may obtain a copy of the License at 7 | @rem 8 | @rem https://www.apache.org/licenses/LICENSE-2.0 9 | @rem 10 | @rem Unless required by applicable law or agreed to in writing, software 11 | @rem distributed under the License is distributed on an "AS IS" BASIS, 12 | @rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | @rem See the License for the specific language governing permissions and 14 | @rem limitations under the License. 15 | @rem 16 | 17 | @if "%DEBUG%"=="" @echo off 18 | @rem ########################################################################## 19 | @rem 20 | @rem Gradle startup script for Windows 21 | @rem 22 | @rem ########################################################################## 23 | 24 | @rem Set local scope for the variables with windows NT shell 25 | if "%OS%"=="Windows_NT" setlocal 26 | 27 | set DIRNAME=%~dp0 28 | if "%DIRNAME%"=="" set DIRNAME=. 29 | @rem This is normally unused 30 | set APP_BASE_NAME=%~n0 31 | set APP_HOME=%DIRNAME% 32 | 33 | @rem Resolve any "." and ".." in APP_HOME to make it shorter. 34 | for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi 35 | 36 | @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. 37 | set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m" 38 | 39 | @rem Find java.exe 40 | if defined JAVA_HOME goto findJavaFromJavaHome 41 | 42 | set JAVA_EXE=java.exe 43 | %JAVA_EXE% -version >NUL 2>&1 44 | if %ERRORLEVEL% equ 0 goto execute 45 | 46 | echo. 47 | echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. 48 | echo. 49 | echo Please set the JAVA_HOME variable in your environment to match the 50 | echo location of your Java installation. 51 | 52 | goto fail 53 | 54 | :findJavaFromJavaHome 55 | set JAVA_HOME=%JAVA_HOME:"=% 56 | set JAVA_EXE=%JAVA_HOME%/bin/java.exe 57 | 58 | if exist "%JAVA_EXE%" goto execute 59 | 60 | echo. 61 | echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% 62 | echo. 63 | echo Please set the JAVA_HOME variable in your environment to match the 64 | echo location of your Java installation. 65 | 66 | goto fail 67 | 68 | :execute 69 | @rem Setup the command line 70 | 71 | set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar 72 | 73 | 74 | @rem Execute Gradle 75 | "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %* 76 | 77 | :end 78 | @rem End local scope for the variables with windows NT shell 79 | if %ERRORLEVEL% equ 0 goto mainEnd 80 | 81 | :fail 82 | rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of 83 | rem the _cmd.exe /c_ return code! 84 | set EXIT_CODE=%ERRORLEVEL% 85 | if %EXIT_CODE% equ 0 set EXIT_CODE=1 86 | if not ""=="%GRADLE_EXIT_CONSOLE%" exit %EXIT_CODE% 87 | exit /b %EXIT_CODE% 88 | 89 | :mainEnd 90 | if "%OS%"=="Windows_NT" endlocal 91 | 92 | :omega 93 | -------------------------------------------------------------------------------- /jitpack.yml: -------------------------------------------------------------------------------- 1 | before_install: 2 | - sdk update 3 | - sdk install java 21-zulu 4 | - sdk use java 21-zulu -------------------------------------------------------------------------------- /legacy/build.gradle: -------------------------------------------------------------------------------- 1 | repositories { 2 | mavenCentral() 3 | maven { url = "https://hub.spigotmc.org/nexus/content/repositories/snapshots/" } 4 | maven { url = 'https://oss.sonatype.org/content/repositories/snapshots' } 5 | maven { url = 'https://oss.sonatype.org/content/repositories/central' } 6 | } 7 | 8 | dependencies { 9 | compileOnly "org.spigotmc:spigot-api:1.8.8-R0.1-SNAPSHOT" 10 | } 11 | -------------------------------------------------------------------------------- /legacy/src/main/java/me/jumper251/replay/legacy/LegacyBlock.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.legacy; 2 | 3 | import org.bukkit.Location; 4 | import org.bukkit.block.Block; 5 | import org.bukkit.entity.Player; 6 | 7 | public class LegacyBlock { 8 | 9 | public static void setTypeIdAndData(Block block, int typeId, byte data, boolean applyPhysics) { 10 | block.setTypeIdAndData(typeId, data, applyPhysics); 11 | } 12 | 13 | public static void sendBlockChange(Player player, Location loc, int typeId, byte data) { 14 | player.sendBlockChange(loc, typeId, data); 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /legacy/src/main/java/me/jumper251/replay/legacy/LegacyMaterial.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.legacy; 2 | 3 | import org.bukkit.Material; 4 | 5 | public class LegacyMaterial { 6 | 7 | public static Material getMaterialById(int id) { 8 | return Material.getMaterial(id); 9 | } 10 | 11 | } 12 | -------------------------------------------------------------------------------- /legacy/src/main/java/me/jumper251/replay/legacy/LegacyUtils.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.legacy; 2 | 3 | import org.bukkit.Material; 4 | import org.bukkit.event.inventory.InventoryClickEvent; 5 | 6 | public class LegacyUtils { 7 | 8 | public static String getInventoryTitle(InventoryClickEvent event) { 9 | return event.getView().getTitle(); 10 | } 11 | } 12 | -------------------------------------------------------------------------------- /settings.gradle: -------------------------------------------------------------------------------- 1 | pluginManagement { 2 | repositories { 3 | gradlePluginPortal() 4 | } 5 | } 6 | 7 | rootProject.name = 'AdvancedReplay' 8 | include 'legacy' 9 | 10 | -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/AbstractPacket.java: -------------------------------------------------------------------------------- 1 | /** 2 | * This file is part of PacketWrapper. 3 | * Copyright (C) 2012-2015 Kristian S. Strangeland 4 | * Copyright (C) 2015 dmulloy2 5 | * 6 | * PacketWrapper is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU Lesser General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * PacketWrapper is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public License 17 | * along with PacketWrapper. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.ProtocolLibrary; 23 | import com.comphenix.protocol.events.PacketContainer; 24 | import com.google.common.base.Objects; 25 | import org.bukkit.entity.Player; 26 | 27 | import java.lang.reflect.InvocationTargetException; 28 | 29 | public abstract class AbstractPacket { 30 | // The packet we will be modifying 31 | protected PacketContainer handle; 32 | 33 | /** 34 | * Constructs a new strongly typed wrapper for the given packet. 35 | * @param handle - handle to the raw packet data. 36 | * @param type - the packet type. 37 | */ 38 | protected AbstractPacket(PacketContainer handle, PacketType type) { 39 | // Make sure we're given a valid packet 40 | if (handle == null) 41 | throw new IllegalArgumentException("Packet handle cannot be NULL."); 42 | if (!Objects.equal(handle.getType(), type)) 43 | throw new IllegalArgumentException(handle.getHandle() + " is not a packet of type " + type); 44 | 45 | this.handle = handle; 46 | } 47 | 48 | /** 49 | * Retrieve a handle to the raw packet data. 50 | * @return Raw packet data. 51 | */ 52 | public PacketContainer getHandle() { 53 | return handle; 54 | } 55 | 56 | /** 57 | * Send the current packet to the given receiver. 58 | * @param receiver - the receiver. 59 | * @throws RuntimeException If the packet cannot be sent. 60 | */ 61 | public void sendPacket(Player receiver) { 62 | try { 63 | ProtocolLibrary.getProtocolManager().sendServerPacket(receiver, getHandle()); 64 | } catch (Exception e) { 65 | throw new RuntimeException("Cannot send packet.", e); 66 | } 67 | } 68 | 69 | /** 70 | * Simulate receiving the current packet from the given sender. 71 | * @param sender - the sender. 72 | * @throws RuntimeException If the packet cannot be received. 73 | * @deprecated Misspelled. recieve -> receive 74 | * @see #receivePacket(Player) 75 | */ 76 | @Deprecated 77 | public void recievePacket(Player sender) { 78 | try { 79 | ProtocolLibrary.getProtocolManager().receiveClientPacket(sender, getHandle()); 80 | } catch (Exception e) { 81 | throw new RuntimeException("Cannot recieve packet.", e); 82 | } 83 | } 84 | 85 | /** 86 | * Simulate receiving the current packet from the given sender. 87 | * @param sender - the sender. 88 | * @throws RuntimeException if the packet cannot be received. 89 | */ 90 | public void receivePacket(Player sender) { 91 | try { 92 | ProtocolLibrary.getProtocolManager().receiveClientPacket(sender, getHandle()); 93 | } catch (Exception e) { 94 | throw new RuntimeException("Cannot recieve packet.", e); 95 | } 96 | } 97 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayClientArmAnimation.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | 24 | public class WrapperPlayClientArmAnimation extends AbstractPacket { 25 | public static final PacketType TYPE = PacketType.Play.Client.ARM_ANIMATION; 26 | 27 | public WrapperPlayClientArmAnimation() { 28 | super(new PacketContainer(TYPE), TYPE); 29 | handle.getModifier().writeDefaults(); 30 | } 31 | 32 | public WrapperPlayClientArmAnimation(PacketContainer packet) { 33 | super(packet, TYPE); 34 | } 35 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayClientBlockDig.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | import com.comphenix.protocol.wrappers.BlockPosition; 24 | import com.comphenix.protocol.wrappers.EnumWrappers.Direction; 25 | import com.comphenix.protocol.wrappers.EnumWrappers.PlayerDigType; 26 | 27 | public class WrapperPlayClientBlockDig extends AbstractPacket { 28 | public static final PacketType TYPE = PacketType.Play.Client.BLOCK_DIG; 29 | 30 | public WrapperPlayClientBlockDig() { 31 | super(new PacketContainer(TYPE), TYPE); 32 | handle.getModifier().writeDefaults(); 33 | } 34 | 35 | public WrapperPlayClientBlockDig(PacketContainer packet) { 36 | super(packet, TYPE); 37 | } 38 | 39 | /** 40 | * Retrieve Location. 41 | *

42 | * Notes: block position 43 | * 44 | * @return The current Location 45 | */ 46 | public BlockPosition getLocation() { 47 | return handle.getBlockPositionModifier().read(0); 48 | } 49 | 50 | /** 51 | * Set Location. 52 | * 53 | * @param value - new value. 54 | */ 55 | public void setLocation(BlockPosition value) { 56 | handle.getBlockPositionModifier().write(0, value); 57 | } 58 | 59 | public Direction getDirection() { 60 | return handle.getDirections().read(0); 61 | } 62 | 63 | public void setDirection(Direction value) { 64 | handle.getDirections().write(0, value); 65 | } 66 | 67 | /** 68 | * Retrieve Status. 69 | *

70 | * Notes: the action the player is taking against the block (see below) 71 | * 72 | * @return The current Status 73 | */ 74 | public PlayerDigType getStatus() { 75 | return handle.getPlayerDigTypes().read(0); 76 | } 77 | 78 | /** 79 | * Set Status. 80 | * 81 | * @param value - new value. 82 | */ 83 | public void setStatus(PlayerDigType value) { 84 | handle.getPlayerDigTypes().write(0, value); 85 | } 86 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayClientBlockPlace.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | import com.comphenix.protocol.wrappers.EnumWrappers.Hand; 24 | 25 | public class WrapperPlayClientBlockPlace extends AbstractPacket { 26 | public static final PacketType TYPE = PacketType.Play.Client.BLOCK_PLACE; 27 | 28 | public WrapperPlayClientBlockPlace() { 29 | super(new PacketContainer(TYPE), TYPE); 30 | handle.getModifier().writeDefaults(); 31 | } 32 | 33 | public WrapperPlayClientBlockPlace(PacketContainer packet) { 34 | super(packet, TYPE); 35 | } 36 | 37 | public Hand getHand() { 38 | return handle.getHands().read(0); 39 | } 40 | 41 | public void setHand(Hand value) { 42 | handle.getHands().write(0, value); 43 | } 44 | 45 | public long getTimestamp() { 46 | return handle.getLongs().read(0); 47 | } 48 | 49 | public void setTimestamp(long value) { 50 | handle.getLongs().write(0, value); 51 | } 52 | 53 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayClientEntityAction.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import org.bukkit.World; 22 | import org.bukkit.entity.Entity; 23 | 24 | import com.comphenix.protocol.PacketType; 25 | import com.comphenix.protocol.events.PacketContainer; 26 | import com.comphenix.protocol.events.PacketEvent; 27 | import com.comphenix.protocol.wrappers.EnumWrappers.PlayerAction; 28 | 29 | public class WrapperPlayClientEntityAction extends AbstractPacket { 30 | public static final PacketType TYPE = PacketType.Play.Client.ENTITY_ACTION; 31 | 32 | public WrapperPlayClientEntityAction() { 33 | super(new PacketContainer(TYPE), TYPE); 34 | handle.getModifier().writeDefaults(); 35 | } 36 | 37 | public WrapperPlayClientEntityAction(PacketContainer packet) { 38 | super(packet, TYPE); 39 | } 40 | 41 | /** 42 | * Retrieve Entity ID. 43 | *

44 | * Notes: entity's ID 45 | * 46 | * @return The current Entity ID 47 | */ 48 | public int getEntityID() { 49 | return handle.getIntegers().read(0); 50 | } 51 | 52 | /** 53 | * Set Entity ID. 54 | * 55 | * @param value - new value. 56 | */ 57 | public void setEntityID(int value) { 58 | handle.getIntegers().write(0, value); 59 | } 60 | 61 | /** 62 | * Retrieve the entity of the painting that will be spawned. 63 | * 64 | * @param world - the current world of the entity. 65 | * @return The spawned entity. 66 | */ 67 | public Entity getEntity(World world) { 68 | return handle.getEntityModifier(world).read(0); 69 | } 70 | 71 | /** 72 | * Retrieve the entity of the painting that will be spawned. 73 | * 74 | * @param event - the packet event. 75 | * @return The spawned entity. 76 | */ 77 | public Entity getEntity(PacketEvent event) { 78 | return getEntity(event.getPlayer().getWorld()); 79 | } 80 | 81 | /** 82 | * Retrieve Action ID. 83 | *

84 | * Notes: the ID of the action, see below. 85 | * 86 | * @return The current Action ID 87 | */ 88 | public PlayerAction getAction() { 89 | return handle.getPlayerActions().read(0); 90 | } 91 | 92 | /** 93 | * Set Action ID. 94 | * 95 | * @param value - new value. 96 | */ 97 | public void setAction(PlayerAction value) { 98 | handle.getPlayerActions().write(0, value); 99 | } 100 | 101 | /** 102 | * Retrieve Jump Boost. 103 | *

104 | * Notes: horse jump boost. Ranged from 0 -> 100. 105 | * 106 | * @return The current Jump Boost 107 | */ 108 | public int getJumpBoost() { 109 | return handle.getIntegers().read(1); 110 | } 111 | 112 | /** 113 | * Set Jump Boost. 114 | * 115 | * @param value - new value. 116 | */ 117 | public void setJumpBoost(int value) { 118 | handle.getIntegers().write(1, value); 119 | } 120 | 121 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayClientHeldItemSlot.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | 24 | public class WrapperPlayClientHeldItemSlot extends AbstractPacket { 25 | public static final PacketType TYPE = PacketType.Play.Client.HELD_ITEM_SLOT; 26 | 27 | public WrapperPlayClientHeldItemSlot() { 28 | super(new PacketContainer(TYPE), TYPE); 29 | handle.getModifier().writeDefaults(); 30 | } 31 | 32 | public WrapperPlayClientHeldItemSlot(PacketContainer packet) { 33 | super(packet, TYPE); 34 | } 35 | 36 | /** 37 | * Retrieve Slot. 38 | *

39 | * Notes: the slot which the player has selected (0-8) 40 | * 41 | * @return The current Slot 42 | */ 43 | public int getSlot() { 44 | return handle.getIntegers().read(0); 45 | } 46 | 47 | /** 48 | * Set Slot. 49 | * 50 | * @param value - new value. 51 | */ 52 | public void setSlot(int value) { 53 | handle.getIntegers().write(0, value); 54 | } 55 | 56 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayClientKeepAlive.java: -------------------------------------------------------------------------------- 1 | /** 2 | * This file is part of PacketWrapper. 3 | * Copyright (C) 2012-2015 Kristian S. Strangeland 4 | * Copyright (C) 2015 dmulloy2 5 | * 6 | * PacketWrapper is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU Lesser General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * PacketWrapper is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public License 17 | * along with PacketWrapper. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | 24 | public class WrapperPlayClientKeepAlive extends AbstractPacket { 25 | public static final PacketType TYPE = PacketType.Play.Client.KEEP_ALIVE; 26 | 27 | public WrapperPlayClientKeepAlive() { 28 | super(new PacketContainer(TYPE), TYPE); 29 | handle.getModifier().writeDefaults(); 30 | } 31 | 32 | public WrapperPlayClientKeepAlive(PacketContainer packet) { 33 | super(packet, TYPE); 34 | } 35 | 36 | /** 37 | * Retrieve Keep Alive ID. 38 | * @return The current Keep Alive ID 39 | */ 40 | public int getKeepAliveId() { 41 | return handle.getIntegers().read(0); 42 | } 43 | 44 | /** 45 | * Set Keep Alive ID. 46 | * @param value - new value. 47 | */ 48 | public void setKeepAliveId(int value) { 49 | handle.getIntegers().write(0, value); 50 | } 51 | 52 | } 53 | -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayClientLook.java: -------------------------------------------------------------------------------- 1 | /** 2 | * This file is part of PacketWrapper. 3 | * Copyright (C) 2012-2015 Kristian S. Strangeland 4 | * Copyright (C) 2015 dmulloy2 5 | * 6 | * PacketWrapper is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU Lesser General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * PacketWrapper is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public License 17 | * along with PacketWrapper. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | 24 | public class WrapperPlayClientLook extends AbstractPacket { 25 | public static final PacketType TYPE = PacketType.Play.Client.LOOK; 26 | 27 | public WrapperPlayClientLook() { 28 | super(new PacketContainer(TYPE), TYPE); 29 | handle.getModifier().writeDefaults(); 30 | } 31 | 32 | public WrapperPlayClientLook(PacketContainer packet) { 33 | super(packet, TYPE); 34 | } 35 | 36 | /** 37 | * Retrieve Yaw. 38 | *

39 | * Notes: absolute rotation on the X Axis, in degrees 40 | * @return The current Yaw 41 | */ 42 | public float getYaw() { 43 | return handle.getFloat().read(0); 44 | } 45 | 46 | /** 47 | * Set Yaw. 48 | * @param value - new value. 49 | */ 50 | public void setYaw(float value) { 51 | handle.getFloat().write(0, value); 52 | } 53 | 54 | /** 55 | * Retrieve Pitch. 56 | *

57 | * Notes: absolute rotation on the Y Axis, in degrees 58 | * @return The current Pitch 59 | */ 60 | public float getPitch() { 61 | return handle.getFloat().read(1); 62 | } 63 | 64 | /** 65 | * Set Pitch. 66 | * @param value - new value. 67 | */ 68 | public void setPitch(float value) { 69 | handle.getFloat().write(1, value); 70 | } 71 | 72 | /** 73 | * Retrieve On Ground. 74 | *

75 | * Notes: true if the client is on the ground, False otherwise 76 | * @return The current On Ground 77 | */ 78 | public boolean getOnGround() { 79 | return handle.getBooleans().read(0); 80 | } 81 | 82 | /** 83 | * Set On Ground. 84 | * @param value - new value. 85 | */ 86 | public void setOnGround(boolean value) { 87 | handle.getBooleans().write(0, value); 88 | } 89 | 90 | } 91 | -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayClientPosition.java: -------------------------------------------------------------------------------- 1 | /** 2 | * This file is part of PacketWrapper. 3 | * Copyright (C) 2012-2015 Kristian S. Strangeland 4 | * Copyright (C) 2015 dmulloy2 5 | * 6 | * PacketWrapper is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU Lesser General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * PacketWrapper is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public License 17 | * along with PacketWrapper. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | 24 | public class WrapperPlayClientPosition extends AbstractPacket { 25 | public static final PacketType TYPE = PacketType.Play.Client.POSITION; 26 | 27 | public WrapperPlayClientPosition() { 28 | super(new PacketContainer(TYPE), TYPE); 29 | handle.getModifier().writeDefaults(); 30 | } 31 | 32 | public WrapperPlayClientPosition(PacketContainer packet) { 33 | super(packet, TYPE); 34 | } 35 | 36 | /** 37 | * Retrieve X. 38 | *

39 | * Notes: absolute position 40 | * @return The current X 41 | */ 42 | public double getX() { 43 | return handle.getDoubles().read(0); 44 | } 45 | 46 | /** 47 | * Set X. 48 | * @param value - new value. 49 | */ 50 | public void setX(double value) { 51 | handle.getDoubles().write(0, value); 52 | } 53 | 54 | /** 55 | * Retrieve FeetY. 56 | *

57 | * Notes: absolute feet position, normally HeadY - 1.62. Used to modify the players bounding box when going up stairs, crouching, etc 58 | * @return The current FeetY 59 | */ 60 | public double getY() { 61 | return handle.getDoubles().read(1); 62 | } 63 | 64 | /** 65 | * Set FeetY. 66 | * @param value - new value. 67 | */ 68 | public void setY(double value) { 69 | handle.getDoubles().write(1, value); 70 | } 71 | 72 | /** 73 | * Retrieve Z. 74 | *

75 | * Notes: absolute position 76 | * @return The current Z 77 | */ 78 | public double getZ() { 79 | return handle.getDoubles().read(2); 80 | } 81 | 82 | /** 83 | * Set Z. 84 | * @param value - new value. 85 | */ 86 | public void setZ(double value) { 87 | handle.getDoubles().write(2, value); 88 | } 89 | 90 | /** 91 | * Retrieve On Ground. 92 | *

93 | * Notes: true if the client is on the ground, False otherwise 94 | * @return The current On Ground 95 | */ 96 | public boolean getOnGround() { 97 | return handle.getBooleans().read(0); 98 | } 99 | 100 | /** 101 | * Set On Ground. 102 | * @param value - new value. 103 | */ 104 | public void setOnGround(boolean value) { 105 | handle.getBooleans().write(0, value); 106 | } 107 | 108 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayClientSetCreativeSlot.java: -------------------------------------------------------------------------------- 1 | /** 2 | * This file is part of PacketWrapper. 3 | * Copyright (C) 2012-2015 Kristian S. Strangeland 4 | * Copyright (C) 2015 dmulloy2 5 | * 6 | * PacketWrapper is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU Lesser General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * PacketWrapper is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public License 17 | * along with PacketWrapper. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | import org.bukkit.inventory.ItemStack; 24 | 25 | public class WrapperPlayClientSetCreativeSlot extends AbstractPacket { 26 | public static final PacketType TYPE = PacketType.Play.Client.SET_CREATIVE_SLOT; 27 | 28 | public WrapperPlayClientSetCreativeSlot() { 29 | super(new PacketContainer(TYPE), TYPE); 30 | handle.getModifier().writeDefaults(); 31 | } 32 | 33 | public WrapperPlayClientSetCreativeSlot(PacketContainer packet) { 34 | super(packet, TYPE); 35 | } 36 | 37 | /** 38 | * Retrieve Slot. 39 | *

40 | * Notes: inventory slot 41 | * @return The current Slot 42 | */ 43 | public int getSlot() { 44 | return handle.getIntegers().read(0); 45 | } 46 | 47 | /** 48 | * Set Slot. 49 | * @param value - new value. 50 | */ 51 | public void setSlot(int value) { 52 | handle.getIntegers().write(0, value); 53 | } 54 | 55 | /** 56 | * Retrieve Clicked item. 57 | * @return The current Clicked item 58 | */ 59 | public ItemStack getClickedItem() { 60 | return handle.getItemModifier().read(0); 61 | } 62 | 63 | /** 64 | * Set Clicked item. 65 | * @param value - new value. 66 | */ 67 | public void setClickedItem(ItemStack value) { 68 | handle.getItemModifier().write(0, value); 69 | } 70 | 71 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayClientSteerVehicle.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | 24 | public class WrapperPlayClientSteerVehicle extends AbstractPacket { 25 | public static final PacketType TYPE = PacketType.Play.Client.STEER_VEHICLE; 26 | 27 | public WrapperPlayClientSteerVehicle() { 28 | super(new PacketContainer(TYPE), TYPE); 29 | handle.getModifier().writeDefaults(); 30 | } 31 | 32 | public WrapperPlayClientSteerVehicle(PacketContainer packet) { 33 | super(packet, TYPE); 34 | } 35 | 36 | /** 37 | * Retrieve Sideways. 38 | *

39 | * Notes: positive to the left of the player 40 | * 41 | * @return The current Sideways 42 | */ 43 | public float getSideways() { 44 | return handle.getFloat().read(0); 45 | } 46 | 47 | /** 48 | * Set Sideways. 49 | * 50 | * @param value - new value. 51 | */ 52 | public void setSideways(float value) { 53 | handle.getFloat().write(0, value); 54 | } 55 | 56 | /** 57 | * Retrieve Forward. 58 | *

59 | * Notes: positive forward 60 | * 61 | * @return The current Forward 62 | */ 63 | public float getForward() { 64 | return handle.getFloat().read(1); 65 | } 66 | 67 | /** 68 | * Set Forward. 69 | * 70 | * @param value - new value. 71 | */ 72 | public void setForward(float value) { 73 | handle.getFloat().write(1, value); 74 | } 75 | 76 | public boolean isJump() { 77 | return handle.getBooleans().read(0); 78 | } 79 | 80 | public void setJump(boolean value) { 81 | handle.getBooleans().write(0, value); 82 | } 83 | 84 | public boolean isUnmount() { 85 | return handle.getBooleans().read(1); 86 | } 87 | 88 | public void setUnmount(boolean value) { 89 | handle.getBooleans().write(1, value); 90 | } 91 | 92 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayClientUseEntity.java: -------------------------------------------------------------------------------- 1 | /** 2 | * This file is part of PacketWrapper. 3 | * Copyright (C) 2012-2015 Kristian S. Strangeland 4 | * Copyright (C) 2015 dmulloy2 5 | * 6 | * PacketWrapper is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU Lesser General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * PacketWrapper is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public License 17 | * along with PacketWrapper. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | import com.comphenix.protocol.events.PacketEvent; 24 | import com.comphenix.protocol.wrappers.EnumWrappers.EntityUseAction; 25 | 26 | import me.jumper251.replay.utils.VersionUtil; 27 | import me.jumper251.replay.utils.VersionUtil.VersionEnum; 28 | 29 | import org.bukkit.World; 30 | import org.bukkit.entity.Entity; 31 | import org.bukkit.util.Vector; 32 | 33 | public class WrapperPlayClientUseEntity extends AbstractPacket { 34 | public static final PacketType TYPE = PacketType.Play.Client.USE_ENTITY; 35 | 36 | public WrapperPlayClientUseEntity() { 37 | super(new PacketContainer(TYPE), TYPE); 38 | handle.getModifier().writeDefaults(); 39 | } 40 | 41 | public WrapperPlayClientUseEntity(PacketContainer packet) { 42 | super(packet, TYPE); 43 | } 44 | 45 | /** 46 | * Retrieve entity ID of the target. 47 | * @return The current entity ID 48 | */ 49 | public int getTargetID() { 50 | return handle.getIntegers().read(0); 51 | } 52 | 53 | /** 54 | * Retrieve the entity that was targeted. 55 | * @param world - the current world of the entity. 56 | * @return The targeted entity. 57 | */ 58 | public Entity getTarget(World world) { 59 | return handle.getEntityModifier(world).read(0); 60 | } 61 | 62 | /** 63 | * Retrieve the entity that was targeted. 64 | * @param event - the packet event. 65 | * @return The targeted entity. 66 | */ 67 | public Entity getTarget(PacketEvent event) { 68 | return getTarget(event.getPlayer().getWorld()); 69 | } 70 | 71 | /** 72 | * Set entity ID of the target. 73 | * @param value - new value. 74 | */ 75 | public void setTargetID(int value) { 76 | handle.getIntegers().write(0, value); 77 | } 78 | 79 | /** 80 | * Retrieve Type. 81 | * @return The current Type 82 | */ 83 | public EntityUseAction getType() { 84 | if (VersionUtil.isAbove(VersionEnum.V1_17)) 85 | return handle.getEnumEntityUseActions().read(0).getAction(); 86 | 87 | return handle.getEntityUseActions().read(0); 88 | } 89 | 90 | /** 91 | * Set Type. 92 | * @param value - new value. 93 | */ 94 | public void setType(EntityUseAction value) { 95 | handle.getEntityUseActions().write(0, value); 96 | } 97 | 98 | /** 99 | * Retrieve the target vector. 100 | *

101 | * Notes: Only if {@link #getType()} is {@link EntityUseAction#INTERACT_AT}. 102 | * 103 | * @return The target vector or null 104 | */ 105 | public Vector getTargetVector() { 106 | return handle.getVectors().read(0); 107 | } 108 | 109 | /** 110 | * Set the target vector. 111 | * @param value - new value. 112 | */ 113 | public void setTargetVector(Vector value) { 114 | handle.getVectors().write(0, value); 115 | } 116 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayClientVehicleMove.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | 24 | public class WrapperPlayClientVehicleMove extends AbstractPacket { 25 | 26 | public static final PacketType TYPE = PacketType.Play.Client.VEHICLE_MOVE; 27 | 28 | public WrapperPlayClientVehicleMove() { 29 | super(new PacketContainer(TYPE), TYPE); 30 | handle.getModifier().writeDefaults(); 31 | } 32 | 33 | public WrapperPlayClientVehicleMove(PacketContainer packet) { 34 | super(packet, TYPE); 35 | } 36 | 37 | /** 38 | * Retrieve X. 39 | *

40 | * Notes: absolute position (X coordinate) 41 | * 42 | * @return The current X 43 | */ 44 | public double getX() { 45 | return handle.getDoubles().read(0); 46 | } 47 | 48 | /** 49 | * Set X. 50 | * 51 | * @param value - new value. 52 | */ 53 | public void setX(double value) { 54 | handle.getDoubles().write(0, value); 55 | } 56 | 57 | /** 58 | * Retrieve Y. 59 | *

60 | * Notes: absolute position (Y coordinate) 61 | * 62 | * @return The current Y 63 | */ 64 | public double getY() { 65 | return handle.getDoubles().read(1); 66 | } 67 | 68 | /** 69 | * Set Y. 70 | * 71 | * @param value - new value. 72 | */ 73 | public void setY(double value) { 74 | handle.getDoubles().write(1, value); 75 | } 76 | 77 | /** 78 | * Retrieve Z. 79 | *

80 | * Notes: absolute position (Z coordinate) 81 | * 82 | * @return The current Z 83 | */ 84 | public double getZ() { 85 | return handle.getDoubles().read(2); 86 | } 87 | 88 | /** 89 | * Set Z. 90 | * 91 | * @param value - new value. 92 | */ 93 | public void setZ(double value) { 94 | handle.getDoubles().write(2, value); 95 | } 96 | 97 | /** 98 | * Retrieve Yaw. 99 | *

100 | * Notes: absolute rotation on the vertical axis, in degrees 101 | * 102 | * @return The current Yaw 103 | */ 104 | public float getYaw() { 105 | return handle.getFloat().read(0); 106 | } 107 | 108 | /** 109 | * Set Yaw. 110 | * 111 | * @param value - new value. 112 | */ 113 | public void setYaw(float value) { 114 | handle.getFloat().write(0, value); 115 | } 116 | 117 | /** 118 | * Retrieve Pitch. 119 | *

120 | * Notes: absolute rotation on the horizontal axis, in degrees 121 | * 122 | * @return The current Pitch 123 | */ 124 | public float getPitch() { 125 | return handle.getFloat().read(1); 126 | } 127 | 128 | /** 129 | * Set Pitch. 130 | * 131 | * @param value - new value. 132 | */ 133 | public void setPitch(float value) { 134 | handle.getFloat().write(1, value); 135 | } 136 | 137 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerAnimation.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import org.bukkit.World; 22 | import org.bukkit.entity.Entity; 23 | 24 | import com.comphenix.protocol.PacketType; 25 | import com.comphenix.protocol.events.PacketContainer; 26 | import com.comphenix.protocol.events.PacketEvent; 27 | 28 | public class WrapperPlayServerAnimation extends AbstractPacket { 29 | public static final PacketType TYPE = PacketType.Play.Server.ANIMATION; 30 | 31 | public WrapperPlayServerAnimation() { 32 | super(new PacketContainer(TYPE), TYPE); 33 | handle.getModifier().writeDefaults(); 34 | } 35 | 36 | public WrapperPlayServerAnimation(PacketContainer packet) { 37 | super(packet, TYPE); 38 | } 39 | 40 | /** 41 | * Retrieve Entity ID. 42 | *

43 | * Notes: entity's ID 44 | * 45 | * @return The current Entity ID 46 | */ 47 | public int getEntityID() { 48 | return handle.getIntegers().read(0); 49 | } 50 | 51 | /** 52 | * Set Entity ID. 53 | * 54 | * @param value - new value. 55 | */ 56 | public void setEntityID(int value) { 57 | handle.getIntegers().write(0, value); 58 | } 59 | 60 | /** 61 | * Retrieve the entity of the painting that will be spawned. 62 | * 63 | * @param world - the current world of the entity. 64 | * @return The spawned entity. 65 | */ 66 | public Entity getEntity(World world) { 67 | return handle.getEntityModifier(world).read(0); 68 | } 69 | 70 | /** 71 | * Retrieve the entity of the painting that will be spawned. 72 | * 73 | * @param event - the packet event. 74 | * @return The spawned entity. 75 | */ 76 | public Entity getEntity(PacketEvent event) { 77 | return getEntity(event.getPlayer().getWorld()); 78 | } 79 | 80 | /** 81 | * Retrieve Animation. 82 | *

83 | * Notes: animation ID 84 | * 85 | * @return The current Animation 86 | */ 87 | public int getAnimation() { 88 | return handle.getIntegers().read(1); 89 | } 90 | 91 | /** 92 | * Set Animation. 93 | * 94 | * @param value - new value. 95 | */ 96 | public void setAnimation(int value) { 97 | handle.getIntegers().write(1, value); 98 | } 99 | 100 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerBed.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import org.bukkit.World; 22 | import org.bukkit.entity.Entity; 23 | 24 | import com.comphenix.protocol.PacketType; 25 | import com.comphenix.protocol.events.PacketContainer; 26 | import com.comphenix.protocol.events.PacketEvent; 27 | import com.comphenix.protocol.wrappers.BlockPosition; 28 | 29 | public class WrapperPlayServerBed extends AbstractPacket { 30 | public static final PacketType TYPE = PacketType.Play.Server.BED; 31 | 32 | public WrapperPlayServerBed() { 33 | super(new PacketContainer(TYPE), TYPE); 34 | handle.getModifier().writeDefaults(); 35 | } 36 | 37 | public WrapperPlayServerBed(PacketContainer packet) { 38 | super(packet, TYPE); 39 | } 40 | 41 | /** 42 | * Retrieve Entity ID. 43 | *

44 | * Notes: entity's ID 45 | * 46 | * @return The current Entity ID 47 | */ 48 | public int getEntityID() { 49 | return handle.getIntegers().read(0); 50 | } 51 | 52 | /** 53 | * Set Entity ID. 54 | * 55 | * @param value - new value. 56 | */ 57 | public void setEntityID(int value) { 58 | handle.getIntegers().write(0, value); 59 | } 60 | 61 | /** 62 | * Retrieve the entity of the painting that will be spawned. 63 | * 64 | * @param world - the current world of the entity. 65 | * @return The spawned entity. 66 | */ 67 | public Entity getEntity(World world) { 68 | return handle.getEntityModifier(world).read(0); 69 | } 70 | 71 | /** 72 | * Retrieve the entity of the painting that will be spawned. 73 | * 74 | * @param event - the packet event. 75 | * @return The spawned entity. 76 | */ 77 | public Entity getEntity(PacketEvent event) { 78 | return getEntity(event.getPlayer().getWorld()); 79 | } 80 | 81 | /** 82 | * Retrieve Location. 83 | *

84 | * Notes: block location of the head part of the bed 85 | * 86 | * @return The current Location 87 | */ 88 | public BlockPosition getLocation() { 89 | return handle.getBlockPositionModifier().read(0); 90 | } 91 | 92 | /** 93 | * Set Location. 94 | * 95 | * @param value - new value. 96 | */ 97 | public void setLocation(BlockPosition value) { 98 | handle.getBlockPositionModifier().write(0, value); 99 | } 100 | 101 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerBlockBreakAnimation.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import org.bukkit.World; 22 | import org.bukkit.entity.Entity; 23 | 24 | import com.comphenix.protocol.PacketType; 25 | import com.comphenix.protocol.events.PacketContainer; 26 | import com.comphenix.protocol.events.PacketEvent; 27 | import com.comphenix.protocol.wrappers.BlockPosition; 28 | 29 | public class WrapperPlayServerBlockBreakAnimation extends AbstractPacket { 30 | public static final PacketType TYPE = 31 | PacketType.Play.Server.BLOCK_BREAK_ANIMATION; 32 | 33 | public WrapperPlayServerBlockBreakAnimation() { 34 | super(new PacketContainer(TYPE), TYPE); 35 | handle.getModifier().writeDefaults(); 36 | } 37 | 38 | public WrapperPlayServerBlockBreakAnimation(PacketContainer packet) { 39 | super(packet, TYPE); 40 | } 41 | 42 | /** 43 | * Retrieve Entity ID. 44 | *

45 | * Notes: entity's ID 46 | * 47 | * @return The current Entity ID 48 | */ 49 | public int getEntityID() { 50 | return handle.getIntegers().read(0); 51 | } 52 | 53 | /** 54 | * Set Entity ID. 55 | * 56 | * @param value - new value. 57 | */ 58 | public void setEntityID(int value) { 59 | handle.getIntegers().write(0, value); 60 | } 61 | 62 | /** 63 | * Retrieve the entity of the painting that will be spawned. 64 | * 65 | * @param world - the current world of the entity. 66 | * @return The spawned entity. 67 | */ 68 | public Entity getEntity(World world) { 69 | return handle.getEntityModifier(world).read(0); 70 | } 71 | 72 | /** 73 | * Retrieve the entity of the painting that will be spawned. 74 | * 75 | * @param event - the packet event. 76 | * @return The spawned entity. 77 | */ 78 | public Entity getEntity(PacketEvent event) { 79 | return getEntity(event.getPlayer().getWorld()); 80 | } 81 | 82 | /** 83 | * Retrieve Location. 84 | *

85 | * Notes: block Position 86 | * 87 | * @return The current Location 88 | */ 89 | public BlockPosition getLocation() { 90 | return handle.getBlockPositionModifier().read(0); 91 | } 92 | 93 | /** 94 | * Set Location. 95 | * 96 | * @param value - new value. 97 | */ 98 | public void setLocation(BlockPosition value) { 99 | handle.getBlockPositionModifier().write(0, value); 100 | } 101 | 102 | /** 103 | * Retrieve Destroy Stage. 104 | *

105 | * Notes: 0 - 9 106 | * 107 | * @return The current Destroy Stage 108 | */ 109 | public int getDestroyStage() { 110 | return handle.getIntegers().read(1); 111 | } 112 | 113 | /** 114 | * Set Destroy Stage. 115 | * 116 | * @param value - new value. 117 | */ 118 | public void setDestroyStage(int value) { 119 | handle.getIntegers().write(1, value); 120 | } 121 | 122 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerCamera.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | 24 | public class WrapperPlayServerCamera extends AbstractPacket { 25 | public static final PacketType TYPE = PacketType.Play.Server.CAMERA; 26 | 27 | public WrapperPlayServerCamera() { 28 | super(new PacketContainer(TYPE), TYPE); 29 | handle.getModifier().writeDefaults(); 30 | } 31 | 32 | public WrapperPlayServerCamera(PacketContainer packet) { 33 | super(packet, TYPE); 34 | } 35 | 36 | /** 37 | * Retrieve Camera ID. 38 | * 39 | * @return The current Camera ID 40 | */ 41 | public int getCameraId() { 42 | return handle.getIntegers().read(0); 43 | } 44 | 45 | /** 46 | * Set Camera ID. 47 | * 48 | * @param value - new value. 49 | */ 50 | public void setCameraId(int value) { 51 | handle.getIntegers().write(0, value); 52 | } 53 | 54 | } 55 | -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerEntityDestroy.java: -------------------------------------------------------------------------------- 1 | /** 2 | * This file is part of PacketWrapper. 3 | * Copyright (C) 2012-2015 Kristian S. Strangeland 4 | * Copyright (C) 2015 dmulloy2 5 | *

6 | * PacketWrapper is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU Lesser General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | *

11 | * PacketWrapper is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | *

16 | * You should have received a copy of the GNU Lesser General Public License 17 | * along with PacketWrapper. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | import me.jumper251.replay.utils.VersionUtil; 24 | 25 | import java.util.ArrayList; 26 | import java.util.List; 27 | 28 | public class WrapperPlayServerEntityDestroy extends AbstractPacket { 29 | public static final PacketType TYPE = PacketType.Play.Server.ENTITY_DESTROY; 30 | 31 | public WrapperPlayServerEntityDestroy() { 32 | super(new PacketContainer(TYPE), TYPE); 33 | handle.getModifier().writeDefaults(); 34 | } 35 | 36 | public WrapperPlayServerEntityDestroy(PacketContainer packet) { 37 | super(packet, TYPE); 38 | } 39 | 40 | /** 41 | * Retrieve Count. 42 | *

43 | * Notes: length of following array 44 | * @return The current Count 45 | */ 46 | public int getCount() { 47 | return getEntityIDs().length; 48 | } 49 | 50 | /** 51 | * Retrieve Entity IDs. 52 | *

53 | * Notes: the list of entities of destroy 54 | * @return The current Entity IDs 55 | */ 56 | public int[] getEntityIDs() { 57 | if (VersionUtil.isAbove(VersionUtil.VersionEnum.V1_17)) { 58 | return handle.getIntLists().read(0).stream().mapToInt(Integer::intValue).toArray(); 59 | } else { 60 | return handle.getIntegerArrays().read(0); 61 | } 62 | } 63 | 64 | /** 65 | * Set Entity IDs. 66 | * @param value - new value. 67 | */ 68 | public void setEntityIds(int[] value) { 69 | if (VersionUtil.isAbove(VersionUtil.VersionEnum.V1_17)) { 70 | List ints = new ArrayList<>(value.length); 71 | for (int i : value) ints.add(i); 72 | handle.getIntLists().write(0, ints); 73 | } else { 74 | handle.getIntegerArrays().write(0, value); 75 | } 76 | } 77 | 78 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerEntityEquipment.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import org.bukkit.World; 22 | import org.bukkit.entity.Entity; 23 | import org.bukkit.inventory.ItemStack; 24 | 25 | import com.comphenix.protocol.PacketType; 26 | import com.comphenix.protocol.events.PacketContainer; 27 | import com.comphenix.protocol.events.PacketEvent; 28 | import com.comphenix.protocol.wrappers.EnumWrappers.ItemSlot; 29 | 30 | public class WrapperPlayServerEntityEquipment extends AbstractPacket { 31 | public static final PacketType TYPE = 32 | PacketType.Play.Server.ENTITY_EQUIPMENT; 33 | 34 | public WrapperPlayServerEntityEquipment() { 35 | super(new PacketContainer(TYPE), TYPE); 36 | handle.getModifier().writeDefaults(); 37 | } 38 | 39 | public WrapperPlayServerEntityEquipment(PacketContainer packet) { 40 | super(packet, TYPE); 41 | } 42 | 43 | /** 44 | * Retrieve Entity ID. 45 | *

46 | * Notes: entity's ID 47 | * 48 | * @return The current Entity ID 49 | */ 50 | public int getEntityID() { 51 | return handle.getIntegers().read(0); 52 | } 53 | 54 | /** 55 | * Set Entity ID. 56 | * 57 | * @param value - new value. 58 | */ 59 | public void setEntityID(int value) { 60 | handle.getIntegers().write(0, value); 61 | } 62 | 63 | /** 64 | * Retrieve the entity of the painting that will be spawned. 65 | * 66 | * @param world - the current world of the entity. 67 | * @return The spawned entity. 68 | */ 69 | public Entity getEntity(World world) { 70 | return handle.getEntityModifier(world).read(0); 71 | } 72 | 73 | /** 74 | * Retrieve the entity of the painting that will be spawned. 75 | * 76 | * @param event - the packet event. 77 | * @return The spawned entity. 78 | */ 79 | public Entity getEntity(PacketEvent event) { 80 | return getEntity(event.getPlayer().getWorld()); 81 | } 82 | 83 | public ItemSlot getSlot() { 84 | return handle.getItemSlots().read(0); 85 | } 86 | 87 | public void setSlot(ItemSlot value) { 88 | handle.getItemSlots().write(0, value); 89 | } 90 | 91 | /** 92 | * Retrieve Item. 93 | *

94 | * Notes: item in slot format 95 | * 96 | * @return The current Item 97 | */ 98 | public ItemStack getItem() { 99 | return handle.getItemModifier().read(0); 100 | } 101 | 102 | /** 103 | * Set Item. 104 | * 105 | * @param value - new value. 106 | */ 107 | public void setItem(ItemStack value) { 108 | handle.getItemModifier().write(0, value); 109 | } 110 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerEntityHeadRotation.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import org.bukkit.World; 22 | import org.bukkit.entity.Entity; 23 | 24 | import com.comphenix.protocol.PacketType; 25 | import com.comphenix.protocol.events.PacketContainer; 26 | import com.comphenix.protocol.events.PacketEvent; 27 | 28 | public class WrapperPlayServerEntityHeadRotation extends AbstractPacket { 29 | public static final PacketType TYPE = 30 | PacketType.Play.Server.ENTITY_HEAD_ROTATION; 31 | 32 | public WrapperPlayServerEntityHeadRotation() { 33 | super(new PacketContainer(TYPE), TYPE); 34 | handle.getModifier().writeDefaults(); 35 | } 36 | 37 | public WrapperPlayServerEntityHeadRotation(PacketContainer packet) { 38 | super(packet, TYPE); 39 | } 40 | 41 | /** 42 | * Retrieve Entity ID. 43 | *

44 | * Notes: entity's ID 45 | * 46 | * @return The current Entity ID 47 | */ 48 | public int getEntityID() { 49 | return handle.getIntegers().read(0); 50 | } 51 | 52 | /** 53 | * Set Entity ID. 54 | * 55 | * @param value - new value. 56 | */ 57 | public void setEntityID(int value) { 58 | handle.getIntegers().write(0, value); 59 | } 60 | 61 | /** 62 | * Retrieve the entity of the painting that will be spawned. 63 | * 64 | * @param world - the current world of the entity. 65 | * @return The spawned entity. 66 | */ 67 | public Entity getEntity(World world) { 68 | return handle.getEntityModifier(world).read(0); 69 | } 70 | 71 | /** 72 | * Retrieve the entity of the painting that will be spawned. 73 | * 74 | * @param event - the packet event. 75 | * @return The spawned entity. 76 | */ 77 | public Entity getEntity(PacketEvent event) { 78 | return getEntity(event.getPlayer().getWorld()); 79 | } 80 | 81 | /** 82 | * Retrieve Head Yaw. 83 | *

84 | * Notes: head yaw in steps of 2p/256 85 | * 86 | * @return The current Head Yaw 87 | */ 88 | public byte getHeadYaw() { 89 | return handle.getBytes().read(0); 90 | } 91 | 92 | /** 93 | * Set Head Yaw. 94 | * 95 | * @param value - new value. 96 | */ 97 | public void setHeadYaw(byte value) { 98 | handle.getBytes().write(0, value); 99 | } 100 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerEntityMetadata.java: -------------------------------------------------------------------------------- 1 | /** 2 | * This file is part of PacketWrapper. 3 | * Copyright (C) 2012-2015 Kristian S. Strangeland 4 | * Copyright (C) 2015 dmulloy2 5 | * 6 | * PacketWrapper is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU Lesser General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * PacketWrapper is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public License 17 | * along with PacketWrapper. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | import com.comphenix.protocol.events.PacketEvent; 24 | import com.comphenix.protocol.wrappers.WrappedWatchableObject; 25 | import org.bukkit.World; 26 | import org.bukkit.entity.Entity; 27 | 28 | import java.util.List; 29 | 30 | public class WrapperPlayServerEntityMetadata extends AbstractPacket { 31 | public static final PacketType TYPE = PacketType.Play.Server.ENTITY_METADATA; 32 | 33 | public WrapperPlayServerEntityMetadata() { 34 | super(new PacketContainer(TYPE), TYPE); 35 | handle.getModifier().writeDefaults(); 36 | } 37 | 38 | public WrapperPlayServerEntityMetadata(PacketContainer packet) { 39 | super(packet, TYPE); 40 | } 41 | 42 | /** 43 | * Retrieve Entity ID. 44 | *

45 | * Notes: entity's ID 46 | * @return The current Entity ID 47 | */ 48 | public int getEntityID() { 49 | return handle.getIntegers().read(0); 50 | } 51 | 52 | /** 53 | * Set Entity ID. 54 | * @param value - new value. 55 | */ 56 | public void setEntityID(int value) { 57 | handle.getIntegers().write(0, value); 58 | } 59 | 60 | /** 61 | * Retrieve the entity of the painting that will be spawned. 62 | * @param world - the current world of the entity. 63 | * @return The spawned entity. 64 | */ 65 | public Entity getEntity(World world) { 66 | return handle.getEntityModifier(world).read(0); 67 | } 68 | 69 | /** 70 | * Retrieve the entity of the painting that will be spawned. 71 | * @param event - the packet event. 72 | * @return The spawned entity. 73 | */ 74 | public Entity getEntity(PacketEvent event) { 75 | return getEntity(event.getPlayer().getWorld()); 76 | } 77 | 78 | /** 79 | * Retrieve Metadata. 80 | * @return The current Metadata 81 | */ 82 | public List getMetadata() { 83 | return handle.getWatchableCollectionModifier().read(0); 84 | } 85 | 86 | /** 87 | * Set Metadata. 88 | * @param value - new value. 89 | */ 90 | public void setMetadata(List value) { 91 | handle.getWatchableCollectionModifier().write(0, value); 92 | } 93 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerEntityStatus.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import org.bukkit.World; 22 | import org.bukkit.entity.Entity; 23 | 24 | import com.comphenix.protocol.PacketType; 25 | import com.comphenix.protocol.events.PacketContainer; 26 | import com.comphenix.protocol.events.PacketEvent; 27 | 28 | public class WrapperPlayServerEntityStatus extends AbstractPacket { 29 | public static final PacketType TYPE = PacketType.Play.Server.ENTITY_STATUS; 30 | 31 | public WrapperPlayServerEntityStatus() { 32 | super(new PacketContainer(TYPE), TYPE); 33 | handle.getModifier().writeDefaults(); 34 | } 35 | 36 | public WrapperPlayServerEntityStatus(PacketContainer packet) { 37 | super(packet, TYPE); 38 | } 39 | 40 | /** 41 | * Retrieve Entity ID. 42 | *

43 | * Notes: entity's ID 44 | * 45 | * @return The current Entity ID 46 | */ 47 | public int getEntityID() { 48 | return handle.getIntegers().read(0); 49 | } 50 | 51 | /** 52 | * Set Entity ID. 53 | * 54 | * @param value - new value. 55 | */ 56 | public void setEntityID(int value) { 57 | handle.getIntegers().write(0, value); 58 | } 59 | 60 | /** 61 | * Retrieve the entity of the painting that will be spawned. 62 | * 63 | * @param world - the current world of the entity. 64 | * @return The spawned entity. 65 | */ 66 | public Entity getEntity(World world) { 67 | return handle.getEntityModifier(world).read(0); 68 | } 69 | 70 | /** 71 | * Retrieve the entity of the painting that will be spawned. 72 | * 73 | * @param event - the packet event. 74 | * @return The spawned entity. 75 | */ 76 | public Entity getEntity(PacketEvent event) { 77 | return getEntity(event.getPlayer().getWorld()); 78 | } 79 | 80 | /** 81 | * Retrieve Entity Status. 82 | *

83 | * Notes: see below 84 | * 85 | * @return The current Entity Status 86 | */ 87 | public byte getEntityStatus() { 88 | return handle.getBytes().read(0); 89 | } 90 | 91 | /** 92 | * Set Entity Status. 93 | * 94 | * @param value - new value. 95 | */ 96 | public void setEntityStatus(byte value) { 97 | handle.getBytes().write(0, value); 98 | } 99 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerGameStateChange.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | 24 | public class WrapperPlayServerGameStateChange extends AbstractPacket { 25 | public static final PacketType TYPE = 26 | PacketType.Play.Server.GAME_STATE_CHANGE; 27 | 28 | public WrapperPlayServerGameStateChange() { 29 | super(new PacketContainer(TYPE), TYPE); 30 | handle.getModifier().writeDefaults(); 31 | } 32 | 33 | public WrapperPlayServerGameStateChange(PacketContainer packet) { 34 | super(packet, TYPE); 35 | } 36 | 37 | /** 38 | * Retrieve Reason. 39 | * 40 | * @return The current Reason 41 | */ 42 | public int getReason() { 43 | return handle.getIntegers().read(0); 44 | } 45 | 46 | /** 47 | * Set Reason. 48 | * 49 | * @param value - new value. 50 | */ 51 | public void setReason(int value) { 52 | handle.getIntegers().write(0, value); 53 | } 54 | 55 | /** 56 | * Retrieve Value. 57 | *

58 | * Notes: depends on reason 59 | * 60 | * @return The current Value 61 | */ 62 | public float getValue() { 63 | return handle.getFloat().read(0); 64 | } 65 | 66 | /** 67 | * Set Value. 68 | * 69 | * @param value - new value. 70 | */ 71 | public void setValue(float value) { 72 | handle.getFloat().write(0, value); 73 | } 74 | 75 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerKeepAlive.java: -------------------------------------------------------------------------------- 1 | /** 2 | * This file is part of PacketWrapper. 3 | * Copyright (C) 2012-2015 Kristian S. Strangeland 4 | * Copyright (C) 2015 dmulloy2 5 | * 6 | * PacketWrapper is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU Lesser General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * PacketWrapper is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public License 17 | * along with PacketWrapper. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | 24 | public class WrapperPlayServerKeepAlive extends AbstractPacket { 25 | public static final PacketType TYPE = PacketType.Play.Server.KEEP_ALIVE; 26 | 27 | public WrapperPlayServerKeepAlive() { 28 | super(new PacketContainer(TYPE), TYPE); 29 | handle.getModifier().writeDefaults(); 30 | } 31 | 32 | public WrapperPlayServerKeepAlive(PacketContainer packet) { 33 | super(packet, TYPE); 34 | } 35 | 36 | /** 37 | * Retrieve Keep Alive ID. 38 | * @return The current Keep Alive ID 39 | */ 40 | public int getKeepAliveId() { 41 | return handle.getIntegers().read(0); 42 | } 43 | 44 | /** 45 | * Set Keep Alive ID. 46 | * @param value - new value. 47 | */ 48 | public void setKeepAliveId(int value) { 49 | handle.getIntegers().write(0, value); 50 | } 51 | 52 | } 53 | -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerPlayerInfo.java: -------------------------------------------------------------------------------- 1 | /** 2 | * This file is part of PacketWrapper. 3 | * Copyright (C) 2012-2015 Kristian S. Strangeland 4 | * Copyright (C) 2015 dmulloy2 5 | * 6 | * PacketWrapper is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU Lesser General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * PacketWrapper is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public License 17 | * along with PacketWrapper. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | import com.comphenix.protocol.wrappers.EnumWrappers; 24 | import com.comphenix.protocol.wrappers.EnumWrappers.PlayerInfoAction; 25 | import com.comphenix.protocol.wrappers.PlayerInfoData; 26 | import com.google.common.collect.Sets; 27 | import me.jumper251.replay.utils.VersionUtil; 28 | 29 | import java.util.List; 30 | import java.util.Set; 31 | 32 | public class WrapperPlayServerPlayerInfo extends AbstractPacket { 33 | public static final PacketType TYPE = PacketType.Play.Server.PLAYER_INFO; 34 | 35 | public WrapperPlayServerPlayerInfo() { 36 | super(new PacketContainer(TYPE), TYPE); 37 | handle.getModifier().writeDefaults(); 38 | } 39 | 40 | public WrapperPlayServerPlayerInfo(PacketContainer packet) { 41 | super(packet, TYPE); 42 | } 43 | 44 | public PlayerInfoAction getAction() { 45 | return handle.getPlayerInfoAction().read(0); 46 | } 47 | 48 | public void setAction(PlayerInfoAction value) { 49 | if (VersionUtil.isAbove(VersionUtil.VersionEnum.V1_19)) { 50 | Set types = Sets.newHashSet(value); 51 | handle.getPlayerInfoActions().write(0, types); 52 | } else { 53 | handle.getPlayerInfoAction().write(0, value); 54 | } 55 | } 56 | 57 | public List getData() { 58 | return handle.getPlayerInfoDataLists().read(0); 59 | } 60 | 61 | public void setData(List value) { 62 | if (VersionUtil.isAbove(VersionUtil.VersionEnum.V1_19)) { 63 | handle.getPlayerInfoDataLists().write(1, value); 64 | } else { 65 | handle.getPlayerInfoDataLists().write(0, value); 66 | } 67 | } 68 | } 69 | -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerRelEntityMove.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import org.bukkit.World; 22 | import org.bukkit.entity.Entity; 23 | 24 | import com.comphenix.protocol.PacketType; 25 | import com.comphenix.protocol.events.PacketContainer; 26 | import com.comphenix.protocol.events.PacketEvent; 27 | 28 | public class WrapperPlayServerRelEntityMove extends AbstractPacket { 29 | public static final PacketType TYPE = 30 | PacketType.Play.Server.REL_ENTITY_MOVE; 31 | 32 | public WrapperPlayServerRelEntityMove() { 33 | super(new PacketContainer(TYPE), TYPE); 34 | handle.getModifier().writeDefaults(); 35 | } 36 | 37 | public WrapperPlayServerRelEntityMove(PacketContainer packet) { 38 | super(packet, TYPE); 39 | } 40 | 41 | /** 42 | * Retrieve Entity ID. 43 | *

44 | * Notes: entity's ID 45 | * 46 | * @return The current Entity ID 47 | */ 48 | public int getEntityID() { 49 | return handle.getIntegers().read(0); 50 | } 51 | 52 | /** 53 | * Set Entity ID. 54 | * 55 | * @param value - new value. 56 | */ 57 | public void setEntityID(int value) { 58 | handle.getIntegers().write(0, value); 59 | } 60 | 61 | /** 62 | * Retrieve the entity of the painting that will be spawned. 63 | * 64 | * @param world - the current world of the entity. 65 | * @return The spawned entity. 66 | */ 67 | public Entity getEntity(World world) { 68 | return handle.getEntityModifier(world).read(0); 69 | } 70 | 71 | /** 72 | * Retrieve the entity of the painting that will be spawned. 73 | * 74 | * @param event - the packet event. 75 | * @return The spawned entity. 76 | */ 77 | public Entity getEntity(PacketEvent event) { 78 | return getEntity(event.getPlayer().getWorld()); 79 | } 80 | 81 | public int getDx() { 82 | return handle.getIntegers().read(1); 83 | } 84 | 85 | public void setDx(int value) { 86 | handle.getIntegers().write(1, value); 87 | } 88 | 89 | public int getDy() { 90 | return handle.getIntegers().read(2); 91 | } 92 | 93 | public void setDy(int value) { 94 | handle.getIntegers().write(2, value); 95 | } 96 | 97 | public int getDz() { 98 | return handle.getIntegers().read(3); 99 | } 100 | 101 | public void setDz(int value) { 102 | handle.getIntegers().write(3, value); 103 | } 104 | 105 | /** 106 | * Retrieve On Ground. 107 | * 108 | * @return The current On Ground 109 | */ 110 | public boolean getOnGround() { 111 | return handle.getBooleans().read(0); 112 | } 113 | 114 | /** 115 | * Set On Ground. 116 | * 117 | * @param value - new value. 118 | */ 119 | public void setOnGround(boolean value) { 120 | handle.getBooleans().write(0, value); 121 | } 122 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerTitle.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | import com.comphenix.protocol.wrappers.EnumWrappers.TitleAction; 24 | import com.comphenix.protocol.wrappers.WrappedChatComponent; 25 | 26 | public class WrapperPlayServerTitle extends AbstractPacket { 27 | public static final PacketType TYPE = PacketType.Play.Server.TITLE; 28 | 29 | public WrapperPlayServerTitle() { 30 | super(new PacketContainer(TYPE), TYPE); 31 | handle.getModifier().writeDefaults(); 32 | } 33 | 34 | public WrapperPlayServerTitle(PacketContainer packet) { 35 | super(packet, TYPE); 36 | } 37 | 38 | /** 39 | * Retrieve Action. 40 | * 41 | * @return The current Action 42 | */ 43 | public TitleAction getAction() { 44 | return handle.getTitleActions().read(0); 45 | } 46 | 47 | /** 48 | * Set Action. 49 | * 50 | * @param value - new value. 51 | */ 52 | public void setAction(TitleAction value) { 53 | handle.getTitleActions().write(0, value); 54 | } 55 | 56 | /** 57 | * Retrieve 0 (TITLE). 58 | *

59 | * Notes: chat 60 | * 61 | * @return The current 0 (TITLE) 62 | */ 63 | public WrappedChatComponent getTitle() { 64 | return handle.getChatComponents().read(0); 65 | } 66 | 67 | /** 68 | * Set 0 (TITLE). 69 | * 70 | * @param value - new value. 71 | */ 72 | public void setTitle(WrappedChatComponent value) { 73 | handle.getChatComponents().write(0, value); 74 | } 75 | 76 | /** 77 | * Retrieve 2 (TIMES). 78 | *

79 | * Notes: int 80 | * 81 | * @return The current 2 (TIMES) 82 | */ 83 | public int getFadeIn() { 84 | return handle.getIntegers().read(0); 85 | } 86 | 87 | /** 88 | * Set 2 (TIMES). 89 | * 90 | * @param value - new value. 91 | */ 92 | public void setFadeIn(int value) { 93 | handle.getIntegers().write(0, value); 94 | } 95 | 96 | /** 97 | * Retrieve Stay. 98 | * 99 | * @return The current Stay 100 | */ 101 | public int getStay() { 102 | return handle.getIntegers().read(1); 103 | } 104 | 105 | /** 106 | * Set Stay. 107 | * 108 | * @param value - new value. 109 | */ 110 | public void setStay(int value) { 111 | handle.getIntegers().write(1, value); 112 | } 113 | 114 | /** 115 | * Retrieve Fade Out. 116 | * 117 | * @return The current Fade Out 118 | */ 119 | public int getFadeOut() { 120 | return handle.getIntegers().read(2); 121 | } 122 | 123 | /** 124 | * Set Fade Out. 125 | * 126 | * @param value - new value. 127 | */ 128 | public void setFadeOut(int value) { 129 | handle.getIntegers().write(2, value); 130 | } 131 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperPlayServerUpdateHealth.java: -------------------------------------------------------------------------------- 1 | /** 2 | * This file is part of PacketWrapper. 3 | * Copyright (C) 2012-2015 Kristian S. Strangeland 4 | * Copyright (C) 2015 dmulloy2 5 | * 6 | * PacketWrapper is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU Lesser General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * PacketWrapper is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public License 17 | * along with PacketWrapper. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | 24 | public class WrapperPlayServerUpdateHealth extends AbstractPacket { 25 | public static final PacketType TYPE = PacketType.Play.Server.UPDATE_HEALTH; 26 | 27 | public WrapperPlayServerUpdateHealth() { 28 | super(new PacketContainer(TYPE), TYPE); 29 | handle.getModifier().writeDefaults(); 30 | } 31 | 32 | public WrapperPlayServerUpdateHealth(PacketContainer packet) { 33 | super(packet, TYPE); 34 | } 35 | 36 | /** 37 | * Retrieve Health. 38 | *

39 | * Notes: 0 or less = dead, 20 = full HP 40 | * @return The current Health 41 | */ 42 | public float getHealth() { 43 | return handle.getFloat().read(0); 44 | } 45 | 46 | /** 47 | * Set Health. 48 | * @param value - new value. 49 | */ 50 | public void setHealth(float value) { 51 | handle.getFloat().write(0, value); 52 | } 53 | 54 | /** 55 | * Retrieve Food. 56 | *

57 | * Notes: 0 - 20 58 | * @return The current Food 59 | */ 60 | public int getFood() { 61 | return handle.getIntegers().read(0); 62 | } 63 | 64 | /** 65 | * Set Food. 66 | * @param value - new value. 67 | */ 68 | public void setFood(int value) { 69 | handle.getIntegers().write(0, value); 70 | } 71 | 72 | /** 73 | * Retrieve Food Saturation. 74 | *

75 | * Notes: seems to vary from 0.0 to 5.0 in integer increments 76 | * @return The current Food Saturation 77 | */ 78 | public float getFoodSaturation() { 79 | return handle.getFloat().read(1); 80 | } 81 | 82 | /** 83 | * Set Food Saturation. 84 | * @param value - new value. 85 | */ 86 | public void setFoodSaturation(float value) { 87 | handle.getFloat().write(1, value); 88 | } 89 | 90 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/WrapperStatusClientPing.java: -------------------------------------------------------------------------------- 1 | /** 2 | * This file is part of PacketWrapper. 3 | * Copyright (C) 2012-2015 Kristian S. Strangeland 4 | * Copyright (C) 2015 dmulloy2 5 | * 6 | * PacketWrapper is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU Lesser General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * PacketWrapper is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public License 17 | * along with PacketWrapper. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper; 20 | 21 | import com.comphenix.protocol.PacketType; 22 | import com.comphenix.protocol.events.PacketContainer; 23 | 24 | public class WrapperStatusClientPing extends AbstractPacket { 25 | public static final PacketType TYPE = PacketType.Status.Client.PING; 26 | 27 | public WrapperStatusClientPing() { 28 | super(new PacketContainer(TYPE), TYPE); 29 | handle.getModifier().writeDefaults(); 30 | } 31 | 32 | public WrapperStatusClientPing(PacketContainer packet) { 33 | super(packet, TYPE); 34 | } 35 | 36 | /** 37 | * Retrieve Time. 38 | * @return The current Time 39 | */ 40 | public long getTime() { 41 | return handle.getLongs().read(0); 42 | } 43 | 44 | /** 45 | * Set Time. 46 | * @param value - new value. 47 | */ 48 | public void setTime(long value) { 49 | handle.getLongs().write(0, value); 50 | } 51 | 52 | } 53 | -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/old/WrapperPlayServerEntityHeadRotation.java: -------------------------------------------------------------------------------- 1 | /** 2 | * This file is part of PacketWrapper. 3 | * Copyright (C) 2012-2015 Kristian S. Strangeland 4 | * Copyright (C) 2015 dmulloy2 5 | * 6 | * PacketWrapper is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU Lesser General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * PacketWrapper is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public License 17 | * along with PacketWrapper. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper.old; 20 | 21 | import org.bukkit.World; 22 | import org.bukkit.entity.Entity; 23 | 24 | import com.comphenix.packetwrapper.AbstractPacket; 25 | import com.comphenix.protocol.PacketType; 26 | import com.comphenix.protocol.events.PacketContainer; 27 | import com.comphenix.protocol.events.PacketEvent; 28 | 29 | public class WrapperPlayServerEntityHeadRotation extends AbstractPacket { 30 | public static final PacketType TYPE = PacketType.Play.Server.ENTITY_HEAD_ROTATION; 31 | 32 | public WrapperPlayServerEntityHeadRotation() { 33 | super(new PacketContainer(TYPE), TYPE); 34 | handle.getModifier().writeDefaults(); 35 | } 36 | 37 | public WrapperPlayServerEntityHeadRotation(PacketContainer packet) { 38 | super(packet, TYPE); 39 | } 40 | 41 | /** 42 | * Retrieve Entity ID. 43 | *

44 | * Notes: entity's ID 45 | * @return The current Entity ID 46 | */ 47 | public int getEntityID() { 48 | return handle.getIntegers().read(0); 49 | } 50 | 51 | /** 52 | * Set Entity ID. 53 | * @param value - new value. 54 | */ 55 | public void setEntityID(int value) { 56 | handle.getIntegers().write(0, value); 57 | } 58 | 59 | /** 60 | * Retrieve the entity of the painting that will be spawned. 61 | * @param world - the current world of the entity. 62 | * @return The spawned entity. 63 | */ 64 | public Entity getEntity(World world) { 65 | return handle.getEntityModifier(world).read(0); 66 | } 67 | 68 | /** 69 | * Retrieve the entity of the painting that will be spawned. 70 | * @param event - the packet event. 71 | * @return The spawned entity. 72 | */ 73 | public Entity getEntity(PacketEvent event) { 74 | return getEntity(event.getPlayer().getWorld()); 75 | } 76 | 77 | /** 78 | * Retrieve Head Yaw. 79 | *

80 | * Notes: head yaw in steps of 2p/256 81 | * @return The current Head Yaw 82 | */ 83 | public byte getHeadYaw() { 84 | return handle.getBytes().read(0); 85 | } 86 | 87 | /** 88 | * Set Head Yaw. 89 | * @param value - new value. 90 | */ 91 | public void setHeadYaw(byte value) { 92 | handle.getBytes().write(0, value); 93 | } 94 | } -------------------------------------------------------------------------------- /src/main/java/com/comphenix/packetwrapper/v15/WrapperPlayServerRelEntityMove.java: -------------------------------------------------------------------------------- 1 | /** 2 | * PacketWrapper - ProtocolLib wrappers for Minecraft packets 3 | * Copyright (C) dmulloy2 4 | * Copyright (C) Kristian S. Strangeland 5 | * 6 | * This program is free software: you can redistribute it and/or modify 7 | * it under the terms of the GNU General Public License as published by 8 | * the Free Software Foundation, either version 3 of the License, or 9 | * (at your option) any later version. 10 | * 11 | * This program is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | * GNU General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU General Public License 17 | * along with this program. If not, see . 18 | */ 19 | package com.comphenix.packetwrapper.v15; 20 | 21 | import org.bukkit.World; 22 | import org.bukkit.entity.Entity; 23 | 24 | import com.comphenix.packetwrapper.AbstractPacket; 25 | import com.comphenix.protocol.PacketType; 26 | import com.comphenix.protocol.events.PacketContainer; 27 | import com.comphenix.protocol.events.PacketEvent; 28 | 29 | public class WrapperPlayServerRelEntityMove extends AbstractPacket { 30 | public static final PacketType TYPE = 31 | PacketType.Play.Server.REL_ENTITY_MOVE; 32 | 33 | public WrapperPlayServerRelEntityMove() { 34 | super(new PacketContainer(TYPE), TYPE); 35 | handle.getModifier().writeDefaults(); 36 | } 37 | 38 | public WrapperPlayServerRelEntityMove(PacketContainer packet) { 39 | super(packet, TYPE); 40 | } 41 | 42 | /** 43 | * Retrieve Entity ID. 44 | *

45 | * Notes: entity's ID 46 | * 47 | * @return The current Entity ID 48 | */ 49 | public int getEntityID() { 50 | return handle.getIntegers().read(0); 51 | } 52 | 53 | /** 54 | * Set Entity ID. 55 | * 56 | * @param value - new value. 57 | */ 58 | public void setEntityID(int value) { 59 | handle.getIntegers().write(0, value); 60 | } 61 | 62 | /** 63 | * Retrieve the entity of the painting that will be spawned. 64 | * 65 | * @param world - the current world of the entity. 66 | * @return The spawned entity. 67 | */ 68 | public Entity getEntity(World world) { 69 | return handle.getEntityModifier(world).read(0); 70 | } 71 | 72 | /** 73 | * Retrieve the entity of the painting that will be spawned. 74 | * 75 | * @param event - the packet event. 76 | * @return The spawned entity. 77 | */ 78 | public Entity getEntity(PacketEvent event) { 79 | return getEntity(event.getPlayer().getWorld()); 80 | } 81 | 82 | public short getDx() { 83 | return handle.getShorts().read(0); 84 | } 85 | 86 | public void setDx(short value) { 87 | handle.getShorts().write(0, value); 88 | } 89 | 90 | public short getDy() { 91 | return handle.getShorts().read(1); 92 | } 93 | 94 | public void setDy(short value) { 95 | handle.getShorts().write(1, value); 96 | } 97 | 98 | public short getDz() { 99 | return handle.getShorts().read(2); 100 | } 101 | 102 | public void setDz(short value) { 103 | handle.getShorts().write(2, value); 104 | } 105 | 106 | /** 107 | * Retrieve On Ground. 108 | * 109 | * @return The current On Ground 110 | */ 111 | public boolean getOnGround() { 112 | return handle.getBooleans().read(0); 113 | } 114 | 115 | /** 116 | * Set On Ground. 117 | * 118 | * @param value - new value. 119 | */ 120 | public void setOnGround(boolean value) { 121 | handle.getBooleans().write(0, value); 122 | } 123 | } -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/ReplaySystem.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay; 2 | 3 | 4 | import java.util.HashMap; 5 | 6 | 7 | import com.alessiodp.libby.BukkitLibraryManager; 8 | import com.alessiodp.libby.Library; 9 | import me.jumper251.replay.filesystem.saving.S3ReplaySaver; 10 | import org.bukkit.plugin.java.JavaPlugin; 11 | 12 | import me.jumper251.replay.database.DatabaseRegistry; 13 | import me.jumper251.replay.filesystem.ConfigManager; 14 | import me.jumper251.replay.filesystem.saving.DatabaseReplaySaver; 15 | import me.jumper251.replay.filesystem.saving.DefaultReplaySaver; 16 | import me.jumper251.replay.filesystem.saving.ReplaySaver; 17 | import me.jumper251.replay.replaysystem.Replay; 18 | import me.jumper251.replay.replaysystem.utils.ReplayCleanup; 19 | import me.jumper251.replay.utils.Metrics; 20 | import me.jumper251.replay.utils.ReplayManager; 21 | import me.jumper251.replay.utils.Updater; 22 | 23 | 24 | public class ReplaySystem extends JavaPlugin { 25 | 26 | 27 | public static ReplaySystem instance; 28 | 29 | public static Updater updater; 30 | public static Metrics metrics; 31 | 32 | public final static String PREFIX = "§8[§3Replay§8] §r§7"; 33 | 34 | 35 | @Override 36 | public void onDisable() { 37 | for (Replay replay : new HashMap<>(ReplayManager.activeReplays).values()) { 38 | if (replay.isRecording() && replay.getRecorder().getData().getActions().size() > 0) { 39 | replay.getRecorder().stop(ConfigManager.SAVE_STOP); 40 | 41 | } 42 | } 43 | 44 | } 45 | 46 | @Override 47 | public void onEnable() { 48 | instance = this; 49 | 50 | Long start = System.currentTimeMillis(); 51 | 52 | BukkitLibraryManager libraryManager = new BukkitLibraryManager(this); 53 | libraryManager.addMavenCentral(); 54 | 55 | getLogger().info("Loading Replay v" + getDescription().getVersion() + " by " + getDescription().getAuthors().get(0)); 56 | 57 | ConfigManager.loadConfigs(); 58 | ReplayManager.register(); 59 | 60 | if (ConfigManager.USE_DATABASE) { 61 | ReplaySaver.register(new DatabaseReplaySaver()); 62 | DatabaseRegistry.getDatabase().getService().getReplays().stream() 63 | .forEach(info -> DatabaseReplaySaver.replayCache.put(info.getID(), info)); 64 | } else if (ConfigManager.USE_S3) { 65 | Library minioLibrary = Library.builder() 66 | .groupId("io{}minio") 67 | .artifactId("minio") 68 | .version("8.5.12") 69 | .resolveTransitiveDependencies(true) 70 | .build(); 71 | libraryManager.loadLibrary(minioLibrary); 72 | S3ReplaySaver s3ReplaySaver = new S3ReplaySaver( 73 | ConfigManager.s3Cfg.getString("endpoint_url"), 74 | ConfigManager.s3Cfg.getString("access_key"), 75 | ConfigManager.s3Cfg.getString("secret_key"), 76 | ConfigManager.s3Cfg.getString("bucket_name") 77 | ); 78 | 79 | s3ReplaySaver.connect().thenAccept(isConnected -> { 80 | if (!isConnected) 81 | getLogger().warning("Could not connect to S3 storage backend."); 82 | }); 83 | 84 | ReplaySaver.register(s3ReplaySaver); 85 | } else { 86 | ReplaySaver.register(new DefaultReplaySaver()); 87 | } 88 | 89 | updater = new Updater(); 90 | metrics = new Metrics(this, 2188); 91 | 92 | if (ConfigManager.CLEANUP_REPLAYS > 0) { 93 | ReplayCleanup.cleanupReplays(); 94 | } 95 | 96 | getLogger().info("Finished (" + (System.currentTimeMillis() - start) + "ms)"); 97 | 98 | } 99 | 100 | 101 | public static ReplaySystem getInstance() { 102 | return instance; 103 | } 104 | } 105 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/api/HookManager.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.api; 2 | 3 | import java.util.ArrayList; 4 | import java.util.List; 5 | 6 | public class HookManager { 7 | 8 | private List hooks = new ArrayList(); 9 | 10 | 11 | public void registerHook(IReplayHook hook) { 12 | if (!this.hooks.contains(hook)) { 13 | this.hooks.add(hook); 14 | } 15 | } 16 | 17 | public void unregisterHook(IReplayHook hook) { 18 | if (this.hooks.contains(hook)) { 19 | this.hooks.remove(hook); 20 | } 21 | } 22 | 23 | public boolean isRegistered() { 24 | return this.hooks.size() > 0; 25 | } 26 | 27 | public List getHooks() { 28 | return hooks; 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/api/IReplayHook.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.api; 2 | 3 | import java.util.List; 4 | 5 | import me.jumper251.replay.replaysystem.data.ActionData; 6 | import me.jumper251.replay.replaysystem.data.types.PacketData; 7 | import me.jumper251.replay.replaysystem.replaying.Replayer; 8 | 9 | public interface IReplayHook { 10 | 11 | List onRecord(String playerName); 12 | 13 | void onPlay(ActionData data, Replayer replayer); 14 | } 15 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/api/ReplaySessionFinishEvent.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.api; 2 | 3 | import org.bukkit.Bukkit; 4 | import org.bukkit.entity.Player; 5 | import org.bukkit.event.Event; 6 | import org.bukkit.event.HandlerList; 7 | 8 | import me.jumper251.replay.replaysystem.Replay; 9 | 10 | public class ReplaySessionFinishEvent extends Event { 11 | 12 | private static final HandlerList HANDLERS = new HandlerList(); 13 | 14 | private Replay replay; 15 | 16 | private Player player; 17 | 18 | public ReplaySessionFinishEvent(Replay replay, Player player) { 19 | super(!Bukkit.isPrimaryThread()); 20 | 21 | this.replay = replay; 22 | this.player = player; 23 | } 24 | 25 | 26 | public Player getPlayer() { 27 | return player; 28 | } 29 | 30 | public Replay getReplay() { 31 | return replay; 32 | } 33 | 34 | @Override 35 | public HandlerList getHandlers() { 36 | return HANDLERS; 37 | } 38 | 39 | public static HandlerList getHandlerList() { 40 | return HANDLERS; 41 | } 42 | 43 | } 44 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/commands/CommandPagination.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.commands; 2 | 3 | import java.util.ArrayList; 4 | import java.util.List; 5 | 6 | public class CommandPagination { 7 | 8 | private List content; 9 | 10 | private int elementsPerPage; 11 | 12 | public CommandPagination(List content, int elementsPerPage) { 13 | this.content = content; 14 | this.elementsPerPage = elementsPerPage; 15 | } 16 | 17 | 18 | public void printPage(int page, IPaginationExecutor executor) { 19 | for (T element : getElementsFor(page)) { 20 | executor.print(element); 21 | } 22 | } 23 | 24 | public List getElementsFor(int page) { 25 | if (page <= 0 || page > getPages()) return new ArrayList(); 26 | 27 | int startIndex = (page - 1) * this.elementsPerPage; 28 | int endIndex = page * this.elementsPerPage; 29 | 30 | return this.content.subList(startIndex, endIndex <= this.content.size() ? endIndex : this.content.size()); 31 | } 32 | 33 | public int getPages() { 34 | return (int) Math.ceil((content.size() / (double) elementsPerPage)); 35 | } 36 | 37 | public void addElement(T element) { 38 | if (!this.content.contains(element)) this.content.add(element); 39 | } 40 | 41 | public int getElementsPerPage() { 42 | return elementsPerPage; 43 | } 44 | 45 | 46 | } 47 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/commands/IPaginationExecutor.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.commands; 2 | 3 | public interface IPaginationExecutor { 4 | 5 | void print(T element); 6 | } 7 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/commands/MessageFormat.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.commands; 2 | 3 | import me.jumper251.replay.filesystem.MessageBuilder; 4 | 5 | public class MessageFormat { 6 | 7 | private String syntaxMessage, overviewMessage, permissionMessage, consoleMessage, notFoundMessage; 8 | 9 | 10 | public MessageFormat syntax(String syntaxMessage) { 11 | this.syntaxMessage = syntaxMessage; 12 | return this; 13 | } 14 | 15 | public MessageFormat overview(String overviewMessage) { 16 | this.overviewMessage = overviewMessage; 17 | return this; 18 | } 19 | 20 | public MessageFormat permission(String permissionMessage) { 21 | this.permissionMessage = permissionMessage; 22 | return this; 23 | } 24 | 25 | public MessageFormat console(String consoleMessage) { 26 | this.consoleMessage = consoleMessage; 27 | return this; 28 | } 29 | 30 | public MessageFormat notFound(String notFoundMessage) { 31 | this.notFoundMessage = notFoundMessage; 32 | return this; 33 | } 34 | 35 | public String getSyntaxMessage(String command, String arg) { 36 | return new MessageBuilder(this.syntaxMessage). 37 | set("command", command) 38 | .set("args", arg) 39 | .build(); 40 | } 41 | 42 | public String getOverviewMessage(String command, String arg, String desc) { 43 | return new MessageBuilder(this.overviewMessage). 44 | set("command", command) 45 | .set("args", arg) 46 | .set("desc", desc) 47 | .build(); 48 | } 49 | 50 | public String getConsoleMessage() { 51 | return consoleMessage != null ? consoleMessage : "You must be a player to execute this command."; 52 | } 53 | 54 | public String getPermissionMessage() { 55 | return this.permissionMessage; 56 | } 57 | 58 | public String getNotFoundMessage() { 59 | return notFoundMessage; 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/commands/SubCommand.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.commands; 2 | 3 | import java.util.ArrayList; 4 | import java.util.List; 5 | 6 | import org.bukkit.command.Command; 7 | import org.bukkit.command.CommandSender; 8 | 9 | public abstract class SubCommand { 10 | 11 | private AbstractCommand parent; 12 | private String label, description, args; 13 | private boolean playerOnly, enabled = true; 14 | private List aliases; 15 | 16 | public SubCommand(AbstractCommand parent, String label, String description, String args, boolean playerOnly) { 17 | this.parent = parent; 18 | this.label = label; 19 | this.description = description; 20 | this.args = args; 21 | this.playerOnly = playerOnly; 22 | this.aliases = new ArrayList(); 23 | 24 | } 25 | 26 | public abstract boolean execute(CommandSender cs, Command cmd, String label, String[] args); 27 | 28 | public List onTab(CommandSender cs, Command cmd, String label, String[] args) { 29 | return null; 30 | } 31 | 32 | public SubCommand addAlias(String alias) { 33 | if (!this.aliases.contains(alias)) this.aliases.add(alias); 34 | 35 | return this; 36 | } 37 | 38 | public String getDescription() { 39 | return description; 40 | } 41 | 42 | public String getLabel() { 43 | return label; 44 | } 45 | 46 | public String getArgs() { 47 | return args; 48 | } 49 | 50 | public boolean isPlayerOnly() { 51 | return playerOnly; 52 | } 53 | 54 | public boolean isEnabled() { 55 | return enabled; 56 | } 57 | 58 | public void setEnabled(boolean enabled) { 59 | this.enabled = enabled; 60 | } 61 | 62 | public List getAliases() { 63 | return aliases; 64 | } 65 | 66 | public AbstractCommand getParent() { 67 | return parent; 68 | } 69 | } 70 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/commands/replay/ReplayCommand.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.commands.replay; 2 | 3 | import me.jumper251.replay.ReplaySystem; 4 | import me.jumper251.replay.commands.AbstractCommand; 5 | import me.jumper251.replay.commands.MessageFormat; 6 | import me.jumper251.replay.commands.SubCommand; 7 | import me.jumper251.replay.filesystem.Messages; 8 | 9 | public class ReplayCommand extends AbstractCommand { 10 | 11 | public ReplayCommand() { 12 | super("Replay", ReplaySystem.PREFIX + "AdvancedReplay §ev" + ReplaySystem.getInstance().getDescription().getVersion(), "replay.command"); 13 | } 14 | 15 | @Override 16 | protected MessageFormat setupFormat() { 17 | return new MessageFormat() 18 | .overview(Messages.COMMAND_OVERVIEW.getFullMessage()) 19 | .syntax(Messages.COMMAND_SYNTAX.getFullMessage()) 20 | .permission(Messages.COMMAND_NO_PERMISSION.getFullMessage()) 21 | .notFound(Messages.COMMAND_NOTFOUND.getFullMessage()); 22 | } 23 | 24 | @Override 25 | protected SubCommand[] setupCommands() { 26 | 27 | return new SubCommand[] { new ReplayStartCommand(this), 28 | new ReplayStopCommand(this).addAlias("save"), 29 | new ReplayPlayCommand(this), 30 | new ReplayDeleteCommand(this).addAlias("remove"), 31 | new ReplayJumpCommand(this), 32 | new ReplayLeaveCommand(this), 33 | new ReplayInfoCommand(this), 34 | new ReplayListCommand(this), 35 | new ReplayReloadCommand(this), 36 | new ReplayReformatCommand(this), 37 | new ReplayMigrateCommand(this) }; 38 | } 39 | 40 | } 41 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/commands/replay/ReplayDeleteCommand.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.commands.replay; 2 | 3 | 4 | import java.util.List; 5 | import java.util.stream.Collectors; 6 | 7 | import me.jumper251.replay.filesystem.Messages; 8 | import org.bukkit.command.Command; 9 | import org.bukkit.command.CommandSender; 10 | import org.bukkit.util.StringUtil; 11 | 12 | import me.jumper251.replay.ReplaySystem; 13 | import me.jumper251.replay.commands.AbstractCommand; 14 | import me.jumper251.replay.commands.SubCommand; 15 | import me.jumper251.replay.filesystem.saving.ReplaySaver; 16 | 17 | public class ReplayDeleteCommand extends SubCommand { 18 | 19 | public ReplayDeleteCommand(AbstractCommand parent) { 20 | super(parent, "delete", "Deletes a replay", "delete ", false); 21 | } 22 | 23 | @Override 24 | public boolean execute(CommandSender cs, Command cmd, String label, String[] args) { 25 | if (args.length != 2) return false; 26 | 27 | String name = args[1]; 28 | 29 | if (ReplaySaver.exists(name)) { 30 | ReplaySaver.delete(name); 31 | Messages.REPLAY_DELETE.send(cs); 32 | } else { 33 | Messages.REPLAY_NOT_FOUND.send(cs); 34 | } 35 | 36 | return true; 37 | } 38 | 39 | @Override 40 | public List onTab(CommandSender cs, Command cmd, String label, String[] args) { 41 | return ReplaySaver.getReplays().stream() 42 | .filter(name -> StringUtil.startsWithIgnoreCase(name, args.length > 1 ? args[1] : null)) 43 | .collect(Collectors.toList()); 44 | } 45 | 46 | 47 | } 48 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/commands/replay/ReplayJumpCommand.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.commands.replay; 2 | 3 | 4 | 5 | 6 | import me.jumper251.replay.filesystem.Messages; 7 | import org.bukkit.command.Command; 8 | import org.bukkit.command.CommandSender; 9 | import org.bukkit.entity.Player; 10 | 11 | import me.jumper251.replay.ReplaySystem; 12 | import me.jumper251.replay.api.ReplayAPI; 13 | import me.jumper251.replay.commands.AbstractCommand; 14 | import me.jumper251.replay.commands.SubCommand; 15 | import me.jumper251.replay.replaysystem.replaying.ReplayHelper; 16 | import me.jumper251.replay.replaysystem.replaying.Replayer; 17 | import me.jumper251.replay.utils.MathUtils; 18 | 19 | public class ReplayJumpCommand extends SubCommand { 20 | 21 | public ReplayJumpCommand(AbstractCommand parent) { 22 | super(parent, "jump", "Jump to a specific moment", "jump

53 | * In case of an explosion the block change is already sent by the explosion packet. 54 | * If ConfigManager.REAL_CHANGES is true, this value is ignored for the block change, 55 | * but continues to be used for playing the Fuse sound. 56 | */ 57 | public boolean doBlockChange() { 58 | return doBlockChange; 59 | } 60 | 61 | public void setDoBlockChange(boolean doBlockChange) { 62 | this.doBlockChange = doBlockChange; 63 | } 64 | 65 | public boolean isBlockBreak() { 66 | Material before = getBefore().toMaterial(); 67 | Material after = getAfter().toMaterial(); 68 | 69 | return before != Material.AIR && after == Material.AIR && before.isBlock() && before != Material.FIRE && (VersionUtil.isAbove(VersionUtil.VersionEnum.V1_13) || before.isSolid()); 70 | } 71 | } 72 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/BlockPositionData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | import com.comphenix.protocol.wrappers.BlockPosition; 4 | 5 | import java.io.Serializable; 6 | 7 | public class BlockPositionData implements Serializable { 8 | 9 | private static final long serialVersionUID = 1L; 10 | 11 | private final int x; 12 | private final int y; 13 | private final int z; 14 | 15 | public BlockPositionData(int x, int y, int z) { 16 | this.x = x; 17 | this.y = y; 18 | this.z = z; 19 | } 20 | 21 | public int getX() { 22 | return x; 23 | } 24 | 25 | public int getY() { 26 | return y; 27 | } 28 | 29 | public int getZ() { 30 | return z; 31 | } 32 | 33 | public static BlockPositionData fromBlockPosition(BlockPosition blockPosition) { 34 | return new BlockPositionData(blockPosition.getX(), blockPosition.getY(), blockPosition.getZ()); 35 | } 36 | 37 | public BlockPosition toBlockPosition() { 38 | return new BlockPosition(x, y, z); 39 | } 40 | 41 | @Override 42 | public String toString() { 43 | return "BlockPositionData{" + 44 | "x=" + x + 45 | ", y=" + y + 46 | ", z=" + z + 47 | '}'; 48 | } 49 | } -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/ChatData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | public class ChatData extends PacketData { 4 | 5 | 6 | /** 7 | * 8 | */ 9 | private static final long serialVersionUID = 6849586468365004854L; 10 | 11 | private String message; 12 | 13 | public ChatData(String message) { 14 | this.message = message; 15 | } 16 | 17 | public String getMessage() { 18 | return message; 19 | } 20 | } 21 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/EntityActionData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | import com.comphenix.protocol.wrappers.EnumWrappers.PlayerAction; 4 | 5 | public class EntityActionData extends PacketData { 6 | 7 | /** 8 | * 9 | */ 10 | private static final long serialVersionUID = 7841723539864388570L; 11 | 12 | 13 | private PlayerAction action; 14 | 15 | public EntityActionData(PlayerAction action) { 16 | this.action = action; 17 | } 18 | 19 | public PlayerAction getAction() { 20 | return action; 21 | } 22 | 23 | } 24 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/EntityAnimationData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | public class EntityAnimationData extends PacketData { 4 | 5 | 6 | 7 | /** 8 | * 9 | */ 10 | private static final long serialVersionUID = 3334893591520224930L; 11 | 12 | private int entId, id; 13 | 14 | public EntityAnimationData(int entId, int id) { 15 | this.id = id; 16 | this.entId = entId; 17 | } 18 | 19 | public int getId() { 20 | return id; 21 | } 22 | 23 | public int getEntId() { 24 | return entId; 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/EntityData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | public class EntityData extends PacketData { 4 | 5 | /** 6 | * 7 | */ 8 | private static final long serialVersionUID = 2309497657075148314L; 9 | 10 | private int action, id; 11 | 12 | private LocationData location; 13 | 14 | private String type; 15 | 16 | public EntityData(int action, int id, LocationData location, String type) { 17 | this.action = action; 18 | this.id = id; 19 | this.location = location; 20 | this.type = type; 21 | } 22 | 23 | public int getAction() { 24 | return action; 25 | } 26 | 27 | public int getId() { 28 | return id; 29 | } 30 | 31 | public LocationData getLocation() { 32 | return location; 33 | } 34 | 35 | public String getType() { 36 | return type; 37 | } 38 | 39 | public void setType(String type) { 40 | this.type = type; 41 | } 42 | 43 | } 44 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/EntityDestroyData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | public class EntityDestroyData extends PacketData { 4 | 5 | 6 | int id; 7 | 8 | public EntityDestroyData(int id) { 9 | this.id = id; 10 | } 11 | 12 | public int getId() { 13 | return id; 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/EntityItemData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | public class EntityItemData extends PacketData { 4 | 5 | /** 6 | * 7 | */ 8 | private static final long serialVersionUID = 2309497657075148314L; 9 | 10 | 11 | private int action, id; 12 | 13 | private ItemData itemData; 14 | 15 | private LocationData location, velocity; 16 | 17 | public EntityItemData(int action, int id, ItemData itemData, LocationData location, LocationData velocity) { 18 | this.action = action; 19 | this.itemData = itemData; 20 | this.location = location; 21 | this.id = id; 22 | this.velocity = velocity; 23 | } 24 | 25 | 26 | public int getAction() { 27 | return action; 28 | } 29 | 30 | public ItemData getItemData() { 31 | return itemData; 32 | } 33 | 34 | public LocationData getLocation() { 35 | return location; 36 | } 37 | 38 | public int getId() { 39 | return id; 40 | } 41 | 42 | public LocationData getVelocity() { 43 | return velocity; 44 | } 45 | 46 | } 47 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/EntityMovingData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | 4 | public class EntityMovingData extends PacketData { 5 | 6 | 7 | /** 8 | * 9 | */ 10 | private static final long serialVersionUID = -3792160902735306458L; 11 | 12 | private double x, y, z; 13 | 14 | private int id; 15 | 16 | private float pitch, yaw; 17 | 18 | 19 | public EntityMovingData(int id, double x, double y, double z, float pitch, float yaw) { 20 | this.x = x; 21 | this.y = y; 22 | this.z = z; 23 | this.id = id; 24 | this.pitch = pitch; 25 | this.yaw = yaw; 26 | } 27 | 28 | public double getY() { 29 | return y; 30 | } 31 | 32 | public float getPitch() { 33 | return pitch; 34 | } 35 | 36 | public double getX() { 37 | return x; 38 | } 39 | 40 | public float getYaw() { 41 | return yaw; 42 | } 43 | 44 | public double getZ() { 45 | return z; 46 | } 47 | 48 | public int getId() { 49 | return id; 50 | } 51 | 52 | 53 | } 54 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/FishingData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | public class FishingData extends PacketData { 4 | 5 | /** 6 | * 7 | */ 8 | private static final long serialVersionUID = -3909142114596921006L; 9 | 10 | 11 | private LocationData location; 12 | 13 | private double x, y, z; 14 | 15 | private int id; 16 | 17 | private String owner; 18 | 19 | public FishingData(int id, LocationData location, double x, double y, double z, String owner) { 20 | this.location = location; 21 | this.x = x; 22 | this.y = y; 23 | this.z = z; 24 | this.id = id; 25 | this.owner = owner; 26 | } 27 | 28 | public LocationData getLocation() { 29 | return location; 30 | } 31 | 32 | public double getX() { 33 | return x; 34 | } 35 | 36 | public double getY() { 37 | return y; 38 | } 39 | 40 | public double getZ() { 41 | return z; 42 | } 43 | 44 | public int getId() { 45 | return id; 46 | } 47 | 48 | public String getOwner() { 49 | return owner; 50 | } 51 | } 52 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/InvData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | 4 | public class InvData extends PacketData { 5 | 6 | /** 7 | * 8 | */ 9 | private static final long serialVersionUID = -5055461506908394060L; 10 | 11 | 12 | private ItemData head, chest, leg, boots, mainHand, offHand; 13 | 14 | public InvData (ItemData head, ItemData chest, ItemData leg, ItemData boots, ItemData mainHand, ItemData offHand) { 15 | this.head = head; 16 | this.chest = chest; 17 | this.leg = leg; 18 | this.boots = boots; 19 | this.mainHand = mainHand; 20 | this.offHand = offHand; 21 | } 22 | 23 | public InvData() { 24 | 25 | } 26 | 27 | public ItemData getBoots() { 28 | return boots; 29 | } 30 | 31 | public ItemData getChest() { 32 | return chest; 33 | } 34 | 35 | public ItemData getHead() { 36 | return head; 37 | } 38 | 39 | public ItemData getLeg() { 40 | return leg; 41 | } 42 | 43 | public ItemData getMainHand() { 44 | return mainHand; 45 | } 46 | 47 | public ItemData getOffHand() { 48 | return offHand; 49 | } 50 | 51 | public void setBoots(ItemData boots) { 52 | this.boots = boots; 53 | } 54 | 55 | public void setChest(ItemData chest) { 56 | this.chest = chest; 57 | } 58 | 59 | public void setHead(ItemData head) { 60 | this.head = head; 61 | } 62 | 63 | public void setLeg(ItemData leg) { 64 | this.leg = leg; 65 | } 66 | 67 | public void setMainHand(ItemData mainHand) { 68 | this.mainHand = mainHand; 69 | } 70 | 71 | public void setOffHand(ItemData offHand) { 72 | this.offHand = offHand; 73 | } 74 | 75 | 76 | } 77 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/ItemData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | 4 | import me.jumper251.replay.legacy.LegacyMaterial; 5 | import me.jumper251.replay.utils.LogUtils; 6 | import me.jumper251.replay.utils.VersionUtil; 7 | import org.bukkit.Material; 8 | import org.bukkit.block.Block; 9 | 10 | public class ItemData extends PacketData{ 11 | 12 | /** 13 | * 14 | */ 15 | private static final long serialVersionUID = 3882181315164039909L; 16 | 17 | 18 | private int id, subId; 19 | 20 | private SerializableItemStack itemStack; 21 | 22 | public ItemData(int id, int subId) { 23 | this.id = id; 24 | this.subId = subId; 25 | } 26 | 27 | public ItemData(SerializableItemStack itemStack) { 28 | this.itemStack = itemStack; 29 | } 30 | 31 | public int getId() { 32 | return id; 33 | } 34 | 35 | public int getSubId() { 36 | return subId; 37 | } 38 | 39 | public SerializableItemStack getItemStack() { 40 | return itemStack; 41 | } 42 | 43 | public Material toMaterial() { 44 | if (itemStack != null) { 45 | return itemStack.getMaterial(); 46 | } 47 | 48 | if (VersionUtil.isAbove(VersionUtil.VersionEnum.V1_13)) { 49 | if (id != 0) { 50 | LogUtils.log("Could not parse material by id on 1.13+"); 51 | } 52 | return Material.AIR; 53 | } 54 | 55 | return LegacyMaterial.getMaterialById(id); 56 | } 57 | 58 | public static ItemData fromMaterial(Material material) { 59 | if (VersionUtil.isAbove(VersionUtil.VersionEnum.V1_13)) { 60 | return new ItemData(SerializableItemStack.fromMaterial(material)); 61 | } else { 62 | return new ItemData(material.getId(), 0); 63 | } 64 | } 65 | 66 | public static ItemData fromBlock(Block block) { 67 | if (VersionUtil.isAbove(VersionUtil.VersionEnum.V1_13)) { 68 | return new ItemData(SerializableItemStack.fromMaterial(block.getBlockData().getMaterial())); 69 | } else { 70 | return new ItemData(block.getState().getType().getId(), block.getState().getData().getData()); 71 | } 72 | } 73 | 74 | public static ItemData air() { 75 | if (VersionUtil.isAbove(VersionUtil.VersionEnum.V1_13)) { 76 | return fromMaterial(Material.AIR); 77 | } else { 78 | return new ItemData(0, 0); 79 | } 80 | } 81 | 82 | } 83 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/LocationData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | import java.io.Serializable; 4 | 5 | import org.bukkit.Bukkit; 6 | import org.bukkit.Location; 7 | 8 | public class LocationData implements Serializable{ 9 | 10 | /** 11 | * 12 | */ 13 | private static final long serialVersionUID = -849472505875330147L; 14 | 15 | private double x, y, z; 16 | 17 | private float yaw, pitch; 18 | 19 | private String world; 20 | 21 | public LocationData(double x, double y, double z, String world) { 22 | this.x = x; 23 | this.y = y; 24 | this.z = z; 25 | this.world = world; 26 | } 27 | 28 | public float getPitch() { 29 | return pitch; 30 | } 31 | 32 | public String getWorld() { 33 | return world; 34 | } 35 | 36 | public double getX() { 37 | return x; 38 | } 39 | 40 | public double getY() { 41 | return y; 42 | } 43 | 44 | public float getYaw() { 45 | return yaw; 46 | } 47 | 48 | public double getZ() { 49 | return z; 50 | } 51 | 52 | public void setYaw(float yaw) { 53 | this.yaw = yaw; 54 | } 55 | 56 | public void setPitch(float pitch) { 57 | this.pitch = pitch; 58 | } 59 | 60 | 61 | public static LocationData fromLocation(Location loc) { 62 | return new LocationData(loc.getX(), loc.getY(), loc.getZ(), loc.getWorld().getName()); 63 | } 64 | 65 | public static Location toLocation(LocationData locationData) { 66 | return new Location(Bukkit.getWorld(locationData.getWorld()), locationData.getX(), locationData.getY(), locationData.getZ()); 67 | } 68 | 69 | public boolean isValidWorld() { 70 | return Bukkit.getWorld(this.world) != null; 71 | } 72 | 73 | 74 | @Override 75 | public String toString() { 76 | return "LocationData{" + 77 | "x=" + x + 78 | ", y=" + y + 79 | ", z=" + z + 80 | ", yaw=" + yaw + 81 | ", pitch=" + pitch + 82 | ", world='" + world + '\'' + 83 | '}'; 84 | } 85 | } 86 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/MetadataUpdate.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | import me.jumper251.replay.replaysystem.recording.PlayerWatcher; 4 | 5 | public class MetadataUpdate extends PacketData { 6 | 7 | /** 8 | * 9 | */ 10 | private static final long serialVersionUID = -8969498588009941633L; 11 | 12 | private boolean burning, blocking, gliding, swimming; 13 | 14 | public MetadataUpdate(boolean burning, boolean blocking) { 15 | this.burning = burning; 16 | this.blocking = blocking; 17 | } 18 | 19 | public MetadataUpdate(boolean burning, boolean blocking, boolean gliding) { 20 | this(burning, blocking); 21 | 22 | this.gliding = gliding; 23 | } 24 | 25 | public MetadataUpdate(boolean burning, boolean blocking, boolean gliding, boolean swimming) { 26 | this(burning, blocking, gliding); 27 | 28 | this.swimming = swimming; 29 | } 30 | 31 | public boolean isBurning() { 32 | return burning; 33 | } 34 | 35 | public boolean isBlocking() { 36 | return blocking; 37 | } 38 | 39 | public boolean isGliding() { 40 | return gliding; 41 | } 42 | 43 | public boolean isSwimming() { 44 | return swimming; 45 | } 46 | 47 | public static MetadataUpdate fromWatcher(PlayerWatcher watcher) { 48 | return new MetadataUpdate(watcher.isBurning(), watcher.isBlocking(), watcher.isElytra(), watcher.isSwimming()); 49 | } 50 | 51 | } 52 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/MovingData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | 4 | public class MovingData extends PacketData { 5 | 6 | 7 | /** 8 | * 9 | */ 10 | private static final long serialVersionUID = -3792160902735306458L; 11 | 12 | private double x, y, z; 13 | 14 | private float pitch, yaw; 15 | 16 | public MovingData(double x, double y, double z, float pitch, float yaw) { 17 | this.x = x; 18 | this.y = y; 19 | this.z = z; 20 | this.pitch = pitch; 21 | this.yaw = yaw; 22 | } 23 | 24 | public double getY() { 25 | return y; 26 | } 27 | 28 | public float getPitch() { 29 | return pitch; 30 | } 31 | 32 | public double getX() { 33 | return x; 34 | } 35 | 36 | public float getYaw() { 37 | return yaw; 38 | } 39 | 40 | public double getZ() { 41 | return z; 42 | } 43 | 44 | 45 | 46 | } 47 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/PacketData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | import java.io.Serializable; 4 | 5 | public abstract class PacketData implements Serializable { 6 | 7 | /** 8 | * 9 | */ 10 | private static final long serialVersionUID = -799584901161673995L; 11 | 12 | } 13 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/ProjectileData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | import org.bukkit.entity.EntityType; 4 | 5 | public class ProjectileData extends PacketData { 6 | 7 | /** 8 | * 9 | */ 10 | private static final long serialVersionUID = 8320803760880960739L; 11 | 12 | private LocationData spawn, velocity; 13 | 14 | private EntityType type; 15 | 16 | 17 | public ProjectileData(LocationData spawn, LocationData velocity, EntityType type) { 18 | this.spawn = spawn; 19 | this.velocity = velocity; 20 | this.type = type; 21 | } 22 | 23 | public LocationData getSpawn() { 24 | return spawn; 25 | } 26 | 27 | public LocationData getVelocity() { 28 | return velocity; 29 | } 30 | 31 | public EntityType getType() { 32 | return type; 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/SignatureData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | public class SignatureData extends PacketData { 4 | 5 | /** 6 | * 7 | */ 8 | private static final long serialVersionUID = -5019331850509482609L; 9 | 10 | 11 | private String name, value, signature; 12 | 13 | public SignatureData(String name, String value, String signature) { 14 | this.name = name; 15 | this.signature = signature; 16 | this.value = value; 17 | } 18 | 19 | public String getName() { 20 | return name; 21 | } 22 | 23 | public String getSignature() { 24 | return signature; 25 | } 26 | 27 | public String getValue() { 28 | return value; 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/SpawnData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | import java.util.UUID; 4 | 5 | 6 | 7 | 8 | 9 | public class SpawnData extends PacketData { 10 | 11 | /** 12 | * 13 | */ 14 | private static final long serialVersionUID = -7896939862437693109L; 15 | 16 | private UUID uuid; 17 | 18 | private LocationData location; 19 | 20 | private SignatureData signature; 21 | 22 | public SpawnData(UUID uuid, LocationData location, SignatureData signature) { 23 | this.uuid = uuid; 24 | this.location = location; 25 | this.signature = signature; 26 | } 27 | 28 | public UUID getUuid() { 29 | return uuid; 30 | } 31 | 32 | public LocationData getLocation() { 33 | return location; 34 | } 35 | 36 | public SignatureData getSignature() { 37 | return signature; 38 | } 39 | 40 | public void setUuid(UUID uuid) { 41 | this.uuid = uuid; 42 | } 43 | 44 | } 45 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/TNTSpawnData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | public class TNTSpawnData extends PacketData { 4 | 5 | /** 6 | * 7 | */ 8 | private static final long serialVersionUID = 2309497657075148314L; 9 | 10 | private int id; 11 | private LocationData locationData; 12 | 13 | 14 | public TNTSpawnData(int id, LocationData locationData) { 15 | this.id = id; 16 | this.locationData = locationData; 17 | } 18 | 19 | public int getId() { 20 | return id; 21 | } 22 | 23 | public LocationData getLocationData() { 24 | return locationData; 25 | } 26 | 27 | } 28 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/VelocityData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | public class VelocityData extends PacketData { 4 | 5 | /** 6 | * 7 | */ 8 | private static final long serialVersionUID = 4046621273672598227L; 9 | 10 | private double x, y, z; 11 | 12 | private int id; 13 | 14 | public VelocityData(int id, double x, double y, double z) { 15 | this.id = id; 16 | this.y = y; 17 | this.x = x; 18 | this.z = z; 19 | } 20 | 21 | public int getId() { 22 | return id; 23 | } 24 | public double getX() { 25 | return x; 26 | } 27 | public double getY() { 28 | return y; 29 | } 30 | public double getZ() { 31 | return z; 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/data/types/WorldChangeData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.data.types; 2 | 3 | public class WorldChangeData extends PacketData { 4 | 5 | /** 6 | * 7 | */ 8 | private static final long serialVersionUID = -7360847147915116994L; 9 | 10 | private LocationData location; 11 | 12 | public WorldChangeData(LocationData location) { 13 | this.location = location; 14 | } 15 | 16 | public LocationData getLocation() { 17 | return location; 18 | } 19 | 20 | } 21 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/recording/CompListener.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.recording; 2 | 3 | 4 | import java.lang.reflect.InvocationTargetException; 5 | 6 | 7 | import org.bukkit.entity.Entity; 8 | import org.bukkit.entity.Player; 9 | import org.bukkit.event.Event; 10 | import org.bukkit.event.EventHandler; 11 | import org.bukkit.event.EventPriority; 12 | import org.bukkit.event.entity.EntityToggleGlideEvent; 13 | import org.bukkit.event.player.PlayerSwapHandItemsEvent; 14 | 15 | import me.jumper251.replay.listener.AbstractListener; 16 | import me.jumper251.replay.replaysystem.data.types.InvData; 17 | import me.jumper251.replay.replaysystem.data.types.MetadataUpdate; 18 | import me.jumper251.replay.replaysystem.utils.NPCManager; 19 | import me.jumper251.replay.utils.ReflectionHelper; 20 | import me.jumper251.replay.utils.VersionUtil; 21 | import me.jumper251.replay.utils.VersionUtil.VersionEnum; 22 | 23 | public class CompListener extends AbstractListener{ 24 | 25 | private PacketRecorder packetRecorder; 26 | 27 | public CompListener(PacketRecorder packetRecorder) { 28 | super(); 29 | 30 | this.packetRecorder = packetRecorder; 31 | } 32 | 33 | @EventHandler (ignoreCancelled = true, priority = EventPriority.MONITOR) 34 | public void onSwap(PlayerSwapHandItemsEvent e) { 35 | Player p = e.getPlayer(); 36 | if (this.packetRecorder.getRecorder().getPlayers().contains(p.getName())) { 37 | 38 | InvData data = NPCManager.copyFromPlayer(p, true, true); 39 | data.setMainHand(NPCManager.fromItemStack(e.getMainHandItem())); 40 | data.setOffHand(NPCManager.fromItemStack(e.getOffHandItem())); 41 | 42 | this.packetRecorder.addData(p.getName(), data); 43 | } 44 | 45 | } 46 | 47 | @EventHandler (ignoreCancelled = true, priority = EventPriority.MONITOR) 48 | public void onGlide(EntityToggleGlideEvent e) { 49 | if (e.getEntity() instanceof Player) { 50 | Player p = (Player) e.getEntity(); 51 | PlayerWatcher watcher = this.packetRecorder.getRecorder().getData().getWatcher(p.getName()); 52 | 53 | if (this.packetRecorder.getRecorder().getPlayers().contains(p.getName())) { 54 | watcher.setElytra(!p.isGliding()); 55 | 56 | this.packetRecorder.addData(p.getName(), new MetadataUpdate(watcher.isBurning(), watcher.isBlocking(), watcher.isElytra())); 57 | } 58 | 59 | } 60 | } 61 | 62 | public void onSwim(Event e) { 63 | Class swimEvent = e.getClass(); 64 | 65 | try { 66 | Entity en = (Entity) swimEvent.getMethod("getEntity").invoke(e); 67 | 68 | if (en instanceof Player) { 69 | Player p = (Player) en; 70 | 71 | PlayerWatcher watcher = this.packetRecorder.getRecorder().getData().getWatcher(p.getName()); 72 | if (this.packetRecorder.getRecorder().getPlayers().contains(p.getName())) { 73 | boolean isSwimming = (boolean) swimEvent.getMethod("isSwimming").invoke(e); 74 | 75 | watcher.setSwimming(isSwimming); 76 | this.packetRecorder.addData(p.getName(), MetadataUpdate.fromWatcher(watcher)); 77 | } 78 | 79 | } 80 | } catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException | NoSuchMethodException 81 | | SecurityException e1) { 82 | 83 | e1.printStackTrace(); 84 | } 85 | 86 | } 87 | 88 | 89 | @Override 90 | public void register() { 91 | super.register(); 92 | 93 | if (VersionUtil.isAbove(VersionEnum.V1_13)) { 94 | ReflectionHelper.getInstance().registerEvent(ReflectionHelper.getInstance().getSwimEvent(), this, this::onSwim); 95 | } 96 | } 97 | 98 | } 99 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/recording/optimization/ReplayQuality.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.recording.optimization; 2 | 3 | import me.jumper251.replay.filesystem.ConfigMessage; 4 | import me.jumper251.replay.filesystem.Messages; 5 | 6 | public enum ReplayQuality { 7 | 8 | LOW(Messages.QUALITY_LOW), 9 | MEDIUM(Messages.QUALITY_MEDIUM), 10 | HIGH(Messages.QUALITY_HIGH); 11 | 12 | private ConfigMessage qualityName; 13 | 14 | private ReplayQuality(ConfigMessage qualityName) { 15 | this.qualityName = qualityName; 16 | } 17 | 18 | public String getQualityName() { 19 | return qualityName.getFullMessage(); 20 | } 21 | 22 | } 23 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/recording/optimization/ReplayStats.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.recording.optimization; 2 | 3 | import java.util.LinkedHashMap; 4 | import java.util.List; 5 | import java.util.Map; 6 | import java.util.stream.Collectors; 7 | 8 | public class ReplayStats { 9 | 10 | private Map actions; 11 | 12 | private List players; 13 | 14 | private long entityCount; 15 | 16 | public ReplayStats(Map actions, List players, long entityCount) { 17 | this.actions = actions; 18 | this.players = players; 19 | this.entityCount = entityCount; 20 | } 21 | 22 | 23 | public long getActionCount() { 24 | return this.actions.values().stream() 25 | .reduce((long) 0, Long::sum); 26 | } 27 | 28 | 29 | public Map getSortedActions() { 30 | 31 | return this.actions.entrySet().stream() 32 | .sorted((Map.Entry.comparingByValue().reversed())) 33 | .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue, (o, n) -> n, LinkedHashMap::new)); 34 | } 35 | 36 | public Map getActions() { 37 | return actions; 38 | } 39 | 40 | public List getPlayers() { 41 | return players; 42 | } 43 | 44 | public long getEntityCount() { 45 | return entityCount; 46 | } 47 | } 48 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/replaying/ReplayingMode.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.replaying; 2 | 3 | public enum ReplayingMode { 4 | PLAYING, 5 | FORWARD, 6 | REVERSED 7 | } 8 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/replaying/session/ReplayProgressType.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.replaying.session; 2 | 3 | import me.jumper251.replay.replaysystem.replaying.Replayer; 4 | import me.jumper251.replay.utils.VersionUtil; 5 | import net.md_5.bungee.api.ChatMessageType; 6 | import net.md_5.bungee.api.chat.BaseComponent; 7 | import net.md_5.bungee.api.chat.TextComponent; 8 | 9 | 10 | public enum ReplayProgressType implements ReplayProgression { 11 | 12 | XP_BAR { 13 | @Override 14 | public void update(Replayer replayer) { 15 | int currentTicks = replayer.getCurrentTicks(); 16 | int level = currentTicks / 20; 17 | float percentage = (float) currentTicks / replayer.getReplay().getData().getDuration(); 18 | 19 | replayer.getWatchingPlayer().setLevel(level); 20 | replayer.getWatchingPlayer().setExp(percentage); 21 | } 22 | }, 23 | ACTION_BAR { 24 | @Override 25 | public void update(Replayer replayer) { 26 | if (VersionUtil.isBelow(VersionUtil.VersionEnum.V1_20)) return; 27 | 28 | int currentTicks = replayer.getCurrentTicks(); 29 | int duration = replayer.getReplay().getData().getDuration(); 30 | String format = "%s §e%s §7/ §e%s §6%s"; 31 | String status = replayer.isPaused() ? "§cPaused" : "§aPlaying"; 32 | String speed = replayer.getSpeed() + "x"; 33 | 34 | BaseComponent component = TextComponent.fromLegacy(String.format(format, status, formatTime(currentTicks), formatTime(duration), speed)); 35 | replayer.getWatchingPlayer().spigot().sendMessage(ChatMessageType.ACTION_BAR, component); 36 | } 37 | }, 38 | NONE { 39 | @Override 40 | public void update(Replayer replayer) { 41 | } 42 | }; 43 | 44 | 45 | public static ReplayProgressType getDefault() { 46 | if (VersionUtil.isAbove(VersionUtil.VersionEnum.V1_21)) { 47 | return ACTION_BAR; 48 | } else { 49 | return XP_BAR; 50 | } 51 | } 52 | 53 | private static String formatTime(int ticks) { 54 | int seconds = ticks / 20; 55 | int minutes = seconds / 60; 56 | seconds = seconds % 60; 57 | 58 | // Format the time in the format mm:ss 59 | return String.format("%02d:%02d", minutes, seconds); 60 | } 61 | 62 | } 63 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/replaying/session/ReplayProgression.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.replaying.session; 2 | 3 | import me.jumper251.replay.replaysystem.replaying.Replayer; 4 | 5 | public interface ReplayProgression { 6 | 7 | void update(Replayer replayer); 8 | } 9 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/utils/ReplayCleanup.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.utils; 2 | 3 | import java.io.File; 4 | import java.time.Instant; 5 | import java.time.LocalDate; 6 | import java.time.ZoneId; 7 | import java.util.List; 8 | 9 | import org.bukkit.Bukkit; 10 | 11 | import me.jumper251.replay.ReplaySystem; 12 | import me.jumper251.replay.filesystem.ConfigManager; 13 | import me.jumper251.replay.filesystem.saving.DatabaseReplaySaver; 14 | import me.jumper251.replay.filesystem.saving.DefaultReplaySaver; 15 | import me.jumper251.replay.filesystem.saving.ReplaySaver; 16 | import me.jumper251.replay.utils.LogUtils; 17 | 18 | public class ReplayCleanup { 19 | 20 | public static void cleanupReplays() { 21 | List replays = ReplaySaver.getReplays(); 22 | 23 | Bukkit.getScheduler().runTaskAsynchronously(ReplaySystem.getInstance(), () -> replays.forEach(ReplayCleanup::checkAndDelete)); 24 | } 25 | 26 | private static void checkAndDelete(String replay) { 27 | LocalDate creationdDate = getCreationDate(replay); 28 | LocalDate threshold = LocalDate.now().minusDays(ConfigManager.CLEANUP_REPLAYS); 29 | 30 | if (creationdDate.isBefore(threshold)) { 31 | LogUtils.log("Replay " + replay + " has expired. Removing it..."); 32 | ReplaySaver.delete(replay); 33 | } 34 | } 35 | 36 | private static LocalDate getCreationDate(String replay) { 37 | if (ReplaySaver.replaySaver instanceof DefaultReplaySaver) { 38 | return fromMillis(new File(DefaultReplaySaver.DIR, replay + ".replay").lastModified()); 39 | } 40 | 41 | if (ReplaySaver.replaySaver instanceof DatabaseReplaySaver) { 42 | return fromMillis(DatabaseReplaySaver.replayCache.get(replay).getTime()); 43 | } 44 | 45 | return LocalDate.now(); 46 | } 47 | 48 | private static LocalDate fromMillis(long millis) { 49 | return Instant.ofEpochMilli(millis).atZone(ZoneId.systemDefault()).toLocalDate(); 50 | 51 | } 52 | } 53 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/utils/entities/FishingUtils.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.utils.entities; 2 | 3 | import java.util.UUID; 4 | 5 | import me.jumper251.replay.utils.version.EntityBridge; 6 | import org.bukkit.Location; 7 | import org.bukkit.entity.EntityType; 8 | 9 | import com.comphenix.packetwrapper.WrapperPlayServerSpawnEntity; 10 | 11 | import me.jumper251.replay.replaysystem.data.types.FishingData; 12 | import me.jumper251.replay.replaysystem.data.types.LocationData; 13 | import me.jumper251.replay.utils.VersionUtil; 14 | import me.jumper251.replay.utils.VersionUtil.VersionEnum; 15 | 16 | public class FishingUtils { 17 | 18 | public static WrapperPlayServerSpawnEntity createHookPacket(FishingData fishing, int throwerID, int entID) { 19 | Location loc = LocationData.toLocation(fishing.getLocation()); 20 | 21 | WrapperPlayServerSpawnEntity packet = new WrapperPlayServerSpawnEntity(); 22 | 23 | packet.setEntityID(entID); 24 | if (VersionUtil.isBelow(VersionEnum.V1_13)) { 25 | packet.setObjectData(throwerID); 26 | packet.setType(90); 27 | } 28 | packet.setUniqueId(UUID.randomUUID()); 29 | 30 | packet.setOptionalSpeedX(fishing.getX()); 31 | packet.setOptionalSpeedY(fishing.getY()); 32 | packet.setOptionalSpeedZ(fishing.getZ()); 33 | 34 | if (VersionUtil.isAbove(VersionEnum.V1_14)) { 35 | packet.setObjectData(throwerID); // Object data index changed 36 | packet.getHandle().getEntityTypeModifier().write(0, EntityBridge.FISHING_BOBBER.toEntityType()); 37 | } 38 | 39 | packet.setX(loc.getX()); 40 | packet.setY(loc.getY()); 41 | packet.setZ(loc.getZ()); 42 | 43 | return packet; 44 | } 45 | 46 | public static com.comphenix.packetwrapper.old.WrapperPlayServerSpawnEntity createHookPacketOld(FishingData fishing, int throwerID, int entID) { 47 | Location loc = LocationData.toLocation(fishing.getLocation()); 48 | 49 | com.comphenix.packetwrapper.old.WrapperPlayServerSpawnEntity packet = new com.comphenix.packetwrapper.old.WrapperPlayServerSpawnEntity(); 50 | 51 | packet.setEntityID(entID); 52 | packet.setObjectData(throwerID); 53 | packet.setType(90); 54 | 55 | packet.setOptionalSpeedX(fishing.getX()); 56 | packet.setOptionalSpeedY(fishing.getY()); 57 | packet.setOptionalSpeedZ(fishing.getZ()); 58 | 59 | 60 | packet.setX(loc.getX()); 61 | packet.setY(loc.getY()); 62 | packet.setZ(loc.getZ()); 63 | packet.setPitch(loc.getPitch()); 64 | packet.setYaw(loc.getYaw()); 65 | 66 | return packet; 67 | } 68 | 69 | 70 | } 71 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/utils/entities/IEntity.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.utils.entities; 2 | 3 | 4 | 5 | import org.bukkit.Location; 6 | import org.bukkit.entity.Player; 7 | 8 | import com.comphenix.protocol.wrappers.WrappedDataWatcher; 9 | 10 | public interface IEntity { 11 | 12 | void spawn(Location loc, Player... players); 13 | 14 | void respawn(Player... players); 15 | 16 | void despawn(); 17 | 18 | void remove(); 19 | 20 | void teleport(Location loc, boolean onGround); 21 | 22 | void move(Location loc, boolean onGround, float yaw, float pitch); 23 | 24 | void look(float yaw, float pitch); 25 | 26 | void updateMetadata(); 27 | 28 | void animate(int id); 29 | 30 | int getId(); 31 | 32 | void setId(int id); 33 | 34 | void setData(WrappedDataWatcher data); 35 | 36 | WrappedDataWatcher getData(); 37 | 38 | void setPitch(float pitch); 39 | 40 | void setYaw(float yaw); 41 | 42 | Location getLocation(); 43 | 44 | void setOrigin(Location origin); 45 | 46 | void setLocation(Location location); 47 | 48 | Location getOrigin(); 49 | 50 | Player[] getVisible(); 51 | 52 | } 53 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/utils/entities/INPC.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.utils.entities; 2 | 3 | import java.util.List; 4 | 5 | import java.util.UUID; 6 | 7 | 8 | 9 | import org.bukkit.Location; 10 | import org.bukkit.entity.Player; 11 | 12 | import com.comphenix.packetwrapper.WrapperPlayServerEntityEquipment; 13 | import com.comphenix.protocol.wrappers.WrappedDataWatcher; 14 | import com.comphenix.protocol.wrappers.WrappedGameProfile; 15 | 16 | public interface INPC { 17 | 18 | void spawn(Location loc, int tabMode, Player... players); 19 | 20 | void respawn(Player... players); 21 | 22 | void despawn(); 23 | 24 | void remove(); 25 | 26 | void teleport(Location loc, boolean onGround); 27 | 28 | void move(Location loc, boolean onGround, float yaw, float pitch); 29 | 30 | void look(float yaw, float pitch); 31 | 32 | void updateMetadata(); 33 | 34 | void animate(int id); 35 | 36 | void sleep(Location loc); 37 | 38 | void addToTeam(String team); 39 | 40 | int getId(); 41 | 42 | String getName(); 43 | 44 | UUID getUuid(); 45 | 46 | void setId(int id); 47 | 48 | void setName(String name); 49 | 50 | void setUuid(UUID uuid); 51 | 52 | void setData(WrappedDataWatcher data); 53 | 54 | WrappedDataWatcher getData(); 55 | 56 | void setProfile(WrappedGameProfile profile); 57 | 58 | void setPitch(float pitch); 59 | 60 | void setYaw(float yaw); 61 | 62 | Location getLocation(); 63 | 64 | void setOrigin(Location origin); 65 | 66 | void setLocation(Location location); 67 | 68 | Location getOrigin(); 69 | 70 | Player[] getVisible(); 71 | 72 | void setLastEquipment(List list); 73 | } 74 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/utils/entities/NPCSpawnPacket.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.utils.entities; 2 | 3 | import com.comphenix.packetwrapper.WrapperPlayServerNamedEntitySpawn; 4 | import com.comphenix.packetwrapper.WrapperPlayServerSpawnEntity; 5 | import com.comphenix.packetwrapper.WrapperPlayServerSpawnEntityLiving; 6 | import com.comphenix.protocol.wrappers.WrappedDataWatcher; 7 | import org.bukkit.entity.EntityType; 8 | import org.bukkit.entity.Player; 9 | import org.bukkit.util.Vector; 10 | 11 | import java.util.UUID; 12 | 13 | public class NPCSpawnPacket { 14 | 15 | private WrapperPlayServerNamedEntitySpawn spawnNamedEntity; 16 | 17 | private WrapperPlayServerSpawnEntity spawnEntity; 18 | 19 | public NPCSpawnPacket(WrapperPlayServerNamedEntitySpawn spawnNamedEntity) { 20 | this.spawnNamedEntity = spawnNamedEntity; 21 | } 22 | 23 | public NPCSpawnPacket(WrapperPlayServerSpawnEntity spawnEntity) { 24 | this.spawnEntity = spawnEntity; 25 | spawnEntity.getHandle().getEntityTypeModifier().write(0, EntityType.PLAYER); 26 | } 27 | 28 | public void setEntityID(int id) { 29 | if (isOld()) { 30 | spawnNamedEntity.setEntityID(id); 31 | } else { 32 | spawnEntity.setEntityID(id); 33 | } 34 | } 35 | 36 | public void setPosition(Vector position) { 37 | if (isOld()) { 38 | spawnNamedEntity.setPosition(position); 39 | } else { 40 | spawnEntity.setPosition(position); 41 | } 42 | } 43 | 44 | 45 | public void setMetadata(WrappedDataWatcher data) { 46 | if (isOld()) { 47 | spawnNamedEntity.setMetadata(data); 48 | } 49 | } 50 | 51 | public void setX(double x) { 52 | if (isOld()) { 53 | spawnNamedEntity.setX(x); 54 | } else { 55 | spawnEntity.setX(x); 56 | } 57 | } 58 | 59 | public void setY(double y) { 60 | if (isOld()) { 61 | spawnNamedEntity.setY(y); 62 | } else { 63 | spawnEntity.setY(y); 64 | } 65 | } 66 | 67 | public void setZ(double z) { 68 | if (isOld()) { 69 | spawnNamedEntity.setZ(z); 70 | } else { 71 | spawnEntity.setZ(z); 72 | } 73 | } 74 | 75 | public void setYaw(float yaw) { 76 | if (isOld()) { 77 | spawnNamedEntity.setYaw(yaw); 78 | } 79 | } 80 | 81 | public void setPitch(float pitch) { 82 | if (isOld()) { 83 | spawnNamedEntity.setPitch(pitch); 84 | } 85 | } 86 | 87 | public void setUniqueId(UUID uuid) { 88 | if (isOld()) { 89 | spawnNamedEntity.setPlayerUUID(uuid); 90 | } else { 91 | spawnEntity.setUniqueId(uuid); 92 | } 93 | } 94 | 95 | public void sendPacket(Player player) { 96 | if (isOld()) { 97 | spawnNamedEntity.sendPacket(player); 98 | } else { 99 | spawnEntity.sendPacket(player); 100 | } 101 | } 102 | 103 | 104 | public boolean isOld() { 105 | return spawnNamedEntity != null; 106 | } 107 | } 108 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/replaysystem/utils/entities/SpawnPacket.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.replaysystem.utils.entities; 2 | 3 | import com.comphenix.packetwrapper.WrapperPlayServerSpawnEntity; 4 | import com.comphenix.packetwrapper.WrapperPlayServerSpawnEntityLiving; 5 | import com.comphenix.protocol.wrappers.WrappedDataWatcher; 6 | import org.bukkit.entity.EntityType; 7 | import org.bukkit.entity.Player; 8 | 9 | import java.util.UUID; 10 | 11 | public class SpawnPacket { 12 | 13 | private WrapperPlayServerSpawnEntityLiving spawnEntityLiving; 14 | 15 | private WrapperPlayServerSpawnEntity spawnEntity; 16 | 17 | public SpawnPacket(WrapperPlayServerSpawnEntityLiving spawnEntityLiving) { 18 | this.spawnEntityLiving = spawnEntityLiving; 19 | } 20 | 21 | public SpawnPacket(WrapperPlayServerSpawnEntity spawnEntity) { 22 | this.spawnEntity = spawnEntity; 23 | } 24 | 25 | public void setEntityID(int id) { 26 | if (isOld()) { 27 | spawnEntityLiving.setEntityID(id); 28 | } else { 29 | spawnEntity.setEntityID(id); 30 | } 31 | } 32 | 33 | public void setType(EntityType type) { 34 | if (isOld()) { 35 | spawnEntityLiving.setType(type); 36 | } else { 37 | spawnEntity.getHandle().getEntityTypeModifier().write(0, type); 38 | } 39 | } 40 | 41 | public void setMetadata(WrappedDataWatcher data) { 42 | if (isOld()) { 43 | spawnEntityLiving.setMetadata(data); 44 | } 45 | } 46 | 47 | public void setX(double x) { 48 | if (isOld()) { 49 | spawnEntityLiving.setX(x); 50 | } else { 51 | spawnEntity.setX(x); 52 | } 53 | } 54 | 55 | public void setY(double y) { 56 | if (isOld()) { 57 | spawnEntityLiving.setY(y); 58 | } else { 59 | spawnEntity.setY(y); 60 | } 61 | } 62 | 63 | public void setZ(double z) { 64 | if (isOld()) { 65 | spawnEntityLiving.setZ(z); 66 | } else { 67 | spawnEntity.setZ(z); 68 | } 69 | } 70 | 71 | public void setYaw(float yaw) { 72 | if (isOld()) { 73 | spawnEntityLiving.setYaw(yaw); 74 | } 75 | } 76 | 77 | public void setPitch(float pitch) { 78 | if (isOld()) { 79 | spawnEntityLiving.setPitch(pitch); 80 | } 81 | } 82 | 83 | public void setUniqueId(UUID uuid) { 84 | if (isOld()) { 85 | spawnEntityLiving.setUniqueId(uuid); 86 | } else { 87 | spawnEntity.setUniqueId(uuid); 88 | } 89 | } 90 | 91 | public void sendPacket(Player player) { 92 | if (isOld()) { 93 | spawnEntityLiving.sendPacket(player); 94 | } else { 95 | spawnEntity.sendPacket(player); 96 | } 97 | } 98 | 99 | 100 | public boolean isOld() { 101 | return spawnEntityLiving != null; 102 | } 103 | } 104 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/IntEnum.java: -------------------------------------------------------------------------------- 1 | /* 2 | * ProtocolLib - Bukkit server library that allows access to the Minecraft protocol. 3 | * Copyright (C) 2012 Kristian S. Stangeland 4 | * 5 | * This program is free software; you can redistribute it and/or modify it under the terms of the 6 | * GNU General Public License as published by the Free Software Foundation; either version 2 of 7 | * the License, or (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; 10 | * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. 11 | * See the GNU General Public License for more details. 12 | * 13 | * You should have received a copy of the GNU General Public License along with this program; 14 | * if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 15 | * 02111-1307 USA 16 | */ 17 | 18 | package me.jumper251.replay.utils; 19 | 20 | import java.lang.reflect.Field; 21 | import java.util.HashSet; 22 | import java.util.Set; 23 | 24 | import com.google.common.collect.BiMap; 25 | import com.google.common.collect.HashBiMap; 26 | 27 | /** 28 | * Represents a traditional int field enum. 29 | * 30 | * @author Kristian 31 | */ 32 | public class IntEnum { 33 | 34 | // Used to convert between IDs and names 35 | protected BiMap members = HashBiMap.create(); 36 | 37 | /** 38 | * Registers every declared integer field. 39 | */ 40 | public IntEnum() { 41 | registerAll(); 42 | } 43 | 44 | /** 45 | * Registers every public int field as a member. 46 | */ 47 | protected void registerAll() { 48 | try { 49 | // Register every int field 50 | for (Field entry : this.getClass().getFields()) { 51 | if (entry.getType().equals(int.class)) { 52 | registerMember(entry.getInt(this), entry.getName()); 53 | } 54 | } 55 | 56 | } catch (IllegalArgumentException e) { 57 | e.printStackTrace(); 58 | } catch (IllegalAccessException e) { 59 | e.printStackTrace(); 60 | } 61 | } 62 | 63 | /** 64 | * Registers a member. 65 | * @param id - id of member. 66 | * @param name - name of member. 67 | */ 68 | protected void registerMember(int id, String name) { 69 | members.put(id, name); 70 | } 71 | 72 | /** 73 | * Determines whether or not the given member exists. 74 | * @param id - the ID of the member to find. 75 | * @return TRUE if a member with the given ID exists, FALSE otherwise. 76 | */ 77 | public boolean hasMember(int id) { 78 | return members.containsKey(id); 79 | } 80 | 81 | /** 82 | * Retrieve the ID of the member with the given name. 83 | * @param name - name of member to retrieve. 84 | * @return ID of the member, or NULL if not found. 85 | */ 86 | public Integer valueOf(String name) { 87 | return members.inverse().get(name); 88 | } 89 | 90 | /** 91 | * Retrieve the name of the member with the given id. 92 | * @param id - id of the member to retrieve. 93 | * @return Declared name of the member, or NULL if not found. 94 | */ 95 | public String getDeclaredName(Integer id) { 96 | return members.get(id); 97 | } 98 | 99 | /** 100 | * Retrieve the ID of every registered member. 101 | * @return Enumeration of every value. 102 | */ 103 | public Set values() { 104 | return new HashSet(members.keySet()); 105 | } 106 | } -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/LogUtils.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils; 2 | 3 | import me.jumper251.replay.ReplaySystem; 4 | 5 | public class LogUtils { 6 | 7 | public static void log(String message){ 8 | ReplaySystem.getInstance().getLogger().info(message); 9 | } 10 | 11 | } 12 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/MathUtils.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils; 2 | 3 | import java.util.List; 4 | 5 | import java.util.Random; 6 | 7 | 8 | public class MathUtils { 9 | 10 | public static int randInt(int min, int max) { 11 | Random rand = new Random(); 12 | int randomNum = rand.nextInt((max - min) + 1) + min; 13 | return randomNum; 14 | } 15 | 16 | public static double round(double number, double amount){ 17 | return Math.round(number * amount)/amount; 18 | 19 | } 20 | 21 | public static double getAverageDouble(List list){ 22 | if(list == null) return -1; 23 | if(list.size() == 0) return -1; 24 | double avg = 0; 25 | for(double val : list){ 26 | avg += val; 27 | } 28 | avg /= list.size(); 29 | 30 | return round(avg, 100); 31 | } 32 | 33 | public static int getAverageInt(List list){ 34 | if(list == null) return -1; 35 | if(list.size() == 0) return -1; 36 | int avg = 0; 37 | for(int val : list){ 38 | avg += val; 39 | } 40 | avg /= list.size(); 41 | 42 | return avg; 43 | } 44 | 45 | public static boolean isInt(String string) { 46 | try 47 | { 48 | Integer.parseInt(string); 49 | return true; } catch (Exception ex) { 50 | } 51 | return false; 52 | } 53 | 54 | public static boolean isDouble(String string) { 55 | try 56 | { 57 | Double.parseDouble(string); 58 | return true; } catch (Exception ex) { 59 | } 60 | return false; 61 | } 62 | 63 | } 64 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/ProtocolLibUtil.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils; 2 | 3 | import com.comphenix.protocol.wrappers.WrappedDataWatcher; 4 | import me.jumper251.replay.replaysystem.utils.entities.PacketNPC; 5 | 6 | public class ProtocolLibUtil { 7 | 8 | /** 9 | * Initialize some ProtocolLib wrappers to avoid class loading issues 10 | * in the first replay after a server start. 11 | */ 12 | public static void prepare() { 13 | PacketNPC npc = new PacketNPC(); 14 | npc.setData(new WrappedDataWatcher()); 15 | npc.getInfoAddPacket(); 16 | npc.look(0, 0); 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/ReplayManager.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils; 2 | 3 | import me.jumper251.replay.ReplaySystem; 4 | import me.jumper251.replay.api.ReplayAPI; 5 | import me.jumper251.replay.commands.replay.ReplayCommand; 6 | import me.jumper251.replay.filesystem.ConfigManager; 7 | import me.jumper251.replay.listener.ReplayListener; 8 | import me.jumper251.replay.replaysystem.Replay; 9 | import org.bukkit.Bukkit; 10 | 11 | import java.util.HashMap; 12 | 13 | public class ReplayManager { 14 | 15 | public static HashMap activeReplays = new HashMap<>(); 16 | 17 | public static void register() { 18 | registerEvents(); 19 | registerCommands(); 20 | 21 | if (ConfigManager.RECORD_STARTUP) { 22 | ReplayAPI.getInstance().recordReplay(null, Bukkit.getConsoleSender()); 23 | } 24 | 25 | Bukkit.getScheduler().runTaskAsynchronously(ReplaySystem.getInstance(), ReplayManager::delayedInit); 26 | } 27 | 28 | private static void registerEvents() { 29 | new ReplayListener().register(); 30 | } 31 | 32 | private static void registerCommands() { 33 | ReplaySystem.getInstance().getCommand("replay").setExecutor(new ReplayCommand()); 34 | } 35 | 36 | private static void delayedInit() { 37 | if (VersionUtil.isAbove(VersionUtil.VersionEnum.V1_21)) { 38 | ProtocolLibUtil.prepare(); 39 | } 40 | } 41 | 42 | } 43 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/StringUtils.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils; 2 | 3 | public class StringUtils { 4 | 5 | private static char[] chars = new char[]{'a' , 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 6 | 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', 'A' , 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 7 | 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', 8 | '0', '1', '2', '3', '4', '5', '6', '7', '8', '9'}; 9 | 10 | public static String getRandomString(int length) { 11 | StringBuilder sb = new StringBuilder(length); 12 | for(int i = 0; i < length; i += 1){ 13 | sb.append(chars[MathUtils.randInt(0, (chars.length - 1))]); 14 | } 15 | return sb.toString(); 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/Updater.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils; 2 | 3 | import java.io.BufferedReader; 4 | 5 | 6 | import java.io.InputStreamReader; 7 | import java.net.HttpURLConnection; 8 | import java.net.URL; 9 | import java.util.concurrent.ExecutorService; 10 | import java.util.concurrent.Executors; 11 | 12 | import me.jumper251.replay.ReplaySystem; 13 | import me.jumper251.replay.filesystem.ConfigManager; 14 | import me.jumper251.replay.utils.fetcher.Acceptor; 15 | import me.jumper251.replay.utils.fetcher.Consumer; 16 | 17 | 18 | 19 | 20 | 21 | public class Updater { 22 | 23 | private String currentVersion; 24 | private int id; 25 | private boolean versionAvailable; 26 | private static ExecutorService pool = Executors.newCachedThreadPool(); 27 | 28 | public Updater(){ 29 | this.currentVersion = ReplaySystem.getInstance().getDescription().getVersion(); 30 | this.id = 52849; 31 | this.versionAvailable = false; 32 | 33 | if(ConfigManager.UPDATE_NOTIFY){ 34 | checkForUpdate(); 35 | } 36 | } 37 | 38 | public void checkForUpdate(){ 39 | getContent(version -> { 40 | if (version != null && !version.equalsIgnoreCase(currentVersion)) { 41 | versionAvailable = true; 42 | } 43 | }); 44 | } 45 | 46 | private void getContent(Consumer consumer){ 47 | 48 | pool.execute(new Acceptor(consumer) { 49 | 50 | @Override 51 | public String getValue() { 52 | try{ 53 | HttpURLConnection con = (HttpURLConnection) new URL("https://api.spigotmc.org/legacy/update.php?resource=" + id).openConnection(); 54 | con.setDoOutput(true); 55 | con.setRequestMethod("GET"); 56 | 57 | String version; 58 | BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(con.getInputStream())); 59 | version = bufferedReader.readLine(); 60 | 61 | return version; 62 | 63 | } catch(Exception e){ 64 | e.printStackTrace(); 65 | 66 | return null; 67 | } 68 | } 69 | 70 | }); 71 | 72 | } 73 | 74 | public boolean isVersionAvailable() { 75 | return versionAvailable; 76 | } 77 | } 78 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/VersionUtil.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils; 2 | 3 | import java.lang.reflect.Field; 4 | 5 | 6 | import org.bukkit.Bukkit; 7 | import org.bukkit.entity.Player; 8 | 9 | public class VersionUtil { 10 | 11 | public static VersionEnum VERSION; 12 | 13 | static { 14 | VERSION = VersionEnum.parseVersion(); 15 | } 16 | 17 | public static boolean isCompatible(VersionEnum ve){ 18 | return VERSION.equals(ve); 19 | } 20 | 21 | public static boolean isAbove(VersionEnum ve) { 22 | return VERSION.getOrder() >= ve.getOrder(); 23 | } 24 | 25 | public static boolean isBelow(VersionEnum ve) { 26 | return VERSION.getOrder() <= ve.getOrder(); 27 | } 28 | 29 | public static boolean isBetween(VersionEnum ve1, VersionEnum ve2) { 30 | return isAbove(ve1) && isBelow(ve2); 31 | } 32 | 33 | public static Class getNmsClass(String nmsClassName) throws ClassNotFoundException { 34 | return Class.forName("net.minecraft.server." + Bukkit.getServer().getClass().getPackage().getName().replace(".", ",").split(",")[3] + "." + nmsClassName); 35 | } 36 | 37 | public static void sendPacket(Player p, Object packet){ 38 | try{ 39 | Object nmsPlayer = p.getClass().getMethod("getHandle").invoke(p); 40 | Field playerConnectionField = nmsPlayer.getClass().getField("playerConnection"); 41 | Object pConnection = playerConnectionField.get(nmsPlayer); 42 | pConnection.getClass().getMethod("sendPacket", Class.forName("net.minecraft.server." + VersionUtil.VERSION + ".Packet")).invoke(pConnection, packet); 43 | }catch(Exception e){ 44 | e.printStackTrace(); 45 | } 46 | 47 | } 48 | 49 | 50 | 51 | public enum VersionEnum { 52 | 53 | V1_8(1), 54 | V1_9(2), 55 | V1_10(3), 56 | V1_11(4), 57 | V1_12(5), 58 | V1_13(6), 59 | V1_14(7), 60 | V1_15(8), 61 | V1_16(9), 62 | V1_17(10), 63 | V1_18(11), 64 | V1_19(12), 65 | V1_20(13), 66 | V1_21(14); 67 | 68 | 69 | private int order; 70 | 71 | VersionEnum(int order) { 72 | this.order = order; 73 | } 74 | 75 | public int getOrder() { 76 | return order; 77 | } 78 | 79 | public static VersionEnum parseVersion() { 80 | String version = Bukkit.getBukkitVersion().split("-")[0]; 81 | String majorMinor = version.split("\\.")[0] + "_" + version.split("\\.")[1]; 82 | 83 | return VersionEnum.valueOf("V" + majorMinor); 84 | } 85 | 86 | } 87 | } 88 | 89 | 90 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/fetcher/Acceptor.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils.fetcher; 2 | 3 | 4 | 5 | public abstract class Acceptor implements Runnable{ 6 | 7 | private Consumer consumer; 8 | 9 | public Acceptor(Consumer consumer) { 10 | this.consumer = consumer; 11 | } 12 | 13 | public abstract T getValue(); 14 | 15 | @Override 16 | public void run() { 17 | consumer.accept(getValue()); 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/fetcher/Consumer.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils.fetcher; 2 | 3 | public interface Consumer { 4 | 5 | void accept(T t); 6 | 7 | 8 | 9 | } 10 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/fetcher/JsonClass.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils.fetcher; 2 | 3 | import com.google.gson.ExclusionStrategy; 4 | import com.google.gson.FieldAttributes; 5 | import com.google.gson.annotations.SerializedName; 6 | 7 | public abstract class JsonClass implements ExclusionStrategy{ 8 | 9 | 10 | 11 | @Override 12 | public boolean shouldSkipClass(Class arg0) { 13 | return false; 14 | } 15 | 16 | @Override 17 | public boolean shouldSkipField(FieldAttributes field) { 18 | SerializedName ns = field.getAnnotation(SerializedName.class); 19 | if(ns != null) 20 | return false; 21 | return true; 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/fetcher/JsonData.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils.fetcher; 2 | 3 | 4 | 5 | import com.google.gson.Gson; 6 | 7 | public class JsonData { 8 | 9 | private boolean enabled; 10 | private JsonClass jsonClass; 11 | private Gson gson = new Gson(); 12 | private String data; 13 | public JsonData(boolean enabled){ 14 | this.enabled = enabled; 15 | } 16 | public JsonData(boolean enabled, JsonClass jsonClass){ 17 | this.enabled = enabled; 18 | this.jsonClass = jsonClass; 19 | 20 | 21 | } 22 | public void setData(String data) { 23 | this.data = data; 24 | } 25 | public void convertData(){ 26 | this.jsonClass = gson.fromJson(data, this.jsonClass.getClass()); 27 | } 28 | public JsonClass getJsonClass() { 29 | return jsonClass; 30 | } 31 | 32 | 33 | public boolean isEnabled(){ 34 | return this.enabled; 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/fetcher/PlayerInfo.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils.fetcher; 2 | 3 | import com.google.gson.annotations.SerializedName; 4 | 5 | public class PlayerInfo extends JsonClass{ 6 | @SerializedName("id") 7 | private String id; 8 | 9 | @SerializedName("name") 10 | private String name; 11 | 12 | @SerializedName("legacy") 13 | private boolean legacy; 14 | 15 | 16 | public String getId() { 17 | return id; 18 | } 19 | 20 | public String getName() { 21 | return name; 22 | } 23 | public boolean getLegacy(){ 24 | return this.legacy; 25 | } 26 | 27 | 28 | 29 | 30 | } 31 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/fetcher/SkinInfo.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils.fetcher; 2 | 3 | 4 | 5 | import java.util.List; 6 | 7 | import java.util.Map; 8 | 9 | import com.google.gson.annotations.SerializedName; 10 | 11 | public class SkinInfo extends JsonClass { 12 | 13 | @SerializedName("id") 14 | private String id; 15 | 16 | @SerializedName("name") 17 | private String name; 18 | 19 | @SerializedName("properties") 20 | private List> properties; 21 | 22 | public String getId() { 23 | return id; 24 | } 25 | 26 | public String getName() { 27 | return name; 28 | } 29 | 30 | public List> getProperties() { 31 | return properties; 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/fetcher/TextureInfo.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils.fetcher; 2 | 3 | import com.google.gson.annotations.SerializedName; 4 | 5 | import java.net.MalformedURLException; 6 | import java.net.URL; 7 | 8 | public class TextureInfo { 9 | private Textures textures; 10 | 11 | 12 | public Textures getTextures() { 13 | return textures; 14 | } 15 | 16 | public static class Skin { 17 | private String url; 18 | 19 | public URL getUrl() { 20 | try { 21 | return new URL(url); 22 | } catch (MalformedURLException e) { 23 | return null; 24 | } 25 | } 26 | } 27 | 28 | public static class Textures { 29 | @SerializedName("SKIN") 30 | private Skin skin; 31 | 32 | 33 | public Skin getSkin() { 34 | return skin; 35 | } 36 | } 37 | } 38 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/version/EnchantmentBridge.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils.version; 2 | 3 | import org.bukkit.enchantments.Enchantment; 4 | 5 | import java.util.EnumSet; 6 | import java.util.HashMap; 7 | import java.util.Map; 8 | 9 | public enum EnchantmentBridge { 10 | 11 | UNBREAKING("DURABILITY"); 12 | 13 | private static final Map enchantmentTypeMap = new HashMap<>(); 14 | 15 | static { 16 | EnumSet.allOf(EnchantmentBridge.class).forEach(type -> { 17 | Enchantment enchantment = Enchantment.getByName(type.name()); 18 | if (enchantment == null) { 19 | enchantment = Enchantment.getByName(type.getLegacyName()); 20 | } 21 | enchantmentTypeMap.put(type, enchantment); 22 | }); 23 | } 24 | 25 | private String legacyName; 26 | 27 | EnchantmentBridge(String legacyName) { 28 | this.legacyName = legacyName; 29 | } 30 | 31 | public Enchantment toEnchantment() { 32 | return enchantmentTypeMap.get(this); 33 | } 34 | 35 | public String getLegacyName() { 36 | return legacyName; 37 | } 38 | } 39 | -------------------------------------------------------------------------------- /src/main/java/me/jumper251/replay/utils/version/EntityBridge.java: -------------------------------------------------------------------------------- 1 | package me.jumper251.replay.utils.version; 2 | 3 | import com.google.common.base.Enums; 4 | import org.bukkit.entity.EntityType; 5 | 6 | import java.util.EnumSet; 7 | import java.util.HashMap; 8 | import java.util.Map; 9 | 10 | public enum EntityBridge { 11 | 12 | FISHING_BOBBER("FISHING_HOOK"), 13 | ITEM("DROPPED_ITEM"), 14 | TNT("PRIMED_TNT"); 15 | 16 | private static final Map entityTypeMap = new HashMap<>(); 17 | 18 | static { 19 | EnumSet.allOf(EntityBridge.class).forEach(entityBridge -> { 20 | EntityType type = Enums.getIfPresent(EntityType.class, entityBridge.name()) 21 | .or(EntityType.valueOf(entityBridge.getLegacyName())); 22 | entityTypeMap.put(entityBridge.name(), type); 23 | }); 24 | } 25 | 26 | private String legacyName; 27 | 28 | EntityBridge(String legacyName) { 29 | this.legacyName = legacyName; 30 | } 31 | 32 | public EntityType toEntityType() { 33 | return entityTypeMap.get(name()); 34 | } 35 | 36 | public String getLegacyName() { 37 | return legacyName; 38 | } 39 | } 40 | -------------------------------------------------------------------------------- /src/main/resources/plugin.yml: -------------------------------------------------------------------------------- 1 | name: AdvancedReplay 2 | version: '${version}' 3 | main: me.jumper251.replay.ReplaySystem 4 | author: Jumper251 5 | depend: [ProtocolLib] 6 | api-version: 1.13 7 | commands: 8 | replay: 9 | description: Main Replay command 10 | aliases: [rp] 11 | permission: replay.command 12 | 13 | permissions: 14 | replay.command: 15 | description: Permission to use the replay command 16 | replay.command.start: 17 | default: op 18 | replay.command.stop: 19 | default: op 20 | replay.command.info: 21 | default: op 22 | replay.command.play: 23 | default: op 24 | replay.command.reload: 25 | default: op 26 | replay.command.overview: 27 | default: op 28 | replay.command.list: 29 | default: op 30 | replay.command.migrate: 31 | default: op 32 | replay.command.delete: 33 | default: op 34 | replay.command.jump: 35 | default: op 36 | replay.admin: 37 | description: Permission to receive update notifications --------------------------------------------------------------------------------