├── gradlew ├── image └── cover.png ├── .github ├── FUNDING.yml ├── ISSUE_TEMPLATE │ ├── question.md │ ├── suggestion.md │ └── bug_report.md ├── PULL_REQUEST_TEMPLATE.md └── workflows │ └── build.yml ├── gradle └── wrapper │ ├── gradle-wrapper.jar │ └── gradle-wrapper.properties ├── src └── main │ ├── resources │ ├── assets │ │ └── maple │ │ │ └── icon.png │ ├── maple.mixins.json │ └── fabric.mod.json │ └── java │ └── de │ └── stylextv │ └── maple │ ├── util │ ├── math │ │ ├── VectorUtil.java │ │ └── MathUtil.java │ ├── time │ │ ├── TimeUtil.java │ │ ├── TimeFormat.java │ │ └── TimeUnit.java │ ├── iterate │ │ ├── iterators │ │ │ ├── types │ │ │ │ ├── IntIterator.java │ │ │ │ ├── IntPairIterator.java │ │ │ │ ├── IntTripletIterator.java │ │ │ │ └── StaticIterator.java │ │ │ ├── RangeIterator.java │ │ │ ├── GridIterator.java │ │ │ ├── SpiralIterator.java │ │ │ └── BoxIterator.java │ │ ├── IntPair.java │ │ ├── IntTriplet.java │ │ └── FunctionIterator.java │ ├── ExceptionUtil.java │ ├── RegistryUtil.java │ ├── world │ │ ├── CoordUtil.java │ │ └── rotation │ │ │ └── RotationUtil.java │ ├── ItemUtil.java │ ├── TextUtil.java │ └── chat │ │ └── ChatUtil.java │ ├── input │ ├── controller │ │ ├── InteractController.java │ │ ├── GuiController.java │ │ ├── InputController.java │ │ ├── PlaceController.java │ │ └── BreakController.java │ ├── InputAction.java │ ├── SmoothLook.java │ ├── InjectedInput.java │ └── target │ │ ├── targets │ │ ├── OpenableTarget.java │ │ ├── BreakableTarget.java │ │ └── PlaceableTarget.java │ │ └── TargetList.java │ ├── pathing │ ├── PathingState.java │ ├── calc │ │ ├── PathState.java │ │ ├── goal │ │ │ ├── InvertedGoal.java │ │ │ ├── AxisGoal.java │ │ │ ├── Goal.java │ │ │ ├── YLevelGoal.java │ │ │ ├── NearGoal.java │ │ │ ├── GetToBlockGoal.java │ │ │ ├── TwoBlocksGoal.java │ │ │ ├── BlockGoal.java │ │ │ └── StrictDirectionGoal.java │ │ └── Cost.java │ ├── movement │ │ ├── MovementState.java │ │ ├── moves │ │ │ ├── AscendMove.java │ │ │ ├── PillarMove.java │ │ │ ├── DiagonalMove.java │ │ │ ├── StraightMove.java │ │ │ ├── DescendMove.java │ │ │ └── ParkourMove.java │ │ ├── helper │ │ │ ├── MovementHelper.java │ │ │ ├── JumpHelper.java │ │ │ ├── BumpHelper.java │ │ │ ├── DangerHelper.java │ │ │ └── InteractHelper.java │ │ └── movements │ │ │ ├── DiagonalMovement.java │ │ │ ├── DescendMovement.java │ │ │ ├── ParkourMovement.java │ │ │ ├── StraightMovement.java │ │ │ ├── PillarMovement.java │ │ │ └── AscendMovement.java │ ├── PathingCommandType.java │ ├── PathingCommand.java │ └── PathingStatus.java │ ├── event │ ├── Event.java │ ├── events │ │ ├── types │ │ │ └── Cancelable.java │ │ ├── BlockUpdateEvent.java │ │ ├── ClientChatEvent.java │ │ ├── EntityDeathEvent.java │ │ ├── EntitySleptEvent.java │ │ ├── InventoryUpdateEvent.java │ │ ├── TickEvent.java │ │ ├── ChunkEvent.java │ │ ├── RenderWorldEvent.java │ │ ├── PacketEvent.java │ │ └── WorldEvent.java │ ├── EventBus.java │ ├── listeners │ │ ├── ChatListener.java │ │ ├── TickListener.java │ │ └── WorldListener.java │ └── EventListener.java │ ├── waypoint │ ├── WaypointTag.java │ └── Waypoint.java │ ├── world │ ├── scan │ │ ├── ScanFilter.java │ │ ├── ScanFilters.java │ │ ├── block │ │ │ ├── BlockFilters.java │ │ │ ├── filters │ │ │ │ └── BlockTypeFilter.java │ │ │ └── BlockFilter.java │ │ └── entity │ │ │ ├── EntityFilters.java │ │ │ ├── filters │ │ │ ├── EntityTypeFilter.java │ │ │ └── EntityNameFilter.java │ │ │ ├── EntityScanner.java │ │ │ └── EntityFilter.java │ ├── WorldBorderInterface.java │ ├── interact │ │ ├── openables │ │ │ ├── OpenableFenceGate.java │ │ │ ├── OpenableTrapdoor.java │ │ │ └── OpenableDoor.java │ │ └── Openable.java │ ├── BlockInterface.java │ └── avoidance │ │ ├── Avoidance.java │ │ └── AvoidanceFilter.java │ ├── io │ ├── serialize │ │ └── serializers │ │ │ ├── list │ │ │ ├── types │ │ │ │ ├── LongListSerializer.java │ │ │ │ ├── FloatListSerializer.java │ │ │ │ ├── ShortListSerializer.java │ │ │ │ ├── DoubleListSerializer.java │ │ │ │ ├── BooleanListSerializer.java │ │ │ │ ├── UUIDListSerializer.java │ │ │ │ └── IntegerListSerializer.java │ │ │ └── ListSerializer.java │ │ │ ├── BooleanSerializer.java │ │ │ ├── StringSerializer.java │ │ │ ├── BitSetSerializer.java │ │ │ ├── UUIDSerializer.java │ │ │ ├── LongSerializer.java │ │ │ ├── FloatSerializer.java │ │ │ ├── ShortSerializer.java │ │ │ ├── CharSerializer.java │ │ │ ├── DoubleSerializer.java │ │ │ └── IntegerSerializer.java │ └── resource │ │ └── types │ │ ├── StreamedAsset.java │ │ └── StreamedFile.java │ ├── Constants.java │ ├── render │ └── mesh │ │ ├── Mesh.java │ │ ├── LineMesh.java │ │ └── BoxMesh.java │ ├── mixin │ ├── MinecraftClientInvoker.java │ ├── GameRendererMixin.java │ ├── ScreenMixin.java │ ├── DefaultedListMixin.java │ ├── LivingEntityMixin.java │ ├── WorldRendererMixin.java │ ├── MinecraftClientMixin.java │ ├── ClientConnectionMixin.java │ └── NetworkHandlerMixin.java │ ├── context │ └── ClientContext.java │ ├── scheme │ ├── Colors.java │ └── Color.java │ ├── cache │ ├── block │ │ └── matchers │ │ │ ├── UnbreakableBlockMatcher.java │ │ │ ├── BlockadeBlockMatcher.java │ │ │ ├── DangerBlockMatcher.java │ │ │ ├── FluidBlockMatcher.java │ │ │ └── SolidBlockMatcher.java │ ├── io │ │ ├── file │ │ │ └── CachedRegionFile.java │ │ └── serialize │ │ │ └── CachedChunkSerializer.java │ └── CacheManager.java │ ├── schematic │ ├── schematics │ │ ├── FillSchematic.java │ │ └── StaticSchematic.java │ └── Schematic.java │ ├── command │ ├── commands │ │ ├── VersionCommand.java │ │ ├── PauseCommand.java │ │ ├── StopCommand.java │ │ ├── ResumeCommand.java │ │ ├── FarmCommand.java │ │ ├── AxisCommand.java │ │ ├── LostCommand.java │ │ ├── HomeCommand.java │ │ ├── ETACommand.java │ │ ├── TunnelCommand.java │ │ ├── MineCommand.java │ │ ├── FollowCommand.java │ │ ├── ModifiedCommand.java │ │ ├── ThisWayCommand.java │ │ ├── GotoCommand.java │ │ └── HelpCommand.java │ ├── Command.java │ ├── ArgumentHelper.java │ └── ArgumentList.java │ ├── task │ ├── tasks │ │ ├── MineTask.java │ │ ├── FarmTask.java │ │ ├── CustomGoalTask.java │ │ ├── FollowTask.java │ │ ├── ScanTask.java │ │ ├── CompositeTask.java │ │ └── GetToBlockTask.java │ ├── TaskManager.java │ └── Task.java │ ├── option │ ├── Option.java │ └── Options.java │ ├── config │ └── ConfigHelper.java │ └── Maple.java ├── settings.gradle ├── CONTRIBUTING.md ├── .gitignore └── gradle.properties /gradlew: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stylextv/maple/HEAD/gradlew -------------------------------------------------------------------------------- /image/cover.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stylextv/maple/HEAD/image/cover.png -------------------------------------------------------------------------------- /.github/FUNDING.yml: -------------------------------------------------------------------------------- 1 | # These are supported funding model platforms 2 | 3 | ko_fi: StylexTV 4 | -------------------------------------------------------------------------------- /gradle/wrapper/gradle-wrapper.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stylextv/maple/HEAD/gradle/wrapper/gradle-wrapper.jar -------------------------------------------------------------------------------- /src/main/resources/assets/maple/icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/stylextv/maple/HEAD/src/main/resources/assets/maple/icon.png -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/math/VectorUtil.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.math; 2 | 3 | public class VectorUtil { 4 | 5 | } 6 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/input/controller/InteractController.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.input.controller; 2 | 3 | public class InteractController { 4 | 5 | } 6 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/PathingState.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing; 2 | 3 | public enum PathingState { 4 | 5 | IDLE, GOING, FAILED, AT_GOAL; 6 | 7 | } 8 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/calc/PathState.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.calc; 2 | 3 | public enum PathState { 4 | 5 | PAUSED, FAILED, FOUND_GOAL; 6 | 7 | } 8 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/Event.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event; 2 | 3 | public abstract class Event { 4 | 5 | public abstract void callListener(EventListener l); 6 | 7 | } 8 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/MovementState.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement; 2 | 3 | public enum MovementState { 4 | 5 | PROCEEDING, DONE, FAILED; 6 | 7 | } 8 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/PathingCommandType.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing; 2 | 3 | public enum PathingCommandType { 4 | 5 | PATH_TO_GOAL, REVALIDATE_GOAL, FORCE_REVALIDATE_GOAL, PAUSE, CANCEL, DEFER; 6 | 7 | } 8 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/time/TimeUtil.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.time; 2 | 3 | public class TimeUtil { 4 | 5 | public static long ticksToMS(double ticks) { 6 | return Math.round(ticks * 50); 7 | } 8 | 9 | } 10 | -------------------------------------------------------------------------------- /gradle/wrapper/gradle-wrapper.properties: -------------------------------------------------------------------------------- 1 | distributionBase=GRADLE_USER_HOME 2 | distributionPath=wrapper/dists 3 | distributionUrl=https\://services.gradle.org/distributions/gradle-7.3.1-bin.zip 4 | zipStoreBase=GRADLE_USER_HOME 5 | zipStorePath=wrapper/dists 6 | -------------------------------------------------------------------------------- /settings.gradle: -------------------------------------------------------------------------------- 1 | pluginManagement { 2 | repositories { 3 | maven { 4 | name = 'Fabric' 5 | url = 'https://maven.fabricmc.net/' 6 | } 7 | mavenCentral() 8 | gradlePluginPortal() 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing 2 | 3 | When contributing to this repository, please first discuss the change you wish to make via issue, 4 | email, or any other method with the owners of this repository before making a change. 5 | 6 | Please note we have a code of conduct, please follow it in all your interactions with the project. 7 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # gradle 2 | 3 | .gradle/ 4 | build/ 5 | out/ 6 | classes/ 7 | 8 | # eclipse 9 | 10 | *.launch 11 | 12 | # idea 13 | 14 | .idea/ 15 | *.iml 16 | *.ipr 17 | *.iws 18 | 19 | # vscode 20 | 21 | .settings/ 22 | .vscode/ 23 | bin/ 24 | .classpath 25 | .project 26 | 27 | # macos 28 | 29 | *.DS_Store 30 | 31 | # fabric 32 | 33 | run/ 34 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/iterate/iterators/types/IntIterator.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.iterate.iterators.types; 2 | 3 | import de.stylextv.maple.util.iterate.FunctionIterator; 4 | 5 | public abstract class IntIterator extends FunctionIterator { 6 | 7 | public IntIterator(int length) { 8 | super(length); 9 | } 10 | 11 | } 12 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/iterate/iterators/types/IntPairIterator.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.iterate.iterators.types; 2 | 3 | import de.stylextv.maple.util.iterate.IntPair; 4 | 5 | public abstract class IntPairIterator extends StaticIterator { 6 | 7 | public IntPairIterator(int length) { 8 | super(length); 9 | } 10 | 11 | } 12 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/iterate/iterators/types/IntTripletIterator.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.iterate.iterators.types; 2 | 3 | import de.stylextv.maple.util.iterate.IntTriplet; 4 | 5 | public abstract class IntTripletIterator extends StaticIterator { 6 | 7 | public IntTripletIterator(int length) { 8 | super(length); 9 | } 10 | 11 | } 12 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/question.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Question 3 | about: Ask a question related to the project 4 | title: '' 5 | labels: question 6 | assignees: StylexTV 7 | 8 | --- 9 | 10 | **What do you need help with?** 11 | A clear and concise description of what your question is about. 12 | 13 | **Additional context** 14 | Add any other context or screenshots about your question here. 15 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/iterate/IntPair.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.iterate; 2 | 3 | public class IntPair { 4 | 5 | private int i; 6 | private int j; 7 | 8 | public IntPair(int i, int j) { 9 | this.i = i; 10 | this.j = j; 11 | } 12 | 13 | public int getFirst() { 14 | return i; 15 | } 16 | 17 | public int getSecond() { 18 | return j; 19 | } 20 | 21 | } 22 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/waypoint/WaypointTag.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.waypoint; 2 | 3 | public enum WaypointTag { 4 | 5 | HOME("Home"), 6 | USER("User"), 7 | BED("Bed"), 8 | DEATH("Death"); 9 | 10 | private String name; 11 | 12 | private WaypointTag(String name) { 13 | this.name = name; 14 | } 15 | 16 | public String getName() { 17 | return name; 18 | } 19 | 20 | } 21 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/events/types/Cancelable.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.events.types; 2 | 3 | import de.stylextv.maple.event.Event; 4 | 5 | public abstract class Cancelable extends Event { 6 | 7 | private boolean canceled; 8 | 9 | public boolean isCanceled() { 10 | return canceled; 11 | } 12 | 13 | public void setCanceled(boolean canceled) { 14 | this.canceled = canceled; 15 | } 16 | 17 | } 18 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/scan/ScanFilter.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.scan; 2 | 3 | import java.util.function.Predicate; 4 | 5 | public class ScanFilter { 6 | 7 | private Predicate predicate; 8 | 9 | public ScanFilter() {} 10 | 11 | public ScanFilter(Predicate predicate) { 12 | this.predicate = predicate; 13 | } 14 | 15 | public boolean matches(T t) { 16 | return predicate.test(t); 17 | } 18 | 19 | } 20 | -------------------------------------------------------------------------------- /gradle.properties: -------------------------------------------------------------------------------- 1 | # Done to increase the memory available to gradle. 2 | org.gradle.jvmargs=-Xmx1G 3 | 4 | # Fabric Properties 5 | # check these on https://fabricmc.net/versions.html 6 | minecraft_version=1.18.1 7 | yarn_mappings=1.18.1+build.12 8 | loader_version=0.12.12 9 | 10 | # Mod Properties 11 | mod_version = 0.1.0+build.10 12 | maven_group = de.stylextv 13 | archives_base_name = maple-fabric 14 | 15 | # Dependencies 16 | fabric_version=0.45.0+1.18 17 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/list/types/LongListSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers.list.types; 2 | 3 | import de.stylextv.maple.io.serialize.Serializer; 4 | import de.stylextv.maple.io.serialize.serializers.list.ListSerializer; 5 | 6 | public class LongListSerializer extends ListSerializer> { 7 | 8 | public LongListSerializer() { 9 | super(Serializer.LONG); 10 | } 11 | 12 | } 13 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/list/types/FloatListSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers.list.types; 2 | 3 | import de.stylextv.maple.io.serialize.Serializer; 4 | import de.stylextv.maple.io.serialize.serializers.list.ListSerializer; 5 | 6 | public class FloatListSerializer extends ListSerializer> { 7 | 8 | public FloatListSerializer() { 9 | super(Serializer.FLOAT); 10 | } 11 | 12 | } 13 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/list/types/ShortListSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers.list.types; 2 | 3 | import de.stylextv.maple.io.serialize.Serializer; 4 | import de.stylextv.maple.io.serialize.serializers.list.ListSerializer; 5 | 6 | public class ShortListSerializer extends ListSerializer> { 7 | 8 | public ShortListSerializer() { 9 | super(Serializer.SHORT); 10 | } 11 | 12 | } 13 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/list/types/DoubleListSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers.list.types; 2 | 3 | import de.stylextv.maple.io.serialize.Serializer; 4 | import de.stylextv.maple.io.serialize.serializers.list.ListSerializer; 5 | 6 | public class DoubleListSerializer extends ListSerializer> { 7 | 8 | public DoubleListSerializer() { 9 | super(Serializer.DOUBLE); 10 | } 11 | 12 | } 13 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/list/types/BooleanListSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers.list.types; 2 | 3 | import de.stylextv.maple.io.serialize.Serializer; 4 | import de.stylextv.maple.io.serialize.serializers.list.ListSerializer; 5 | 6 | public class BooleanListSerializer extends ListSerializer> { 7 | 8 | public BooleanListSerializer() { 9 | super(Serializer.BOOLEAN); 10 | } 11 | 12 | } 13 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/Constants.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple; 2 | 3 | public class Constants { 4 | 5 | public static final String MOD_ID = "maple"; 6 | 7 | public static final String NAME = "Maple"; 8 | 9 | public static final String NAME_COLOR = "§d"; 10 | 11 | public static final String COLORED_NAME = NAME_COLOR + NAME; 12 | 13 | public static final String VERSION = "v0.1.0+build.10"; 14 | 15 | public static final String AUTHOR = "StylexTV"; 16 | 17 | } 18 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/render/mesh/Mesh.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.render.mesh; 2 | 3 | import net.minecraft.util.math.Vec3f; 4 | 5 | public abstract class Mesh { 6 | 7 | private Vec3f[] vertices; 8 | 9 | public abstract void create(); 10 | 11 | public Vec3f[] getVertices() { 12 | if(vertices == null) create(); 13 | 14 | return vertices; 15 | } 16 | 17 | public void setVertices(Vec3f[] vertices) { 18 | this.vertices = vertices; 19 | } 20 | 21 | } 22 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/list/types/UUIDListSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers.list.types; 2 | 3 | import java.util.UUID; 4 | 5 | import de.stylextv.maple.io.serialize.Serializer; 6 | import de.stylextv.maple.io.serialize.serializers.list.ListSerializer; 7 | 8 | public class UUIDListSerializer extends ListSerializer> { 9 | 10 | public UUIDListSerializer() { 11 | super(Serializer.UUID); 12 | } 13 | 14 | } 15 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/iterate/IntTriplet.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.iterate; 2 | 3 | public class IntTriplet { 4 | 5 | private int i; 6 | private int j; 7 | private int k; 8 | 9 | public IntTriplet(int i, int j, int k) { 10 | this.i = i; 11 | this.j = j; 12 | this.k = k; 13 | } 14 | 15 | public int getFirst() { 16 | return i; 17 | } 18 | 19 | public int getSecond() { 20 | return j; 21 | } 22 | 23 | public int getThird() { 24 | return k; 25 | } 26 | 27 | } 28 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/mixin/MinecraftClientInvoker.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.mixin; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | import org.spongepowered.asm.mixin.gen.Invoker; 5 | 6 | import net.minecraft.client.MinecraftClient; 7 | 8 | @Mixin(MinecraftClient.class) 9 | public interface MinecraftClientInvoker { 10 | 11 | @Invoker("handleBlockBreaking") 12 | public void invokeHandleBlockBreaking(boolean b); 13 | 14 | @Invoker("doItemUse") 15 | public void invokeDoItemUse(); 16 | 17 | } 18 | -------------------------------------------------------------------------------- /src/main/resources/maple.mixins.json: -------------------------------------------------------------------------------- 1 | { 2 | "required": true, 3 | "minVersion": "0.8", 4 | "package": "de.stylextv.maple.mixin", 5 | "compatibilityLevel": "JAVA_16", 6 | "mixins": [], 7 | "client": [ 8 | "MinecraftClientMixin", 9 | "MinecraftClientInvoker", 10 | "GameRendererMixin", 11 | "WorldRendererMixin", 12 | "NetworkHandlerMixin", 13 | "ClientConnectionMixin", 14 | "DefaultedListMixin", 15 | "ScreenMixin", 16 | "LivingEntityMixin" 17 | ], 18 | "injectors": { 19 | "defaultRequire": 1 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/context/ClientContext.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.context; 2 | 3 | import net.minecraft.client.MinecraftClient; 4 | 5 | public class ClientContext { 6 | 7 | private static final MinecraftClient CLIENT = MinecraftClient.getInstance(); 8 | 9 | public static boolean isClientSide() { 10 | if(CLIENT.isOnThread()) return true; 11 | 12 | Thread thread = Thread.currentThread(); 13 | 14 | String name = thread.getName().toLowerCase(); 15 | 16 | return name.contains("client"); 17 | } 18 | 19 | } 20 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/scan/ScanFilters.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.scan; 2 | 3 | public class ScanFilters, V> { 4 | 5 | private T[] filters; 6 | 7 | @SafeVarargs 8 | public ScanFilters(T... filters) { 9 | this.filters = filters; 10 | } 11 | 12 | public boolean matches(V v) { 13 | for(T filter : filters) { 14 | 15 | if(!filter.matches(v)) return false; 16 | } 17 | 18 | return true; 19 | } 20 | 21 | public T[] getFilters() { 22 | return filters; 23 | } 24 | 25 | } 26 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/input/InputAction.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.input; 2 | 3 | public enum InputAction { 4 | 5 | MOVE_FORWARD(true), 6 | MOVE_BACK(true), 7 | MOVE_LEFT(true), 8 | MOVE_RIGHT(true), 9 | 10 | JUMP, 11 | 12 | SNEAK, 13 | SPRINT, 14 | 15 | LEFT_CLICK, 16 | RIGHT_CLICK; 17 | 18 | private boolean move; 19 | 20 | private InputAction() { 21 | this(false); 22 | } 23 | 24 | private InputAction(boolean move) { 25 | this.move = move; 26 | } 27 | 28 | public boolean isMove() { 29 | return move; 30 | } 31 | 32 | } 33 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/scheme/Colors.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.scheme; 2 | 3 | public class Colors { 4 | 5 | public static final Color PRIMARY = new Color(251, 84, 251); 6 | 7 | public static final Color PATH = new Color(225, 58, 67); 8 | 9 | public static final Color PATH_CALCULATION = new Color(37, 247, 247); 10 | 11 | public static final Color BEST_PATH_SO_FAR = new Color(51, 58, 224); 12 | 13 | public static final Color GOAL = new Color(83, 255, 73); 14 | 15 | public static final Color WAYPOINT = new Color(224, 58, 224); 16 | 17 | } 18 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/BooleanSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers; 2 | 3 | import de.stylextv.maple.io.resource.StreamedResource; 4 | import de.stylextv.maple.io.serialize.Serializer; 5 | 6 | public class BooleanSerializer extends Serializer { 7 | 8 | @Override 9 | public Boolean readFrom(StreamedResource r) { 10 | byte b = r.read(); 11 | 12 | return b != 0; 13 | } 14 | 15 | @Override 16 | public void writeTo(StreamedResource r, Boolean b) { 17 | r.write((byte) (b ? 1 : 0)); 18 | } 19 | 20 | } 21 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/EventBus.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event; 2 | 3 | import java.util.ArrayList; 4 | import java.util.List; 5 | 6 | import de.stylextv.maple.context.ClientContext; 7 | 8 | public class EventBus { 9 | 10 | private static List listeners = new ArrayList<>(); 11 | 12 | public static void registerListener(EventListener l) { 13 | listeners.add(l); 14 | } 15 | 16 | public static void onEvent(Event event) { 17 | if(!ClientContext.isClientSide()) return; 18 | 19 | listeners.forEach(l -> event.callListener(l)); 20 | } 21 | 22 | } 23 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/events/BlockUpdateEvent.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.events; 2 | 3 | import de.stylextv.maple.event.Event; 4 | import de.stylextv.maple.event.EventListener; 5 | import net.minecraft.util.math.BlockPos; 6 | 7 | public class BlockUpdateEvent extends Event { 8 | 9 | private BlockPos pos; 10 | 11 | public BlockUpdateEvent(BlockPos pos) { 12 | this.pos = pos; 13 | } 14 | 15 | @Override 16 | public void callListener(EventListener l) { 17 | l.onBlockUpdate(this); 18 | } 19 | 20 | public BlockPos getPos() { 21 | return pos; 22 | } 23 | 24 | } 25 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/events/ClientChatEvent.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.events; 2 | 3 | import de.stylextv.maple.event.EventListener; 4 | import de.stylextv.maple.event.events.types.Cancelable; 5 | 6 | public class ClientChatEvent extends Cancelable { 7 | 8 | private String message; 9 | 10 | public ClientChatEvent(String message) { 11 | this.message = message; 12 | } 13 | 14 | @Override 15 | public void callListener(EventListener l) { 16 | l.onClientChat(this); 17 | } 18 | 19 | public String getOriginalMessage() { 20 | return message; 21 | } 22 | 23 | } 24 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/StringSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers; 2 | 3 | import de.stylextv.maple.io.resource.StreamedResource; 4 | import de.stylextv.maple.io.serialize.Serializer; 5 | 6 | public class StringSerializer extends Serializer { 7 | 8 | @Override 9 | public String readFrom(StreamedResource r) { 10 | byte[] data = r.readAll(); 11 | 12 | return new String(data); 13 | } 14 | 15 | @Override 16 | public void writeTo(StreamedResource r, String s) { 17 | byte[] data = s.getBytes(); 18 | 19 | r.write(data); 20 | } 21 | 22 | } 23 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/events/EntityDeathEvent.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.events; 2 | 3 | import de.stylextv.maple.event.Event; 4 | import de.stylextv.maple.event.EventListener; 5 | import net.minecraft.entity.LivingEntity; 6 | 7 | public class EntityDeathEvent extends Event { 8 | 9 | private LivingEntity entity; 10 | 11 | public EntityDeathEvent(LivingEntity entity) { 12 | this.entity = entity; 13 | } 14 | 15 | @Override 16 | public void callListener(EventListener l) { 17 | l.onEntityDeath(this); 18 | } 19 | 20 | public LivingEntity getEntity() { 21 | return entity; 22 | } 23 | 24 | } 25 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/events/EntitySleptEvent.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.events; 2 | 3 | import de.stylextv.maple.event.Event; 4 | import de.stylextv.maple.event.EventListener; 5 | import net.minecraft.entity.LivingEntity; 6 | 7 | public class EntitySleptEvent extends Event { 8 | 9 | private LivingEntity entity; 10 | 11 | public EntitySleptEvent(LivingEntity entity) { 12 | this.entity = entity; 13 | } 14 | 15 | @Override 16 | public void callListener(EventListener l) { 17 | l.onEntitySlept(this); 18 | } 19 | 20 | public LivingEntity getEntity() { 21 | return entity; 22 | } 23 | 24 | } 25 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/scan/block/BlockFilters.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.scan.block; 2 | 3 | import de.stylextv.maple.world.scan.ScanFilters; 4 | import net.minecraft.block.BlockState; 5 | 6 | public class BlockFilters extends ScanFilters { 7 | 8 | public BlockFilters(BlockFilter... filters) { 9 | super(filters); 10 | } 11 | 12 | public static BlockFilters fromFilter(BlockFilter filter) { 13 | return new BlockFilters(filter); 14 | } 15 | 16 | public static BlockFilters fromFilters(BlockFilter... filters) { 17 | return new BlockFilters(filters); 18 | } 19 | 20 | } 21 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/scan/entity/EntityFilters.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.scan.entity; 2 | 3 | import de.stylextv.maple.world.scan.ScanFilters; 4 | import net.minecraft.entity.Entity; 5 | 6 | public class EntityFilters extends ScanFilters { 7 | 8 | public EntityFilters(EntityFilter... filters) { 9 | super(filters); 10 | } 11 | 12 | public static EntityFilters fromFilter(EntityFilter filter) { 13 | return new EntityFilters(filter); 14 | } 15 | 16 | public static EntityFilters fromFilters(EntityFilter... filters) { 17 | return new EntityFilters(filters); 18 | } 19 | 20 | } 21 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/cache/block/matchers/UnbreakableBlockMatcher.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.cache.block.matchers; 2 | 3 | import de.stylextv.maple.cache.block.BlockMatcher; 4 | import de.stylextv.maple.cache.block.BlockType; 5 | import net.minecraft.block.Block; 6 | import net.minecraft.block.InfestedBlock; 7 | 8 | public class UnbreakableBlockMatcher extends BlockMatcher { 9 | 10 | @Override 11 | public BlockType match(Block block) { 12 | boolean isUnbreakable = block.getHardness() < 0; 13 | 14 | if(isUnbreakable || block instanceof InfestedBlock) return BlockType.UNBREAKABLE; 15 | 16 | return null; 17 | } 18 | 19 | } 20 | -------------------------------------------------------------------------------- /.github/PULL_REQUEST_TEMPLATE.md: -------------------------------------------------------------------------------- 1 | ## Types of changes 2 | 3 | - [ ] Bug fix (non-breaking change which fixes an issue) 4 | - [ ] New feature (non-breaking change which adds functionality) 5 | - [ ] Breaking change (fix or feature that would cause existing functionality to change) 6 | - [ ] I have read the **CONTRIBUTING** document. 7 | - [ ] My code follows the code style of this project. 8 | - [ ] My change requires a change to the documentation. 9 | - [ ] I have updated the documentation accordingly. 10 | - [ ] I have added tests to cover my changes. 11 | - [ ] All new and existing tests passed. 12 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/suggestion.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Suggestion 3 | about: Suggest an idea for this project 4 | title: '' 5 | labels: enhancement 6 | assignees: StylexTV 7 | 8 | --- 9 | 10 | **Describe your suggestion** 11 | A clear and concise description of what should happen and what should be added to Maple. 12 | 13 | **Customizability** 14 | If applicable, what settings/customizability should be offered to tweak the functionality of your suggestion. 15 | 16 | **Describe alternatives you've considered** 17 | A clear and concise description of any alternative solutions or features you've considered. 18 | 19 | **Additional context** 20 | Add any other context or screenshots about the suggestion here. 21 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/schematic/schematics/FillSchematic.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.schematic.schematics; 2 | 3 | import de.stylextv.maple.schematic.Schematic; 4 | import net.minecraft.block.Block; 5 | import net.minecraft.block.BlockState; 6 | 7 | public class FillSchematic extends Schematic { 8 | 9 | private Block block; 10 | 11 | public FillSchematic(int width, int height, int length, Block block) { 12 | super(width, height, length); 13 | 14 | this.block = block; 15 | } 16 | 17 | @Override 18 | public Block getBlock(int x, int y, int z, BlockState state) { 19 | return block; 20 | } 21 | 22 | public Block getBlock() { 23 | return block; 24 | } 25 | 26 | } 27 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/scan/entity/filters/EntityTypeFilter.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.scan.entity.filters; 2 | 3 | import de.stylextv.maple.world.scan.entity.EntityFilter; 4 | import net.minecraft.entity.Entity; 5 | import net.minecraft.entity.EntityType; 6 | 7 | public class EntityTypeFilter extends EntityFilter { 8 | 9 | private EntityType type; 10 | 11 | public EntityTypeFilter(EntityType type) { 12 | this.type = type; 13 | } 14 | 15 | @Override 16 | public boolean matches(Entity e) { 17 | EntityType t = e.getType(); 18 | 19 | return t.equals(type); 20 | } 21 | 22 | public EntityType getType() { 23 | return type; 24 | } 25 | 26 | } 27 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/events/InventoryUpdateEvent.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.events; 2 | import de.stylextv.maple.event.Event; 3 | import de.stylextv.maple.event.EventListener; 4 | import net.minecraft.item.ItemStack; 5 | import net.minecraft.util.collection.DefaultedList; 6 | 7 | public class InventoryUpdateEvent extends Event { 8 | 9 | private DefaultedList list; 10 | 11 | public InventoryUpdateEvent(DefaultedList list) { 12 | this.list = list; 13 | } 14 | 15 | public DefaultedList getList() { 16 | return list; 17 | } 18 | 19 | @Override 20 | public void callListener(EventListener l) { 21 | l.onInventoryUpdate(this); 22 | } 23 | 24 | } 25 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/WorldBorderInterface.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world; 2 | 3 | import de.stylextv.maple.context.WorldContext; 4 | import net.minecraft.util.math.BlockPos; 5 | import net.minecraft.world.border.WorldBorder; 6 | 7 | public class WorldBorderInterface { 8 | 9 | public static boolean isInside(BlockPos pos) { 10 | return isInside(pos.getX(), pos.getZ()); 11 | } 12 | 13 | // TODO don't use native methods (too slow)! 14 | public static boolean isInside(int x, int z) { 15 | WorldBorder border = getBorder(); 16 | 17 | return border.contains(x, z); 18 | } 19 | 20 | public static WorldBorder getBorder() { 21 | return WorldContext.world().getWorldBorder(); 22 | } 23 | 24 | } 25 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/VersionCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.Constants; 4 | import de.stylextv.maple.command.ArgumentList; 5 | import de.stylextv.maple.command.Command; 6 | import de.stylextv.maple.util.chat.ChatUtil; 7 | 8 | public class VersionCommand extends Command { 9 | 10 | public VersionCommand() { 11 | super("version", "Shows the installed version of Maple.", "ver", "v"); 12 | } 13 | 14 | @Override 15 | public boolean execute(ArgumentList args) { 16 | String s = Constants.COLORED_NAME + " " + Constants.VERSION + " §7by §e" + Constants.AUTHOR; 17 | 18 | ChatUtil.send("Installed: " + s); 19 | 20 | return true; 21 | } 22 | 23 | } 24 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/listeners/ChatListener.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.listeners; 2 | 3 | import de.stylextv.maple.command.CommandManager; 4 | import de.stylextv.maple.context.GameContext; 5 | import de.stylextv.maple.event.EventListener; 6 | import de.stylextv.maple.event.events.ClientChatEvent; 7 | 8 | public class ChatListener implements EventListener { 9 | 10 | @Override 11 | public void onClientChat(ClientChatEvent event) { 12 | String msg = event.getOriginalMessage(); 13 | 14 | if(CommandManager.isCommandMessage(msg)) { 15 | event.setCanceled(true); 16 | 17 | GameContext.chatHud().addToMessageHistory(msg); 18 | 19 | CommandManager.parseMessage(msg); 20 | } 21 | } 22 | 23 | } 24 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/schematic/schematics/StaticSchematic.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.schematic.schematics; 2 | 3 | import de.stylextv.maple.schematic.Schematic; 4 | import net.minecraft.block.Block; 5 | import net.minecraft.block.BlockState; 6 | 7 | public class StaticSchematic extends Schematic { 8 | 9 | private Block[][][] blocks; 10 | 11 | public StaticSchematic(int width, int height, int length, Block[][][] blocks) { 12 | super(width, height, length); 13 | 14 | this.blocks = blocks; 15 | } 16 | 17 | @Override 18 | public Block getBlock(int x, int y, int z, BlockState state) { 19 | return blocks[x][y][z]; 20 | } 21 | 22 | public Block[][][] getBlocks() { 23 | return blocks; 24 | } 25 | 26 | } 27 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/schematic/Schematic.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.schematic; 2 | 3 | import net.minecraft.block.Block; 4 | import net.minecraft.block.BlockState; 5 | 6 | public abstract class Schematic { 7 | 8 | private int width; 9 | private int height; 10 | private int length; 11 | 12 | public Schematic(int width, int height, int length) { 13 | this.width = width; 14 | this.height = height; 15 | this.length = length; 16 | } 17 | 18 | public abstract Block getBlock(int x, int y, int z, BlockState state); 19 | 20 | public int getWidth() { 21 | return width; 22 | } 23 | 24 | public int getHeight() { 25 | return height; 26 | } 27 | 28 | public int getLength() { 29 | return length; 30 | } 31 | 32 | } 33 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/task/tasks/MineTask.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.task.tasks; 2 | 3 | import de.stylextv.maple.util.chat.ChatUtil; 4 | import de.stylextv.maple.world.scan.block.BlockFilter; 5 | import de.stylextv.maple.world.scan.block.BlockFilters; 6 | 7 | public class MineTask extends BreakTask { 8 | 9 | public MineTask(BlockFilter filter) { 10 | this(BlockFilters.fromFilter(filter)); 11 | } 12 | 13 | public MineTask(BlockFilters filters) { 14 | super(filters); 15 | } 16 | 17 | @Override 18 | public void onFail() { 19 | ChatUtil.send("Can't get any closer to blocks."); 20 | } 21 | 22 | @Override 23 | public void onEmptyGoal() { 24 | ChatUtil.send("Can't find any matching blocks nearby."); 25 | } 26 | 27 | } 28 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/scan/entity/filters/EntityNameFilter.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.scan.entity.filters; 2 | 3 | import de.stylextv.maple.world.scan.entity.EntityFilter; 4 | import net.minecraft.entity.Entity; 5 | import net.minecraft.text.Text; 6 | 7 | public class EntityNameFilter extends EntityFilter { 8 | 9 | private String name; 10 | 11 | public EntityNameFilter(String name) { 12 | this.name = name; 13 | } 14 | 15 | @Override 16 | public boolean matches(Entity e) { 17 | Text text = e.getCustomName(); 18 | 19 | if(text == null) return false; 20 | 21 | String s = text.asString(); 22 | 23 | return s.equals(name); 24 | } 25 | 26 | public String getName() { 27 | return name; 28 | } 29 | 30 | } 31 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/events/TickEvent.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.events; 2 | 3 | import de.stylextv.maple.event.Event; 4 | import de.stylextv.maple.event.EventListener; 5 | 6 | public class TickEvent extends Event { 7 | 8 | private Type type; 9 | 10 | public TickEvent(Type type) { 11 | this.type = type; 12 | } 13 | 14 | @Override 15 | public void callListener(EventListener l) { 16 | if(type == Type.CLIENT) { 17 | 18 | l.onClientTick(this); 19 | 20 | return; 21 | } 22 | 23 | if(type == Type.RENDER) { 24 | 25 | l.onRenderTick(this); 26 | } 27 | } 28 | 29 | public Type getType() { 30 | return type; 31 | } 32 | 33 | public enum Type { 34 | 35 | CLIENT, RENDER; 36 | 37 | } 38 | 39 | } 40 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/PauseCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.command.Command; 5 | import de.stylextv.maple.task.TaskManager; 6 | import de.stylextv.maple.util.chat.ChatUtil; 7 | 8 | public class PauseCommand extends Command { 9 | 10 | public PauseCommand() { 11 | super("pause", "Pauses the current task."); 12 | } 13 | 14 | @Override 15 | public boolean execute(ArgumentList args) { 16 | if(!TaskManager.hasTask()) { 17 | 18 | ChatUtil.send("§cNo task present!"); 19 | 20 | return true; 21 | } 22 | 23 | TaskManager.pauseTask(); 24 | 25 | ChatUtil.send("Paused."); 26 | 27 | return true; 28 | } 29 | 30 | } 31 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/StopCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.command.Command; 5 | import de.stylextv.maple.task.TaskManager; 6 | import de.stylextv.maple.util.chat.ChatUtil; 7 | 8 | public class StopCommand extends Command { 9 | 10 | public StopCommand() { 11 | super("stop", "Stops the current task.", "cancel"); 12 | } 13 | 14 | @Override 15 | public boolean execute(ArgumentList args) { 16 | if(!TaskManager.hasTask()) { 17 | 18 | ChatUtil.send("§cNo task present!"); 19 | 20 | return true; 21 | } 22 | 23 | TaskManager.stopTask(); 24 | 25 | ChatUtil.send("Stopped."); 26 | 27 | return true; 28 | } 29 | 30 | } 31 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/moves/AscendMove.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.moves; 2 | 3 | import de.stylextv.maple.pathing.calc.Node; 4 | import de.stylextv.maple.pathing.calc.PathFinder; 5 | import de.stylextv.maple.pathing.movement.Move; 6 | import de.stylextv.maple.pathing.movement.Movement; 7 | import de.stylextv.maple.pathing.movement.movements.AscendMovement; 8 | 9 | public class AscendMove extends Move { 10 | 11 | public AscendMove(int x, int y, int z) { 12 | super(x, y, z); 13 | } 14 | 15 | @Override 16 | public Movement apply(Node n, PathFinder finder) { 17 | Node destination = finder.getAdjacentNode(n, getDeltaX(), getDeltaY(), getDeltaZ()); 18 | 19 | return new AscendMovement(n, destination); 20 | } 21 | 22 | } 23 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/moves/PillarMove.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.moves; 2 | 3 | import de.stylextv.maple.pathing.calc.Node; 4 | import de.stylextv.maple.pathing.calc.PathFinder; 5 | import de.stylextv.maple.pathing.movement.Move; 6 | import de.stylextv.maple.pathing.movement.Movement; 7 | import de.stylextv.maple.pathing.movement.movements.PillarMovement; 8 | 9 | public class PillarMove extends Move { 10 | 11 | public PillarMove(int x, int y, int z) { 12 | super(x, y, z); 13 | } 14 | 15 | @Override 16 | public Movement apply(Node n, PathFinder finder) { 17 | Node destination = finder.getAdjacentNode(n, getDeltaX(), getDeltaY(), getDeltaZ()); 18 | 19 | return new PillarMovement(n, destination); 20 | } 21 | 22 | } 23 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/time/TimeFormat.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.time; 2 | 3 | import java.util.Date; 4 | 5 | public class TimeFormat { 6 | 7 | public static String formatDate(long time) { 8 | return new Date(time).toString(); 9 | } 10 | 11 | public static String formatDuration(long time) { 12 | String s = null; 13 | 14 | while(time != 0 || s == null) { 15 | 16 | TimeUnit u = TimeUnit.getUnit(time); 17 | 18 | long amount = u.getAmount(time); 19 | 20 | time -= amount * u.getDuration(); 21 | 22 | String s2 = amount + " " + u.getName(amount); 23 | 24 | if(s != null) { 25 | s += " and " + s2; 26 | 27 | break; 28 | } 29 | 30 | s = s2; 31 | } 32 | 33 | return s; 34 | } 35 | 36 | } 37 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/scan/block/filters/BlockTypeFilter.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.scan.block.filters; 2 | 3 | import de.stylextv.maple.world.scan.block.BlockFilter; 4 | import net.minecraft.block.Block; 5 | import net.minecraft.block.BlockState; 6 | 7 | public class BlockTypeFilter extends BlockFilter { 8 | 9 | private Block[] blocks; 10 | 11 | public BlockTypeFilter(Block... blocks) { 12 | this.blocks = blocks; 13 | } 14 | 15 | @Override 16 | public boolean matches(BlockState state) { 17 | Block block = state.getBlock(); 18 | 19 | for(Block b : blocks) { 20 | 21 | if(block.equals(b)) return true; 22 | } 23 | 24 | return false; 25 | } 26 | 27 | public Block[] getBlocks() { 28 | return blocks; 29 | } 30 | 31 | } 32 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/ResumeCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.command.Command; 5 | import de.stylextv.maple.task.TaskManager; 6 | import de.stylextv.maple.util.chat.ChatUtil; 7 | 8 | public class ResumeCommand extends Command { 9 | 10 | public ResumeCommand() { 11 | super("resume", "Resumes the current task."); 12 | } 13 | 14 | @Override 15 | public boolean execute(ArgumentList args) { 16 | if(!TaskManager.hasTask()) { 17 | 18 | ChatUtil.send("§cNo task present!"); 19 | 20 | return true; 21 | } 22 | 23 | TaskManager.resumeTask(); 24 | 25 | ChatUtil.send("Resumed."); 26 | 27 | return true; 28 | } 29 | 30 | } 31 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/FarmCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.command.Command; 5 | import de.stylextv.maple.task.Task; 6 | import de.stylextv.maple.task.TaskManager; 7 | import de.stylextv.maple.task.tasks.FarmTask; 8 | import de.stylextv.maple.util.chat.ChatUtil; 9 | 10 | public class FarmCommand extends Command { 11 | 12 | public FarmCommand() { 13 | super("farm", "Starts harvesting nearby crops."); 14 | } 15 | 16 | @Override 17 | public boolean execute(ArgumentList args) { 18 | Task task = new FarmTask(); 19 | 20 | TaskManager.startTask(task); 21 | 22 | ChatUtil.send("Started farming."); 23 | 24 | return true; 25 | } 26 | 27 | } 28 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/mixin/GameRendererMixin.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.mixin; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | import org.spongepowered.asm.mixin.injection.At; 5 | import org.spongepowered.asm.mixin.injection.Inject; 6 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 7 | 8 | import de.stylextv.maple.event.EventBus; 9 | import de.stylextv.maple.event.events.TickEvent; 10 | import net.minecraft.client.render.GameRenderer; 11 | 12 | @Mixin(GameRenderer.class) 13 | public class GameRendererMixin { 14 | 15 | @Inject(method = "render(FJZ)V", at = @At("HEAD")) 16 | private void render(float tickDelta, long startTime, boolean tick, CallbackInfo info) { 17 | EventBus.onEvent(new TickEvent(TickEvent.Type.RENDER)); 18 | } 19 | 20 | } 21 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/moves/DiagonalMove.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.moves; 2 | 3 | import de.stylextv.maple.pathing.calc.Node; 4 | import de.stylextv.maple.pathing.calc.PathFinder; 5 | import de.stylextv.maple.pathing.movement.Move; 6 | import de.stylextv.maple.pathing.movement.Movement; 7 | import de.stylextv.maple.pathing.movement.movements.DiagonalMovement; 8 | 9 | public class DiagonalMove extends Move { 10 | 11 | public DiagonalMove(int x, int y, int z) { 12 | super(x, y, z); 13 | } 14 | 15 | @Override 16 | public Movement apply(Node n, PathFinder finder) { 17 | Node destination = finder.getAdjacentNode(n, getDeltaX(), getDeltaY(), getDeltaZ()); 18 | 19 | return new DiagonalMovement(n, destination); 20 | } 21 | 22 | } 23 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/moves/StraightMove.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.moves; 2 | 3 | import de.stylextv.maple.pathing.calc.Node; 4 | import de.stylextv.maple.pathing.calc.PathFinder; 5 | import de.stylextv.maple.pathing.movement.Move; 6 | import de.stylextv.maple.pathing.movement.Movement; 7 | import de.stylextv.maple.pathing.movement.movements.StraightMovement; 8 | 9 | public class StraightMove extends Move { 10 | 11 | public StraightMove(int x, int y, int z) { 12 | super(x, y, z); 13 | } 14 | 15 | @Override 16 | public Movement apply(Node n, PathFinder finder) { 17 | Node destination = finder.getAdjacentNode(n, getDeltaX(), getDeltaY(), getDeltaZ()); 18 | 19 | return new StraightMovement(n, destination); 20 | } 21 | 22 | } 23 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/AxisCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.command.Command; 5 | import de.stylextv.maple.pathing.calc.goal.AxisGoal; 6 | import de.stylextv.maple.pathing.calc.goal.Goal; 7 | import de.stylextv.maple.task.TaskManager; 8 | import de.stylextv.maple.util.chat.ChatUtil; 9 | 10 | public class AxisCommand extends Command { 11 | 12 | public AxisCommand() { 13 | super("axis", "Travel to the nearest axis."); 14 | } 15 | 16 | @Override 17 | public boolean execute(ArgumentList args) { 18 | Goal goal = new AxisGoal(); 19 | 20 | TaskManager.gotoGoal(goal); 21 | 22 | ChatUtil.send("Started."); 23 | 24 | return true; 25 | } 26 | 27 | } 28 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/ExceptionUtil.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util; 2 | 3 | public class ExceptionUtil { 4 | 5 | public static void catchEverything(Runnable r) { 6 | catchEverything(r, true); 7 | } 8 | 9 | public static void catchEverything(Runnable r, boolean print) { 10 | catchEverything(r, null, print); 11 | } 12 | 13 | public static void catchEverything(Runnable r, Runnable catchCallback) { 14 | catchEverything(r, catchCallback, false); 15 | } 16 | 17 | public static void catchEverything(Runnable r, Runnable catchCallback, boolean print) { 18 | try { 19 | 20 | r.run(); 21 | 22 | } catch(Exception ex) { 23 | 24 | if(catchCallback != null) catchCallback.run(); 25 | 26 | if(print) ex.printStackTrace(); 27 | } 28 | } 29 | 30 | } 31 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/BitSetSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers; 2 | 3 | import java.util.BitSet; 4 | 5 | import de.stylextv.maple.io.resource.StreamedResource; 6 | import de.stylextv.maple.io.serialize.Serializer; 7 | 8 | public class BitSetSerializer extends Serializer { 9 | 10 | @Override 11 | public BitSet readFrom(StreamedResource r) { 12 | int l = Serializer.INTEGER.readFrom(r); 13 | 14 | byte[] data = r.read(l); 15 | 16 | return BitSet.valueOf(data); 17 | } 18 | 19 | @Override 20 | public void writeTo(StreamedResource r, BitSet bitSet) { 21 | byte[] data = bitSet.toByteArray(); 22 | 23 | int l = data.length; 24 | 25 | Serializer.INTEGER.writeTo(r, l); 26 | 27 | r.write(data); 28 | } 29 | 30 | } 31 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/UUIDSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers; 2 | 3 | import java.util.UUID; 4 | 5 | import de.stylextv.maple.io.resource.StreamedResource; 6 | import de.stylextv.maple.io.serialize.Serializer; 7 | 8 | public class UUIDSerializer extends Serializer { 9 | 10 | @Override 11 | public UUID readFrom(StreamedResource r) { 12 | long l1 = Serializer.LONG.readFrom(r); 13 | long l2 = Serializer.LONG.readFrom(r); 14 | 15 | return new UUID(l1, l2); 16 | } 17 | 18 | @Override 19 | public void writeTo(StreamedResource r, UUID id) { 20 | long l1 = id.getMostSignificantBits(); 21 | long l2 = id.getLeastSignificantBits(); 22 | 23 | Serializer.LONG.writeTo(r, l1); 24 | Serializer.LONG.writeTo(r, l2); 25 | } 26 | 27 | } 28 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/events/ChunkEvent.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.events; 2 | 3 | import de.stylextv.maple.event.Event; 4 | import de.stylextv.maple.event.EventListener; 5 | 6 | public class ChunkEvent extends Event { 7 | 8 | private Type type; 9 | 10 | private int x; 11 | private int z; 12 | 13 | public ChunkEvent(Type type, int x, int z) { 14 | this.type = type; 15 | this.x = x; 16 | this.z = z; 17 | } 18 | 19 | @Override 20 | public void callListener(EventListener l) { 21 | if(type == Type.DATA) l.onChunkData(this); 22 | } 23 | 24 | public Type getType() { 25 | return type; 26 | } 27 | 28 | public int getX() { 29 | return x; 30 | } 31 | 32 | public int getZ() { 33 | return z; 34 | } 35 | 36 | public enum Type { 37 | 38 | DATA; 39 | 40 | } 41 | 42 | } 43 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/interact/openables/OpenableFenceGate.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.interact.openables; 2 | 3 | import de.stylextv.maple.pathing.movement.Movement; 4 | import de.stylextv.maple.world.interact.Openable; 5 | import net.minecraft.block.Block; 6 | import net.minecraft.block.BlockState; 7 | import net.minecraft.block.FenceGateBlock; 8 | 9 | public class OpenableFenceGate extends Openable { 10 | 11 | @Override 12 | public boolean matchesBlock(Block block) { 13 | return block instanceof FenceGateBlock; 14 | } 15 | 16 | @Override 17 | public boolean isLocked(BlockState block) { 18 | return false; 19 | } 20 | 21 | @Override 22 | public boolean isOpen(BlockState state, Movement m) { 23 | boolean open = state.get(FenceGateBlock.OPEN); 24 | 25 | return open; 26 | } 27 | 28 | } 29 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/BlockInterface.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world; 2 | 3 | import de.stylextv.maple.cache.CacheManager; 4 | import de.stylextv.maple.cache.block.BlockType; 5 | import de.stylextv.maple.context.WorldContext; 6 | import net.minecraft.block.BlockState; 7 | import net.minecraft.util.math.BlockPos; 8 | 9 | public class BlockInterface { 10 | 11 | public static BlockState getState(int x, int y, int z) { 12 | return getState(new BlockPos(x, y, z)); 13 | } 14 | 15 | public static BlockState getState(BlockPos pos) { 16 | boolean loaded = WorldBorderInterface.isInside(pos) && WorldContext.isPosFullyLoaded(pos); 17 | 18 | if(loaded) return WorldContext.getBlockState(pos); 19 | 20 | BlockType type = CacheManager.getBlockType(pos); 21 | 22 | return type.getState(); 23 | } 24 | 25 | } 26 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/iterate/iterators/RangeIterator.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.iterate.iterators; 2 | 3 | import de.stylextv.maple.util.iterate.iterators.types.IntIterator; 4 | 5 | public class RangeIterator extends IntIterator { 6 | 7 | public static final RangeIterator ZERO_TO_SIXTEEN = new RangeIterator(16); 8 | 9 | private int from; 10 | private int to; 11 | 12 | public RangeIterator(int length) { 13 | this(0, length - 1); 14 | } 15 | 16 | public RangeIterator(int from, int to) { 17 | super(to - from + 1); 18 | 19 | this.from = from; 20 | this.to = to; 21 | } 22 | 23 | @Override 24 | public Integer get(int index) { 25 | return from + index; 26 | } 27 | 28 | public int getFrom() { 29 | return from; 30 | } 31 | 32 | public int getTo() { 33 | return to; 34 | } 35 | 36 | } 37 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/cache/block/matchers/BlockadeBlockMatcher.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.cache.block.matchers; 2 | 3 | import de.stylextv.maple.cache.block.BlockMatcher; 4 | import de.stylextv.maple.cache.block.BlockType; 5 | import net.minecraft.block.Block; 6 | import net.minecraft.block.BlockState; 7 | import net.minecraft.block.FenceBlock; 8 | import net.minecraft.block.WallBlock; 9 | 10 | public class BlockadeBlockMatcher extends BlockMatcher { 11 | 12 | @Override 13 | public BlockType match(BlockState state, BlockState above, BlockState below) { 14 | Block block = below.getBlock(); 15 | 16 | boolean aboveFence = block instanceof FenceBlock; 17 | boolean aboveWall = block instanceof WallBlock; 18 | 19 | if(aboveFence || aboveWall) return BlockType.UNBREAKABLE; 20 | 21 | return null; 22 | } 23 | 24 | } 25 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/iterate/FunctionIterator.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.iterate; 2 | 3 | import java.util.Iterator; 4 | 5 | public abstract class FunctionIterator implements Iterable { 6 | 7 | private int length; 8 | 9 | public FunctionIterator(int length) { 10 | this.length = length; 11 | } 12 | 13 | public abstract T get(int index); 14 | 15 | @Override 16 | public Iterator iterator() { 17 | return new Iterator() { 18 | 19 | private int index; 20 | 21 | @Override 22 | public boolean hasNext() { 23 | return index < length; 24 | } 25 | 26 | @Override 27 | public T next() { 28 | T t = get(index); 29 | 30 | index++; 31 | 32 | return t; 33 | } 34 | 35 | }; 36 | } 37 | 38 | public int getLength() { 39 | return length; 40 | } 41 | 42 | } 43 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/cache/block/matchers/DangerBlockMatcher.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.cache.block.matchers; 2 | 3 | import de.stylextv.maple.cache.block.BlockMatcher; 4 | import de.stylextv.maple.cache.block.BlockType; 5 | import net.minecraft.block.Block; 6 | import net.minecraft.block.Blocks; 7 | 8 | public class DangerBlockMatcher extends BlockMatcher { 9 | 10 | private static final Block[] BLOCKS = new Block[] { 11 | Blocks.LAVA, 12 | Blocks.FIRE, 13 | Blocks.SOUL_FIRE, 14 | Blocks.CAMPFIRE, 15 | Blocks.SOUL_CAMPFIRE, 16 | Blocks.CACTUS, 17 | Blocks.SWEET_BERRY_BUSH, 18 | Blocks.POWDER_SNOW, 19 | Blocks.BUBBLE_COLUMN 20 | }; 21 | 22 | @Override 23 | public BlockType match(Block block) { 24 | for(Block b : BLOCKS) { 25 | if(block.equals(b)) return BlockType.DANGER; 26 | } 27 | 28 | return null; 29 | } 30 | 31 | } 32 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/LongSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers; 2 | 3 | import java.nio.ByteBuffer; 4 | 5 | import de.stylextv.maple.io.resource.StreamedResource; 6 | import de.stylextv.maple.io.serialize.Serializer; 7 | 8 | public class LongSerializer extends Serializer { 9 | 10 | private static final int SIZE_IN_BYTES = 8; 11 | 12 | @Override 13 | public Long readFrom(StreamedResource r) { 14 | byte[] data = r.read(SIZE_IN_BYTES); 15 | 16 | ByteBuffer buffer = ByteBuffer.wrap(data); 17 | 18 | return buffer.getLong(); 19 | } 20 | 21 | @Override 22 | public void writeTo(StreamedResource r, Long l) { 23 | ByteBuffer buffer = ByteBuffer.allocate(SIZE_IN_BYTES); 24 | 25 | buffer.putLong(l); 26 | 27 | byte[] data = buffer.array(); 28 | 29 | r.write(data); 30 | } 31 | 32 | } 33 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/cache/io/file/CachedRegionFile.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.cache.io.file; 2 | 3 | import java.io.File; 4 | 5 | import de.stylextv.maple.cache.CachedChunk; 6 | import de.stylextv.maple.cache.CachedRegion; 7 | import de.stylextv.maple.io.resource.types.StreamedFile; 8 | import de.stylextv.maple.io.serialize.Serializer; 9 | 10 | public class CachedRegionFile extends StreamedFile { 11 | 12 | public CachedRegionFile(File f) { 13 | super(f); 14 | } 15 | 16 | // TODO rework 17 | public void readRegion(CachedRegion r) { 18 | while(!isEmpty()) { 19 | 20 | CachedChunk c = Serializer.CACHED_CHUNK.readFrom(this); 21 | 22 | r.addChunk(c); 23 | } 24 | } 25 | 26 | public void writeRegion(CachedRegion r) { 27 | for(CachedChunk c : r.chunks()) { 28 | 29 | Serializer.CACHED_CHUNK.writeTo(this, c); 30 | } 31 | } 32 | 33 | } 34 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/events/RenderWorldEvent.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.events; 2 | 3 | import de.stylextv.maple.event.Event; 4 | import de.stylextv.maple.event.EventListener; 5 | import net.minecraft.client.util.math.MatrixStack; 6 | 7 | public class RenderWorldEvent extends Event { 8 | 9 | private Type type; 10 | 11 | private MatrixStack matrixStack; 12 | 13 | public RenderWorldEvent(Type type, MatrixStack stack) { 14 | this.type = type; 15 | this.matrixStack = stack; 16 | } 17 | 18 | @Override 19 | public void callListener(EventListener l) { 20 | if(type == Type.ENTITIES) l.onEntitiesRender(this); 21 | } 22 | 23 | public Type getType() { 24 | return type; 25 | } 26 | 27 | public MatrixStack getMatrixStack() { 28 | return matrixStack; 29 | } 30 | 31 | public enum Type { 32 | 33 | ENTITIES; 34 | 35 | } 36 | 37 | } 38 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/RegistryUtil.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util; 2 | 3 | import java.util.Optional; 4 | 5 | import net.minecraft.block.Block; 6 | import net.minecraft.entity.EntityType; 7 | import net.minecraft.util.Identifier; 8 | import net.minecraft.util.registry.Registry; 9 | 10 | public class RegistryUtil { 11 | 12 | public static Block getBlock(String id) { 13 | Identifier i = idFromString(id); 14 | 15 | Optional o = Registry.BLOCK.getOrEmpty(i); 16 | 17 | return o.orElse(null); 18 | } 19 | 20 | public static EntityType getEntityType(String id) { 21 | Identifier i = idFromString(id); 22 | 23 | Optional> o = Registry.ENTITY_TYPE.getOrEmpty(i); 24 | 25 | return o.orElse(null); 26 | } 27 | 28 | private static Identifier idFromString(String s) { 29 | return Identifier.tryParse(s); 30 | } 31 | 32 | } 33 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/FloatSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers; 2 | 3 | import java.nio.ByteBuffer; 4 | 5 | import de.stylextv.maple.io.resource.StreamedResource; 6 | import de.stylextv.maple.io.serialize.Serializer; 7 | 8 | public class FloatSerializer extends Serializer { 9 | 10 | private static final int SIZE_IN_BYTES = 4; 11 | 12 | @Override 13 | public Float readFrom(StreamedResource r) { 14 | byte[] data = r.read(SIZE_IN_BYTES); 15 | 16 | ByteBuffer buffer = ByteBuffer.wrap(data); 17 | 18 | return buffer.getFloat(); 19 | } 20 | 21 | @Override 22 | public void writeTo(StreamedResource r, Float f) { 23 | ByteBuffer buffer = ByteBuffer.allocate(SIZE_IN_BYTES); 24 | 25 | buffer.putFloat(f); 26 | 27 | byte[] data = buffer.array(); 28 | 29 | r.write(data); 30 | } 31 | 32 | } 33 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/ShortSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers; 2 | 3 | import java.nio.ByteBuffer; 4 | 5 | import de.stylextv.maple.io.resource.StreamedResource; 6 | import de.stylextv.maple.io.serialize.Serializer; 7 | 8 | public class ShortSerializer extends Serializer { 9 | 10 | private static final int SIZE_IN_BYTES = 2; 11 | 12 | @Override 13 | public Short readFrom(StreamedResource r) { 14 | byte[] data = r.read(SIZE_IN_BYTES); 15 | 16 | ByteBuffer buffer = ByteBuffer.wrap(data); 17 | 18 | return buffer.getShort(); 19 | } 20 | 21 | @Override 22 | public void writeTo(StreamedResource r, Short s) { 23 | ByteBuffer buffer = ByteBuffer.allocate(SIZE_IN_BYTES); 24 | 25 | buffer.putShort(s); 26 | 27 | byte[] data = buffer.array(); 28 | 29 | r.write(data); 30 | } 31 | 32 | } 33 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/mixin/ScreenMixin.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.mixin; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | import org.spongepowered.asm.mixin.injection.At; 5 | import org.spongepowered.asm.mixin.injection.Inject; 6 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 7 | 8 | import de.stylextv.maple.event.EventBus; 9 | import de.stylextv.maple.event.events.ClientChatEvent; 10 | import net.minecraft.client.gui.screen.Screen; 11 | 12 | @Mixin(Screen.class) 13 | public class ScreenMixin { 14 | 15 | @Inject(method = "sendMessage(Ljava/lang/String;Z)V", at = @At("HEAD"), cancellable = true) 16 | private void sendMessage(String message, boolean toHud, CallbackInfo info) { 17 | ClientChatEvent event = new ClientChatEvent(message); 18 | 19 | EventBus.onEvent(event); 20 | 21 | if(event.isCanceled()) info.cancel(); 22 | } 23 | 24 | } 25 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/LostCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.command.Command; 5 | import de.stylextv.maple.util.chat.ChatUtil; 6 | import de.stylextv.maple.waypoint.Waypoint; 7 | import de.stylextv.maple.waypoint.WaypointTag; 8 | import de.stylextv.maple.waypoint.Waypoints; 9 | 10 | public class LostCommand extends Command { 11 | 12 | public LostCommand() { 13 | super("lost", "Travel to the nearest waypoint."); 14 | } 15 | 16 | @Override 17 | public boolean execute(ArgumentList args) { 18 | Waypoint p = Waypoints.nearestByTag(WaypointTag.USER); 19 | 20 | if(p == null) { 21 | ChatUtil.send("§cNo waypoints available!"); 22 | 23 | return true; 24 | } 25 | 26 | Waypoints.gotoWaypoint(p); 27 | 28 | return true; 29 | } 30 | 31 | } 32 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/CharSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers; 2 | 3 | import java.nio.ByteBuffer; 4 | 5 | import de.stylextv.maple.io.resource.StreamedResource; 6 | import de.stylextv.maple.io.serialize.Serializer; 7 | 8 | public class CharSerializer extends Serializer { 9 | 10 | private static final int SIZE_IN_BYTES = 2; 11 | 12 | @Override 13 | public Character readFrom(StreamedResource r) { 14 | byte[] data = r.read(SIZE_IN_BYTES); 15 | 16 | ByteBuffer buffer = ByteBuffer.wrap(data); 17 | 18 | return buffer.getChar(); 19 | } 20 | 21 | @Override 22 | public void writeTo(StreamedResource r, Character c) { 23 | ByteBuffer buffer = ByteBuffer.allocate(SIZE_IN_BYTES); 24 | 25 | buffer.putChar(c); 26 | 27 | byte[] data = buffer.array(); 28 | 29 | r.write(data); 30 | } 31 | 32 | } 33 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/DoubleSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers; 2 | 3 | import java.nio.ByteBuffer; 4 | 5 | import de.stylextv.maple.io.resource.StreamedResource; 6 | import de.stylextv.maple.io.serialize.Serializer; 7 | 8 | public class DoubleSerializer extends Serializer { 9 | 10 | private static final int SIZE_IN_BYTES = 8; 11 | 12 | @Override 13 | public Double readFrom(StreamedResource r) { 14 | byte[] data = r.read(SIZE_IN_BYTES); 15 | 16 | ByteBuffer buffer = ByteBuffer.wrap(data); 17 | 18 | return buffer.getDouble(); 19 | } 20 | 21 | @Override 22 | public void writeTo(StreamedResource r, Double d) { 23 | ByteBuffer buffer = ByteBuffer.allocate(SIZE_IN_BYTES); 24 | 25 | buffer.putDouble(d); 26 | 27 | byte[] data = buffer.array(); 28 | 29 | r.write(data); 30 | } 31 | 32 | } 33 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/IntegerSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers; 2 | 3 | import java.nio.ByteBuffer; 4 | 5 | import de.stylextv.maple.io.resource.StreamedResource; 6 | import de.stylextv.maple.io.serialize.Serializer; 7 | 8 | public class IntegerSerializer extends Serializer { 9 | 10 | private static final int SIZE_IN_BYTES = 4; 11 | 12 | @Override 13 | public Integer readFrom(StreamedResource r) { 14 | byte[] data = r.read(SIZE_IN_BYTES); 15 | 16 | ByteBuffer buffer = ByteBuffer.wrap(data); 17 | 18 | return buffer.getInt(); 19 | } 20 | 21 | @Override 22 | public void writeTo(StreamedResource r, Integer i) { 23 | ByteBuffer buffer = ByteBuffer.allocate(SIZE_IN_BYTES); 24 | 25 | buffer.putInt(i); 26 | 27 | byte[] data = buffer.array(); 28 | 29 | r.write(data); 30 | } 31 | 32 | } 33 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/option/Option.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.option; 2 | 3 | import de.stylextv.maple.Maple; 4 | 5 | public class Option { 6 | 7 | private transient String name; 8 | 9 | private transient T defaultValue; 10 | 11 | private T value; 12 | 13 | public Option(String name, T value) { 14 | this.name = name; 15 | this.defaultValue = value; 16 | this.value = value; 17 | 18 | Options.registerOption(this); 19 | } 20 | 21 | public void reset() { 22 | setValue(defaultValue); 23 | } 24 | 25 | public boolean wasModified() { 26 | return !value.equals(defaultValue); 27 | } 28 | 29 | public String getName() { 30 | return name; 31 | } 32 | 33 | public T getValue() { 34 | return value; 35 | } 36 | 37 | public void setValue(T value) { 38 | this.value = value; 39 | 40 | Maple.getInstance().getOptions().save(); 41 | } 42 | 43 | } 44 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/world/CoordUtil.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.world; 2 | 3 | import de.stylextv.maple.util.math.MathUtil; 4 | import net.minecraft.util.math.BlockPos; 5 | 6 | public class CoordUtil { 7 | 8 | public static int chunkToRegionPos(int i) { 9 | return i >> 5; 10 | } 11 | 12 | public static int blockToChunkPos(int i) { 13 | return i >> 4; 14 | } 15 | 16 | public static int unitToBlockPos(double d) { 17 | return (int) Math.floor(d); 18 | } 19 | 20 | public static int posInChunk(int i) { 21 | return i & 15; 22 | } 23 | 24 | public static long posAsLong(int x, int y, int z) { 25 | return BlockPos.asLong(x, y, z); 26 | } 27 | 28 | public static String formatDistance(double d) { 29 | long l = Math.round(d); 30 | 31 | if(l < 1000) return l + " blocks"; 32 | 33 | return MathUtil.formatNumber(l / 1000.0) + " km"; 34 | } 35 | 36 | } 37 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/HomeCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.command.Command; 5 | import de.stylextv.maple.util.chat.ChatUtil; 6 | import de.stylextv.maple.waypoint.Waypoint; 7 | import de.stylextv.maple.waypoint.WaypointTag; 8 | import de.stylextv.maple.waypoint.Waypoints; 9 | 10 | public class HomeCommand extends Command { 11 | 12 | public HomeCommand() { 13 | super("home", "Travel to the nearest waypoint marked as §oHOME§7.", "h"); 14 | } 15 | 16 | @Override 17 | public boolean execute(ArgumentList args) { 18 | Waypoint p = Waypoints.nearestByTag(WaypointTag.HOME); 19 | 20 | if(p == null) { 21 | ChatUtil.send("§cNo waypoints available!"); 22 | 23 | return true; 24 | } 25 | 26 | Waypoints.gotoWaypoint(p); 27 | 28 | return true; 29 | } 30 | 31 | } 32 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/events/PacketEvent.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.events; 2 | 3 | import de.stylextv.maple.event.Event; 4 | import de.stylextv.maple.event.EventListener; 5 | import net.minecraft.network.Packet; 6 | 7 | public class PacketEvent extends Event { 8 | 9 | private Type type; 10 | 11 | private Packet packet; 12 | 13 | public PacketEvent(Type type, Packet packet) { 14 | this.type = type; 15 | this.packet = packet; 16 | } 17 | 18 | @Override 19 | public void callListener(EventListener l) { 20 | if(type == Type.SENT) { 21 | 22 | l.onPacketSent(this); 23 | 24 | } else { 25 | 26 | l.onPacketReceived(this); 27 | } 28 | } 29 | 30 | public Type getType() { 31 | return type; 32 | } 33 | 34 | public Packet getPacket() { 35 | return packet; 36 | } 37 | 38 | public enum Type { 39 | 40 | SENT, RECEIVED; 41 | 42 | } 43 | 44 | } 45 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/events/WorldEvent.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.events; 2 | 3 | import de.stylextv.maple.event.Event; 4 | import de.stylextv.maple.event.EventListener; 5 | import net.minecraft.client.world.ClientWorld; 6 | 7 | public class WorldEvent extends Event { 8 | 9 | private Type type; 10 | 11 | private ClientWorld world; 12 | 13 | public WorldEvent(Type type, ClientWorld world) { 14 | this.type = type; 15 | this.world = world; 16 | } 17 | 18 | @Override 19 | public void callListener(EventListener l) { 20 | if(type == Type.LOAD) { 21 | 22 | l.onWorldLoad(this); 23 | 24 | } else { 25 | 26 | l.onWorldUnload(this); 27 | } 28 | } 29 | 30 | public Type getType() { 31 | return type; 32 | } 33 | 34 | public ClientWorld getWorld() { 35 | return world; 36 | } 37 | 38 | public enum Type { 39 | 40 | LOAD, UNLOAD; 41 | 42 | } 43 | 44 | } 45 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/iterate/iterators/types/StaticIterator.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.iterate.iterators.types; 2 | 3 | import de.stylextv.maple.util.iterate.FunctionIterator; 4 | 5 | public abstract class StaticIterator extends FunctionIterator { 6 | 7 | private Object[] elements; 8 | 9 | private boolean generated; 10 | 11 | public StaticIterator(int length) { 12 | super(length); 13 | 14 | this.elements = new Object[length]; 15 | } 16 | 17 | public abstract void generate(); 18 | 19 | public void set(int index, T t) { 20 | elements[index] = t; 21 | } 22 | 23 | @SuppressWarnings("unchecked") 24 | @Override 25 | public T get(int index) { 26 | if(!generated) { 27 | 28 | generate(); 29 | 30 | generated = true; 31 | } 32 | 33 | return (T) elements[index]; 34 | } 35 | 36 | public boolean isGenerated() { 37 | return generated; 38 | } 39 | 40 | } 41 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/list/types/IntegerListSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers.list.types; 2 | 3 | import java.util.Arrays; 4 | import java.util.List; 5 | import java.util.stream.IntStream; 6 | import java.util.stream.Stream; 7 | 8 | import de.stylextv.maple.io.resource.StreamedResource; 9 | import de.stylextv.maple.io.serialize.Serializer; 10 | import de.stylextv.maple.io.serialize.serializers.list.ListSerializer; 11 | 12 | public class IntegerListSerializer extends ListSerializer> { 13 | 14 | public IntegerListSerializer() { 15 | super(Serializer.INTEGER); 16 | } 17 | 18 | public void writeTo(StreamedResource r, int[] array) { 19 | IntStream stream = Arrays.stream(array); 20 | 21 | Stream boxed = stream.boxed(); 22 | 23 | List list = boxed.toList(); 24 | 25 | writeTo(r, list); 26 | } 27 | 28 | } 29 | -------------------------------------------------------------------------------- /src/main/resources/fabric.mod.json: -------------------------------------------------------------------------------- 1 | { 2 | "schemaVersion": 1, 3 | "id": "maple", 4 | "version": "${version}", 5 | 6 | "name": "Maple", 7 | "description": "Maple is a free and powerful path-finding bot that lets you navigate the vast landscapes of Minecraft without any user intervention.", 8 | "authors": [ 9 | "StylexTV" 10 | ], 11 | "contact": { 12 | "homepage": "https://maplemc.github.io/", 13 | "sources": "https://github.com/StylexTV/Maple", 14 | "issues": "https://github.com/StylexTV/Maple/issues" 15 | }, 16 | 17 | "license": "GPL-3.0", 18 | "icon": "assets/maple/icon.png", 19 | 20 | "environment": "client", 21 | "entrypoints": { 22 | "main": [ 23 | "de.stylextv.maple.Maple" 24 | ] 25 | }, 26 | "mixins": [ 27 | "maple.mixins.json" 28 | ], 29 | 30 | "depends": { 31 | "fabricloader": ">=0.12.2", 32 | "minecraft": "1.18.x", 33 | "java": ">=17" 34 | } 35 | } 36 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/PathingCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing; 2 | 3 | import de.stylextv.maple.pathing.calc.goal.Goal; 4 | 5 | public class PathingCommand { 6 | 7 | public static final PathingCommand PAUSE = new PathingCommand(PathingCommandType.PAUSE); 8 | 9 | public static final PathingCommand CANCEL = new PathingCommand(PathingCommandType.CANCEL); 10 | 11 | public static final PathingCommand DEFER = new PathingCommand(PathingCommandType.DEFER); 12 | 13 | private PathingCommandType type; 14 | 15 | private Goal goal; 16 | 17 | public PathingCommand(PathingCommandType type) { 18 | this(type, null); 19 | } 20 | 21 | public PathingCommand(PathingCommandType type, Goal goal) { 22 | this.type = type; 23 | this.goal = goal; 24 | } 25 | 26 | public PathingCommandType getType() { 27 | return type; 28 | } 29 | 30 | public Goal getGoal() { 31 | return goal; 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/helper/MovementHelper.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.helper; 2 | 3 | import de.stylextv.maple.pathing.calc.Node; 4 | import de.stylextv.maple.pathing.movement.Movement; 5 | import net.minecraft.util.math.BlockPos; 6 | 7 | public class MovementHelper { 8 | 9 | private T movement; 10 | 11 | public MovementHelper(T m) { 12 | this.movement = m; 13 | } 14 | 15 | public double cost() { 16 | return 0; 17 | } 18 | 19 | public BlockPos sourcePos() { 20 | return getSource().blockPos(); 21 | } 22 | 23 | public BlockPos destinationPos() { 24 | return getDestination().blockPos(); 25 | } 26 | 27 | public Node getSource() { 28 | return movement.getSource(); 29 | } 30 | 31 | public Node getDestination() { 32 | return movement.getDestination(); 33 | } 34 | 35 | public T getMovement() { 36 | return movement; 37 | } 38 | 39 | } 40 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/ItemUtil.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util; 2 | 3 | import net.minecraft.block.BlockState; 4 | import net.minecraft.enchantment.EnchantmentHelper; 5 | import net.minecraft.enchantment.Enchantments; 6 | import net.minecraft.item.ItemStack; 7 | 8 | public class ItemUtil { 9 | 10 | public static float getToolScore(ItemStack stack, BlockState state) { 11 | float score = getDigSpeed(stack, state); 12 | 13 | if(stack.isDamageable() && score <= 1) { 14 | 15 | score = -stack.getRepairCost() - 1; 16 | } 17 | 18 | return score; 19 | } 20 | 21 | public static float getDigSpeed(ItemStack stack, BlockState state) { 22 | float f = stack.getMiningSpeedMultiplier(state); 23 | 24 | if(f <= 1) return f; 25 | 26 | int level = EnchantmentHelper.getLevel(Enchantments.EFFICIENCY, stack); 27 | 28 | if(level > 0) f += level * level + 1; 29 | 30 | return f; 31 | } 32 | 33 | } 34 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/calc/goal/InvertedGoal.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.calc.goal; 2 | 3 | import de.stylextv.maple.pathing.calc.Node; 4 | 5 | public class InvertedGoal extends Goal { 6 | 7 | private Goal goal; 8 | 9 | public InvertedGoal(Goal goal) { 10 | this.goal = goal; 11 | } 12 | 13 | @Override 14 | public double heuristic(Node n) { 15 | return -goal.heuristic(n); 16 | } 17 | 18 | @Override 19 | public boolean isFinalNode(Node n) { 20 | return false; 21 | } 22 | 23 | @Override 24 | public boolean equals(Goal other) { 25 | if(!(other instanceof InvertedGoal)) return false; 26 | 27 | Goal otherGoal = ((InvertedGoal) other).getGoal(); 28 | 29 | return otherGoal.equals(goal); 30 | } 31 | 32 | @Override 33 | public String toString() { 34 | return String.format("InvertedGoal{goal=%s}", goal); 35 | } 36 | 37 | public Goal getGoal() { 38 | return goal; 39 | } 40 | 41 | } 42 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/bug_report.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Bug report 3 | about: Create a report to help improve the project 4 | title: '' 5 | labels: bug 6 | assignees: StylexTV 7 | 8 | --- 9 | 10 | **Exceptions and logs** 11 | Please find the latest ´.log´ file after reproducing the bug and closing the game (usually located in `.minecraft/logs/`). 12 | 13 | **To Reproduce** 14 | Steps to reproduce the behavior: 15 | 1. Do this 16 | 2. Make that 17 | 3. Error! 18 | 19 | **Screenshots** 20 | If applicable, add screenshots to help explain your problem. 21 | 22 | **Modified options** 23 | Run #modified ingame to get a list of all modified options, and place that list here. 24 | 25 | **Environment (please complete the following information):** 26 | - OS: [e.g. iOS, Windows] 27 | - Java version: [e.g. 1.8.0] 28 | - Minecraft version: 29 | - Maple version: 30 | - Other mods (if used): 31 | 32 | **Additional context** 33 | Add any other context about the problem here. 34 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/calc/goal/AxisGoal.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.calc.goal; 2 | 3 | import de.stylextv.maple.pathing.calc.Cost; 4 | import de.stylextv.maple.pathing.calc.Node; 5 | 6 | public class AxisGoal extends Goal { 7 | 8 | @Override 9 | public double heuristic(Node n) { 10 | int x = Math.abs(n.getX()); 11 | int z = Math.abs(n.getZ()); 12 | 13 | int majorDis = Math.min(x, z); 14 | 15 | int minorDis = Math.abs(x - z) / 2; 16 | 17 | return Math.min(majorDis * Cost.SPRINT_STRAIGHT, minorDis * Cost.SPRINT_DIAGONALLY); 18 | } 19 | 20 | @Override 21 | public boolean isFinalNode(Node n) { 22 | int x = n.getX(); 23 | int z = n.getZ(); 24 | 25 | return x == 0 || z == 0 || Math.abs(x) == Math.abs(z); 26 | } 27 | 28 | @Override 29 | public boolean equals(Goal other) { 30 | return other instanceof AxisGoal; 31 | } 32 | 33 | @Override 34 | public String toString() { 35 | return "AxisGoal"; 36 | } 37 | 38 | } 39 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/movements/DiagonalMovement.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.movements; 2 | 3 | import de.stylextv.maple.input.InputAction; 4 | import de.stylextv.maple.pathing.calc.Node; 5 | import de.stylextv.maple.pathing.movement.Movement; 6 | 7 | public class DiagonalMovement extends Movement { 8 | 9 | public DiagonalMovement(Node source, Node destination) { 10 | super(source, destination); 11 | } 12 | 13 | @Override 14 | public void updateHelpers() { 15 | getInteractHelper().collectDefaultBlocks(); 16 | } 17 | 18 | @Override 19 | public double cost() { 20 | double cost = getInteractHelper().cost(); 21 | 22 | return cost + super.cost(); 23 | } 24 | 25 | @Override 26 | public void onRenderTick() { 27 | if(getInteractHelper().onRenderTick()) return; 28 | 29 | lookAt(getDestination()); 30 | 31 | setPressed(InputAction.MOVE_FORWARD, true); 32 | setPressed(InputAction.SPRINT, true); 33 | } 34 | 35 | } 36 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/option/Options.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.option; 2 | 3 | import de.stylextv.maple.config.ConfigHelper; 4 | 5 | public class Options { 6 | 7 | private static final String FILE_NAME = "options"; 8 | 9 | private static final Option[] OPTIONS = new Option[2]; 10 | 11 | private static int pointer; 12 | 13 | public final Option allowBreak = new Option("allowBreak", true); 14 | 15 | public final Option allowPlace = new Option("allowPlace", true); 16 | 17 | public void save() { 18 | ConfigHelper.saveFile(FILE_NAME, this); 19 | } 20 | 21 | public static Options load() { 22 | Options options = ConfigHelper.loadFile(FILE_NAME, Options.class); 23 | 24 | return options; 25 | } 26 | 27 | public static void registerOption(Option option) { 28 | OPTIONS[pointer] = option; 29 | 30 | pointer++; 31 | } 32 | 33 | public static Option[] getOptions() { 34 | return OPTIONS; 35 | } 36 | 37 | } 38 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/Command.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command; 2 | 3 | public abstract class Command { 4 | 5 | private String name; 6 | 7 | private String[] aliases; 8 | 9 | private String description; 10 | 11 | public Command(String name, String description, String... aliases) { 12 | this.name = name; 13 | this.aliases = aliases; 14 | this.description = description; 15 | } 16 | 17 | public abstract boolean execute(ArgumentList args); 18 | 19 | public boolean nameEquals(String s) { 20 | if(name.equalsIgnoreCase(s)) return true; 21 | 22 | for(String alias : aliases) { 23 | if(alias.equalsIgnoreCase(s)) return true; 24 | } 25 | 26 | return false; 27 | } 28 | 29 | public String getName() { 30 | return name; 31 | } 32 | 33 | public String[] getAliases() { 34 | return aliases; 35 | } 36 | 37 | public String getDescription() { 38 | return description; 39 | } 40 | 41 | public String[] getUsages() { 42 | return null; 43 | } 44 | 45 | } 46 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/math/MathUtil.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.math; 2 | 3 | import java.text.DecimalFormat; 4 | import java.text.DecimalFormatSymbols; 5 | import java.util.Locale; 6 | 7 | public class MathUtil { 8 | 9 | private static final double NATURAL_LOG_TWO = Math.log(2); 10 | 11 | private static final DecimalFormat FORMAT = new DecimalFormat("#.0", new DecimalFormatSymbols(Locale.US)); 12 | 13 | public static int clamp(int i, int min, int max) { 14 | return (int) clamp((float) i, min, max); 15 | } 16 | 17 | public static float clamp(float f, float min, float max) { 18 | if(f < min) return min; 19 | if(f > max) return max; 20 | 21 | return f; 22 | } 23 | 24 | public static double lerp(double d, double target, double speed) { 25 | return d + (target - d) * speed; 26 | } 27 | 28 | public static double log2(double d) { 29 | return Math.log(d) / NATURAL_LOG_TWO; 30 | } 31 | 32 | public static String formatNumber(double d) { 33 | return FORMAT.format(d); 34 | } 35 | 36 | } 37 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/interact/openables/OpenableTrapdoor.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.interact.openables; 2 | 3 | import de.stylextv.maple.pathing.movement.Movement; 4 | import de.stylextv.maple.world.interact.Openable; 5 | import net.minecraft.block.Block; 6 | import net.minecraft.block.BlockState; 7 | import net.minecraft.block.Blocks; 8 | import net.minecraft.block.TrapdoorBlock; 9 | 10 | public class OpenableTrapdoor extends Openable { 11 | 12 | @Override 13 | public boolean matchesBlock(Block block) { 14 | return block instanceof TrapdoorBlock; 15 | } 16 | 17 | @Override 18 | public boolean isLocked(BlockState state) { 19 | Block block = state.getBlock(); 20 | 21 | return block.equals(Blocks.IRON_TRAPDOOR); 22 | } 23 | 24 | @Override 25 | public boolean isOpen(BlockState state, Movement m) { 26 | boolean open = state.get(TrapdoorBlock.OPEN); 27 | 28 | boolean b = m.isVerticalOnly() || m.isDownwards(); 29 | 30 | if(!b) open = !open; 31 | 32 | return open; 33 | } 34 | 35 | } 36 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/resource/types/StreamedAsset.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.resource.types; 2 | 3 | import java.io.InputStream; 4 | import java.io.OutputStream; 5 | 6 | import de.stylextv.maple.io.resource.StreamedResource; 7 | 8 | public class StreamedAsset extends StreamedResource { 9 | 10 | private static final String ASSETS_FOLDER = "assets/"; 11 | 12 | private String path; 13 | 14 | public StreamedAsset(String path) { 15 | this(path, true); 16 | } 17 | 18 | public StreamedAsset(String path, boolean compress) { 19 | super(compress); 20 | 21 | this.path = path; 22 | } 23 | 24 | @Override 25 | protected InputStream inputStream() { 26 | Thread thread = Thread.currentThread(); 27 | 28 | ClassLoader loader = thread.getContextClassLoader(); 29 | 30 | return loader.getResourceAsStream(ASSETS_FOLDER + path); 31 | } 32 | 33 | @Override 34 | protected OutputStream outputStream() { 35 | return null; 36 | } 37 | 38 | public String getPath() { 39 | return path; 40 | } 41 | 42 | } 43 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/cache/block/matchers/FluidBlockMatcher.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.cache.block.matchers; 2 | 3 | import de.stylextv.maple.cache.block.BlockMatcher; 4 | import de.stylextv.maple.cache.block.BlockType; 5 | import net.minecraft.block.Block; 6 | import net.minecraft.block.BlockState; 7 | import net.minecraft.block.Blocks; 8 | import net.minecraft.fluid.Fluid; 9 | import net.minecraft.fluid.Fluids; 10 | 11 | public class FluidBlockMatcher extends BlockMatcher { 12 | 13 | @Override 14 | public BlockType match(BlockState state, BlockState above, BlockState below) { 15 | Fluid fluid = state.getFluidState().getFluid(); 16 | 17 | if(fluid.equals(Fluids.FLOWING_WATER)) return BlockType.DANGER; 18 | 19 | Block block = below.getBlock(); 20 | 21 | boolean aboveMagma = block.equals(Blocks.MAGMA_BLOCK); 22 | 23 | if(aboveMagma) return BlockType.DANGER; 24 | 25 | boolean isWater = fluid.equals(Fluids.WATER); 26 | 27 | if(isWater) return BlockType.WATER; 28 | 29 | return null; 30 | } 31 | 32 | } 33 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/iterate/iterators/GridIterator.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.iterate.iterators; 2 | 3 | import de.stylextv.maple.util.iterate.IntPair; 4 | import de.stylextv.maple.util.iterate.iterators.types.IntPairIterator; 5 | 6 | public class GridIterator extends IntPairIterator { 7 | 8 | public static final GridIterator SIXTEEN_BY_SIXTEEN = new GridIterator(16, 16); 9 | 10 | private int width; 11 | private int height; 12 | 13 | public GridIterator(int size) { 14 | this(size, size); 15 | } 16 | 17 | public GridIterator(int width, int height) { 18 | super(width * height); 19 | 20 | this.width = width; 21 | this.height = height; 22 | } 23 | 24 | @Override 25 | public void generate() { 26 | for(int i = 0; i < getLength(); i++) { 27 | 28 | int x = i % width; 29 | int y = i / width; 30 | 31 | set(i, new IntPair(x, y)); 32 | } 33 | } 34 | 35 | public int getWidth() { 36 | return width; 37 | } 38 | 39 | public int getHeight() { 40 | return height; 41 | } 42 | 43 | } 44 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/ETACommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.command.Command; 5 | import de.stylextv.maple.pathing.calc.Path; 6 | import de.stylextv.maple.pathing.movement.MovementExecutor; 7 | import de.stylextv.maple.util.chat.ChatUtil; 8 | import de.stylextv.maple.util.time.TimeFormat; 9 | 10 | public class ETACommand extends Command { 11 | 12 | public ETACommand() { 13 | super("eta", "Displays the estimated time to reach the current destination."); 14 | } 15 | 16 | @Override 17 | public boolean execute(ArgumentList args) { 18 | if(!MovementExecutor.hasPath()) { 19 | ChatUtil.send("§cNot actively pathing!"); 20 | 21 | return true; 22 | } 23 | 24 | Path p = MovementExecutor.getPath(); 25 | 26 | long time = p.timeToGoal(); 27 | 28 | String s = TimeFormat.formatDuration(time); 29 | 30 | ChatUtil.send("Estimated time until arrival: " + s); 31 | 32 | return true; 33 | } 34 | 35 | } 36 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/mixin/DefaultedListMixin.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.mixin; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | import org.spongepowered.asm.mixin.injection.At; 5 | import org.spongepowered.asm.mixin.injection.Coerce; 6 | import org.spongepowered.asm.mixin.injection.Inject; 7 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable; 8 | 9 | import de.stylextv.maple.event.EventBus; 10 | import de.stylextv.maple.event.events.InventoryUpdateEvent; 11 | import net.minecraft.item.ItemStack; 12 | import net.minecraft.util.collection.DefaultedList; 13 | 14 | @Mixin(DefaultedList.class) 15 | public class DefaultedListMixin { 16 | 17 | @SuppressWarnings("unchecked") 18 | @Inject(method = "set", at = @At("TAIL")) 19 | private void set(int index, @Coerce T element, CallbackInfoReturnable info) { 20 | if(!(element instanceof ItemStack)) return; 21 | 22 | DefaultedList list = (DefaultedList) (Object) this; 23 | 24 | EventBus.onEvent(new InventoryUpdateEvent(list)); 25 | } 26 | 27 | } 28 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/TextUtil.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util; 2 | 3 | public class TextUtil { 4 | 5 | public static String combine(Object[] arr, String seperator) { 6 | String s = ""; 7 | 8 | for(int i = 0; i < arr.length; i++) { 9 | if(i != 0) s += seperator; 10 | 11 | Object o = arr[i]; 12 | 13 | s += o.toString(); 14 | } 15 | 16 | return s; 17 | } 18 | 19 | public static String findBracket(String s, char ch1, char ch2) { 20 | return findBracket(s, ch1, ch2, false); 21 | } 22 | 23 | public static String findBracket(String s, char ch1, char ch2, boolean stopOnSpace) { 24 | boolean b = false; 25 | 26 | String content = ""; 27 | 28 | for(char ch : s.toCharArray()) { 29 | 30 | if(ch == ' ' && stopOnSpace && !b) return null; 31 | 32 | if(ch == ch2 && b) break; 33 | 34 | if(ch == ch1) { 35 | 36 | b = true; 37 | 38 | continue; 39 | } 40 | 41 | if(b) content += ch; 42 | } 43 | 44 | if(!b) return null; 45 | 46 | return content; 47 | } 48 | 49 | } 50 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/iterate/iterators/SpiralIterator.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.iterate.iterators; 2 | 3 | import de.stylextv.maple.util.iterate.IntPair; 4 | import de.stylextv.maple.util.iterate.iterators.types.IntPairIterator; 5 | 6 | public class SpiralIterator extends IntPairIterator { 7 | 8 | private int size; 9 | 10 | public SpiralIterator(int size) { 11 | super(size * size); 12 | 13 | this.size = size; 14 | } 15 | 16 | @Override 17 | public void generate() { 18 | int x = 0; 19 | int y = 0; 20 | 21 | int dx = 0; 22 | int dy = -1; 23 | 24 | for(int i = 0; i < getLength(); i++) { 25 | 26 | set(i, new IntPair(x, y)); 27 | 28 | boolean b1 = x < 0 && x == -y; 29 | boolean b2 = x > 0 && x == 1 - y; 30 | 31 | boolean turn = b1 || b2 || x == y; 32 | 33 | if(turn) { 34 | 35 | int temp = dx; 36 | 37 | dx = -dy; 38 | dy = temp; 39 | } 40 | 41 | x += dx; 42 | y += dy; 43 | } 44 | } 45 | 46 | public int getSize() { 47 | return size; 48 | } 49 | 50 | } 51 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/input/SmoothLook.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.input; 2 | 3 | import de.stylextv.maple.context.PlayerContext; 4 | import de.stylextv.maple.util.world.rotation.Rotation; 5 | import net.minecraft.client.network.ClientPlayerEntity; 6 | 7 | public class SmoothLook { 8 | 9 | private boolean active; 10 | 11 | private Rotation rotation; 12 | 13 | public void setRotation(Rotation r) { 14 | active = true; 15 | 16 | rotation = r; 17 | } 18 | 19 | public void update() { 20 | if(active) { 21 | active = false; 22 | 23 | apply(); 24 | 25 | return; 26 | } 27 | 28 | reset(); 29 | } 30 | 31 | private void apply() { 32 | ClientPlayerEntity p = PlayerContext.player(); 33 | 34 | float yaw = p.getYaw(); 35 | float pitch = p.getPitch(); 36 | 37 | Rotation r = new Rotation(yaw, pitch); 38 | 39 | Rotation target = rotation.calibrateYaw(r); 40 | 41 | p.setYaw(target.getYaw()); 42 | p.setPitch(target.getPitch()); 43 | } 44 | 45 | private void reset() { 46 | rotation = null; 47 | } 48 | 49 | } 50 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/input/InjectedInput.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.input; 2 | 3 | import de.stylextv.maple.input.controller.InputController; 4 | import net.minecraft.client.input.Input; 5 | 6 | public class InjectedInput extends Input { 7 | 8 | @Override 9 | public void tick(boolean slowDown) { 10 | pressingForward = InputController.isPressed(InputAction.MOVE_FORWARD); 11 | pressingBack = InputController.isPressed(InputAction.MOVE_BACK); 12 | pressingLeft = InputController.isPressed(InputAction.MOVE_LEFT); 13 | pressingRight = InputController.isPressed(InputAction.MOVE_RIGHT); 14 | 15 | movementForward = pressingForward == pressingBack ? 0 : (pressingForward ? 1 : -1); 16 | movementSideways = pressingLeft == pressingRight ? 0 : (pressingLeft ? 1 : -1); 17 | 18 | if(slowDown) { 19 | movementForward *= 0.3f; 20 | movementSideways *= 0.3f; 21 | } 22 | 23 | jumping = InputController.isPressed(InputAction.JUMP); 24 | 25 | sneaking = InputController.isPressed(InputAction.SNEAK); 26 | 27 | InputController.releaseAll(); 28 | } 29 | 30 | } 31 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/scan/entity/EntityScanner.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.scan.entity; 2 | 3 | import java.util.ArrayList; 4 | import java.util.List; 5 | 6 | import de.stylextv.maple.context.PlayerContext; 7 | import de.stylextv.maple.context.WorldContext; 8 | import net.minecraft.client.network.ClientPlayerEntity; 9 | import net.minecraft.client.world.ClientWorld; 10 | import net.minecraft.entity.Entity; 11 | 12 | public class EntityScanner { 13 | 14 | public static List scanWorld() { 15 | EntityFilters filters = EntityFilters.fromFilter(EntityFilter.ALL); 16 | 17 | return scanWorld(filters); 18 | } 19 | 20 | public static List scanWorld(EntityFilters filters) { 21 | List entities = new ArrayList<>(); 22 | 23 | ClientWorld world = WorldContext.world(); 24 | 25 | ClientPlayerEntity p = PlayerContext.player(); 26 | 27 | for(Entity e : world.getEntities()) { 28 | 29 | if(e.equals(p)) continue; 30 | 31 | if(filters.matches(e)) entities.add(e); 32 | } 33 | 34 | return entities; 35 | } 36 | 37 | } 38 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/task/tasks/FarmTask.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.task.tasks; 2 | 3 | import de.stylextv.maple.util.chat.ChatUtil; 4 | import de.stylextv.maple.world.scan.block.BlockFilter; 5 | import de.stylextv.maple.world.scan.block.BlockFilters; 6 | import de.stylextv.maple.world.scan.block.filters.BlockTypeFilter; 7 | import net.minecraft.block.Blocks; 8 | 9 | public class FarmTask extends BreakTask { 10 | 11 | private static final BlockFilter FILTER = new BlockTypeFilter( 12 | Blocks.WHEAT, 13 | Blocks.CARROTS, 14 | Blocks.POTATOES, 15 | Blocks.BEETROOTS, 16 | Blocks.PUMPKIN, 17 | Blocks.MELON, 18 | Blocks.SUGAR_CANE, 19 | Blocks.BAMBOO, 20 | Blocks.CACTUS, 21 | Blocks.NETHER_WART 22 | ); 23 | 24 | public FarmTask() { 25 | super(BlockFilters.fromFilters(FILTER, BlockFilter.FULLY_GROWN)); 26 | } 27 | 28 | @Override 29 | public void onFail() { 30 | ChatUtil.send("Can't get any closer to crops."); 31 | } 32 | 33 | @Override 34 | public void onEmptyGoal() { 35 | ChatUtil.send("Can't find any matching crops nearby."); 36 | } 37 | 38 | } 39 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/TunnelCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.command.Command; 5 | import de.stylextv.maple.context.PlayerContext; 6 | import de.stylextv.maple.pathing.calc.goal.Goal; 7 | import de.stylextv.maple.pathing.calc.goal.StrictDirectionGoal; 8 | import de.stylextv.maple.task.TaskManager; 9 | import de.stylextv.maple.util.chat.ChatUtil; 10 | import net.minecraft.util.math.BlockPos; 11 | import net.minecraft.util.math.Direction; 12 | 13 | public class TunnelCommand extends Command { 14 | 15 | public TunnelCommand() { 16 | super("tunnel", "Tunnel in the direction you are looking."); 17 | } 18 | 19 | @Override 20 | public boolean execute(ArgumentList args) { 21 | BlockPos pos = PlayerContext.feetPosition(); 22 | 23 | Direction dir = PlayerContext.horizontalDirection(); 24 | 25 | Goal goal = new StrictDirectionGoal(pos, dir); 26 | 27 | TaskManager.gotoGoal(goal); 28 | 29 | ChatUtil.send("Started tunneling."); 30 | 31 | return true; 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/mixin/LivingEntityMixin.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.mixin; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | import org.spongepowered.asm.mixin.injection.At; 5 | import org.spongepowered.asm.mixin.injection.Inject; 6 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 7 | 8 | import de.stylextv.maple.event.EventBus; 9 | import de.stylextv.maple.event.events.EntityDeathEvent; 10 | import de.stylextv.maple.event.events.EntitySleptEvent; 11 | import net.minecraft.entity.LivingEntity; 12 | 13 | @Mixin(LivingEntity.class) 14 | public class LivingEntityMixin { 15 | 16 | @Inject(method = "setHealth(F)V", at = @At("TAIL")) 17 | private void setHealth(float health, CallbackInfo info) { 18 | if(health <= 0) { 19 | 20 | LivingEntity entity = (LivingEntity) (Object) this; 21 | 22 | EventBus.onEvent(new EntityDeathEvent(entity)); 23 | } 24 | } 25 | 26 | @Inject(method = "wakeUp()V", at = @At("TAIL")) 27 | private void wakeUp(CallbackInfo info) { 28 | LivingEntity entity = (LivingEntity) (Object) this; 29 | 30 | EventBus.onEvent(new EntitySleptEvent(entity)); 31 | } 32 | 33 | } 34 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/MineCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.command.Command; 5 | import de.stylextv.maple.task.Task; 6 | import de.stylextv.maple.task.TaskManager; 7 | import de.stylextv.maple.task.tasks.MineTask; 8 | import de.stylextv.maple.util.chat.ChatUtil; 9 | import de.stylextv.maple.world.scan.block.BlockFilter; 10 | 11 | public class MineCommand extends Command { 12 | 13 | public MineCommand() { 14 | super("mine", "Starts mining a specified block type."); 15 | } 16 | 17 | @Override 18 | public boolean execute(ArgumentList args) { 19 | if(args.hasExactly(0)) return false; 20 | 21 | String s = args.get(0); 22 | 23 | BlockFilter filter = BlockFilter.fromString(s); 24 | 25 | if(filter == null) return false; 26 | 27 | Task task = new MineTask(filter); 28 | 29 | TaskManager.startTask(task); 30 | 31 | ChatUtil.send("Started mining."); 32 | 33 | return true; 34 | } 35 | 36 | @Override 37 | public String[] getUsages() { 38 | return new String[] {""}; 39 | } 40 | 41 | } 42 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/task/tasks/CustomGoalTask.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.task.tasks; 2 | 3 | import de.stylextv.maple.pathing.PathingCommand; 4 | import de.stylextv.maple.pathing.PathingCommandType; 5 | import de.stylextv.maple.pathing.PathingStatus; 6 | import de.stylextv.maple.pathing.calc.goal.Goal; 7 | import de.stylextv.maple.task.Task; 8 | import de.stylextv.maple.util.chat.ChatUtil; 9 | 10 | public class CustomGoalTask extends Task { 11 | 12 | private Goal goal; 13 | 14 | public CustomGoalTask(Goal goal) { 15 | this.goal = goal; 16 | } 17 | 18 | @Override 19 | public PathingCommand onRenderTick(PathingStatus status) { 20 | boolean matches = status.goalMatches(goal); 21 | 22 | if(!matches) return new PathingCommand(PathingCommandType.PATH_TO_GOAL, goal); 23 | 24 | if(status.isPathing()) return PathingCommand.DEFER; 25 | 26 | boolean atGoal = status.isAtGoal(); 27 | 28 | String s = atGoal ? "Destination reached." : "Can't get any closer to goal."; 29 | 30 | ChatUtil.send(s); 31 | 32 | return super.onRenderTick(status); 33 | } 34 | 35 | public Goal getGoal() { 36 | return goal; 37 | } 38 | 39 | } 40 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/cache/block/matchers/SolidBlockMatcher.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.cache.block.matchers; 2 | 3 | import de.stylextv.maple.cache.block.BlockMatcher; 4 | import de.stylextv.maple.cache.block.BlockType; 5 | import de.stylextv.maple.util.world.CollisionUtil; 6 | import net.minecraft.block.BlockState; 7 | import net.minecraft.util.math.BlockPos; 8 | import net.minecraft.util.math.Box; 9 | 10 | public class SolidBlockMatcher extends BlockMatcher { 11 | 12 | private static final Box COLLISION_BOX = new Box(0, 0.5, 0, 1, 1.5, 1); 13 | 14 | @Override 15 | public BlockType match(BlockState state, BlockState above, BlockState below, BlockPos pos) { 16 | boolean noFluid = state.getFluidState().isEmpty(); 17 | 18 | if(noFluid) { 19 | 20 | boolean hasCollision = CollisionUtil.hasCollision(pos, state); 21 | 22 | if(!hasCollision) return null; 23 | } 24 | 25 | Box box = COLLISION_BOX.offset(pos); 26 | 27 | boolean collides = CollisionUtil.collidesWithBlock(box, pos, state) || CollisionUtil.collidesWithBlock(box, pos.up(), above); 28 | 29 | if(collides) return BlockType.SOLID; 30 | 31 | return null; 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/listeners/TickListener.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.listeners; 2 | 3 | import de.stylextv.maple.context.GameContext; 4 | import de.stylextv.maple.event.EventListener; 5 | import de.stylextv.maple.event.events.TickEvent; 6 | import de.stylextv.maple.input.controller.BreakController; 7 | import de.stylextv.maple.input.controller.InputController; 8 | import de.stylextv.maple.input.controller.PlaceController; 9 | import de.stylextv.maple.input.controller.ViewController; 10 | import de.stylextv.maple.pathing.movement.MovementExecutor; 11 | import de.stylextv.maple.task.TaskManager; 12 | 13 | public class TickListener implements EventListener { 14 | 15 | @Override 16 | public void onClientTick(TickEvent event) { 17 | if(!GameContext.isIngame()) return; 18 | 19 | BreakController.onTick(); 20 | PlaceController.onTick(); 21 | 22 | InputController.onTick(); 23 | } 24 | 25 | @Override 26 | public void onRenderTick(TickEvent event) { 27 | if(!GameContext.isIngame()) return; 28 | 29 | TaskManager.onRenderTick(); 30 | 31 | MovementExecutor.onRenderTick(); 32 | 33 | ViewController.onRenderTick(); 34 | } 35 | 36 | } 37 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/world/rotation/RotationUtil.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.world.rotation; 2 | 3 | import net.minecraft.util.math.Vec3d; 4 | 5 | public class RotationUtil { 6 | 7 | public static final double DEG_TO_RAD = Math.PI / 180; 8 | 9 | public static final double RAD_TO_DEG = 180 / Math.PI; 10 | 11 | private static final double PI_OVER_TWO = Math.PI / 2; 12 | 13 | public static Rotation vecToRotation(double x, double y, double z) { 14 | double l = Math.sqrt(z * z + x * x); 15 | 16 | double tan1 = Math.atan2(z, x); 17 | double tan2 = Math.atan2(l, y); 18 | 19 | float yaw = (float) ((tan1 + PI_OVER_TWO) * RAD_TO_DEG); 20 | float pitch = (float) ((-tan2 + PI_OVER_TWO) * RAD_TO_DEG); 21 | 22 | Rotation r = new Rotation(yaw, pitch); 23 | 24 | return r.normalizeYaw(); 25 | } 26 | 27 | public static Vec3d rotationToVec(Rotation r) { 28 | double yaw = r.getYaw() * DEG_TO_RAD; 29 | double pitch = r.getPitch() * DEG_TO_RAD; 30 | 31 | double l = Math.cos(pitch); 32 | 33 | double x = -Math.sin(yaw) * l; 34 | double z = Math.cos(yaw) * l; 35 | 36 | double y = -Math.sin(pitch); 37 | 38 | return new Vec3d(x, y, z); 39 | } 40 | 41 | } 42 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/scan/entity/EntityFilter.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.scan.entity; 2 | 3 | import java.util.function.Predicate; 4 | 5 | import de.stylextv.maple.util.RegistryUtil; 6 | import de.stylextv.maple.world.scan.ScanFilter; 7 | import de.stylextv.maple.world.scan.entity.filters.EntityNameFilter; 8 | import de.stylextv.maple.world.scan.entity.filters.EntityTypeFilter; 9 | import net.minecraft.entity.Entity; 10 | import net.minecraft.entity.EntityType; 11 | import net.minecraft.entity.LivingEntity; 12 | 13 | public class EntityFilter extends ScanFilter { 14 | 15 | public static final EntityFilter ALL = new EntityFilter((e) -> { 16 | return true; 17 | }); 18 | 19 | public static final EntityFilter ALIVE = new EntityFilter((e) -> { 20 | return e instanceof LivingEntity && e.isAlive(); 21 | }); 22 | 23 | public EntityFilter() {} 24 | 25 | public EntityFilter(Predicate predicate) { 26 | super(predicate); 27 | } 28 | 29 | public static EntityFilter fromString(String s) { 30 | EntityType type = RegistryUtil.getEntityType(s); 31 | 32 | if(type == null) return new EntityNameFilter(s); 33 | 34 | return new EntityTypeFilter(type); 35 | } 36 | 37 | } 38 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/ArgumentHelper.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command; 2 | 3 | import de.stylextv.maple.context.PlayerContext; 4 | import net.minecraft.util.math.BlockPos; 5 | 6 | public class ArgumentHelper { 7 | 8 | private static final String INT_REGEX = "-?\\d+"; 9 | 10 | private static final String NUMERIC_REGEX = "-?\\d+(\\.\\d+)?"; 11 | 12 | public static int toCoordinate(String s, int i) { 13 | int base = 0; 14 | 15 | if(s.startsWith("~")) { 16 | s = s.substring(1); 17 | 18 | BlockPos pos = PlayerContext.feetPosition(); 19 | 20 | if(i == 0) base = pos.getX(); 21 | else if(i == 1) base = pos.getY(); 22 | else if(i == 2) base = pos.getZ(); 23 | } 24 | 25 | if(s.isEmpty()) return base; 26 | 27 | int offset = toInt(s); 28 | 29 | return base + offset; 30 | } 31 | 32 | public static int toInt(String s) { 33 | return Integer.parseInt(s); 34 | } 35 | 36 | public static float toFloat(String s) { 37 | return Float.parseFloat(s); 38 | } 39 | 40 | public static boolean isInt(String s) { 41 | return s.matches(INT_REGEX); 42 | } 43 | 44 | public static boolean isNumeric(String s) { 45 | return s.matches(NUMERIC_REGEX); 46 | } 47 | 48 | } 49 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/calc/goal/Goal.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.calc.goal; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.event.events.RenderWorldEvent; 5 | import de.stylextv.maple.pathing.calc.Node; 6 | 7 | public abstract class Goal { 8 | 9 | public abstract double heuristic(Node n); 10 | 11 | public abstract boolean isFinalNode(Node n); 12 | 13 | public void render(RenderWorldEvent event) {} 14 | 15 | public abstract boolean equals(Goal other); 16 | 17 | public static Goal fromArgs(ArgumentList args) { 18 | if(args.hasAtLeast(3)) { 19 | 20 | int x = args.getCoordinate(0); 21 | int y = args.getCoordinate(1); 22 | int z = args.getCoordinate(2); 23 | 24 | if(args.hasAtLeast(4)) { 25 | 26 | float dis = args.getFloat(3); 27 | 28 | return new NearGoal(x, y, z, dis); 29 | } 30 | 31 | return new BlockGoal(x, y, z); 32 | } 33 | 34 | if(args.hasAtLeast(2)) { 35 | 36 | int x = args.getCoordinate(0); 37 | int z = args.getCoordinate(1, 2); 38 | 39 | return new XZGoal(x, z); 40 | } 41 | 42 | int y = args.getCoordinate(0, 1); 43 | 44 | return new YLevelGoal(y); 45 | } 46 | 47 | } 48 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/calc/goal/YLevelGoal.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.calc.goal; 2 | 3 | import de.stylextv.maple.pathing.calc.Cost; 4 | import de.stylextv.maple.pathing.calc.Node; 5 | 6 | public class YLevelGoal extends Goal { 7 | 8 | private int y; 9 | 10 | public YLevelGoal(int y) { 11 | this.y = y; 12 | } 13 | 14 | @Override 15 | public double heuristic(Node n) { 16 | return cost(n.getY(), y); 17 | } 18 | 19 | @Override 20 | public boolean isFinalNode(Node n) { 21 | return n.getY() == y; 22 | } 23 | 24 | @Override 25 | public boolean equals(Goal other) { 26 | if(!(other instanceof YLevelGoal)) return false; 27 | 28 | int otherY = ((YLevelGoal) other).getY(); 29 | 30 | return otherY == y; 31 | } 32 | 33 | @Override 34 | public String toString() { 35 | return String.format("YGoal{y=%s}", y); 36 | } 37 | 38 | public int getY() { 39 | return y; 40 | } 41 | 42 | public static double cost(int y, int goalY) { 43 | if(y < goalY) { 44 | int dis = goalY - y; 45 | 46 | return dis * Cost.JUMP; 47 | } 48 | 49 | if(y > goalY) { 50 | int dis = y - goalY; 51 | 52 | return Cost.FALL_N_BLOCKS[2] / 2 * dis; 53 | } 54 | 55 | return 0; 56 | } 57 | 58 | } 59 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/scan/block/BlockFilter.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.scan.block; 2 | 3 | import java.util.function.Predicate; 4 | 5 | import de.stylextv.maple.util.RegistryUtil; 6 | import de.stylextv.maple.world.scan.ScanFilter; 7 | import de.stylextv.maple.world.scan.block.filters.BlockTypeFilter; 8 | import net.minecraft.block.Block; 9 | import net.minecraft.block.BlockState; 10 | import net.minecraft.block.CropBlock; 11 | 12 | public class BlockFilter extends ScanFilter { 13 | 14 | public static final BlockFilter ALL = new BlockFilter((state) -> { 15 | return true; 16 | }); 17 | 18 | public static final BlockFilter FULLY_GROWN = new BlockFilter((state) -> { 19 | Block block = state.getBlock(); 20 | 21 | if(!(block instanceof CropBlock)) return true; 22 | 23 | CropBlock crop = (CropBlock) block; 24 | 25 | return crop.isMature(state); 26 | }); 27 | 28 | public BlockFilter() {} 29 | 30 | public BlockFilter(Predicate predicate) { 31 | super(predicate); 32 | } 33 | 34 | public static BlockFilter fromString(String s) { 35 | Block block = RegistryUtil.getBlock(s); 36 | 37 | if(block == null) return null; 38 | 39 | return new BlockTypeFilter(block); 40 | } 41 | 42 | } 43 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/FollowCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.command.Command; 5 | import de.stylextv.maple.task.Task; 6 | import de.stylextv.maple.task.TaskManager; 7 | import de.stylextv.maple.task.tasks.FollowTask; 8 | import de.stylextv.maple.util.chat.ChatUtil; 9 | import de.stylextv.maple.world.scan.entity.EntityFilter; 10 | 11 | public class FollowCommand extends Command { 12 | 13 | private static final String[] USAGES = new String[] { 14 | "", 15 | "" 16 | }; 17 | 18 | public FollowCommand() { 19 | super("follow", "Starts following a specified entity."); 20 | } 21 | 22 | @Override 23 | public boolean execute(ArgumentList args) { 24 | if(args.hasExactly(0)) return false; 25 | 26 | String s = args.get(0); 27 | 28 | EntityFilter filter = EntityFilter.fromString(s); 29 | 30 | if(filter == null) return false; 31 | 32 | Task task = new FollowTask(filter); 33 | 34 | TaskManager.startTask(task); 35 | 36 | ChatUtil.send("Started following."); 37 | 38 | return true; 39 | } 40 | 41 | @Override 42 | public String[] getUsages() { 43 | return USAGES; 44 | } 45 | 46 | } 47 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/iterate/iterators/BoxIterator.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.iterate.iterators; 2 | 3 | import de.stylextv.maple.util.iterate.IntTriplet; 4 | import de.stylextv.maple.util.iterate.iterators.types.IntTripletIterator; 5 | 6 | public class BoxIterator extends IntTripletIterator { 7 | 8 | // TODO most common box iterators as constants 9 | 10 | private int width; 11 | private int height; 12 | private int length; 13 | 14 | public BoxIterator(int size) { 15 | this(size, size, size); 16 | } 17 | 18 | public BoxIterator(int width, int height, int length) { 19 | super(width * height * length); 20 | 21 | this.width = width; 22 | this.height = height; 23 | this.length = length; 24 | } 25 | 26 | @Override 27 | public void generate() { 28 | int m = (width * width); 29 | 30 | for(int i = 0; i < getLength(); i++) { 31 | 32 | int y = i / m; 33 | 34 | int j = i - y * m; 35 | 36 | int x = j % width; 37 | int z = j / width; 38 | 39 | set(i, new IntTriplet(x, y, z)); 40 | } 41 | } 42 | 43 | public int getWidth() { 44 | return width; 45 | } 46 | 47 | public int getHeight() { 48 | return height; 49 | } 50 | 51 | public int getLength() { 52 | return length; 53 | } 54 | 55 | } 56 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/interact/openables/OpenableDoor.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.interact.openables; 2 | 3 | import de.stylextv.maple.pathing.movement.Movement; 4 | import de.stylextv.maple.world.interact.Openable; 5 | import net.minecraft.block.Block; 6 | import net.minecraft.block.BlockState; 7 | import net.minecraft.block.Blocks; 8 | import net.minecraft.block.DoorBlock; 9 | import net.minecraft.util.math.Direction; 10 | 11 | public class OpenableDoor extends Openable { 12 | 13 | @Override 14 | public boolean matchesBlock(Block block) { 15 | return block instanceof DoorBlock; 16 | } 17 | 18 | @Override 19 | public boolean isLocked(BlockState state) { 20 | Block block = state.getBlock(); 21 | 22 | return block.equals(Blocks.IRON_DOOR); 23 | } 24 | 25 | @Override 26 | public boolean isOpen(BlockState state, Movement m) { 27 | if(m.isVerticalOnly() || m.isDiagonal()) return true; 28 | 29 | Direction dir = m.getDirection(); 30 | 31 | Direction opposite = dir.getOpposite(); 32 | 33 | Direction doorDir = state.get(DoorBlock.FACING); 34 | 35 | boolean open = state.get(DoorBlock.OPEN); 36 | 37 | boolean aligns = doorDir.equals(dir) || doorDir.equals(opposite); 38 | 39 | if(!aligns) open = !open; 40 | 41 | return open; 42 | } 43 | 44 | } 45 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/render/mesh/LineMesh.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.render.mesh; 2 | 3 | import java.util.HashMap; 4 | 5 | import de.stylextv.maple.util.world.CoordUtil; 6 | import net.minecraft.util.math.Vec3f; 7 | 8 | public class LineMesh extends Mesh { 9 | 10 | private static final HashMap MESH_CACHE = new HashMap<>(); 11 | 12 | private float dx; 13 | private float dy; 14 | private float dz; 15 | 16 | public LineMesh(float dx, float dy, float dz) { 17 | this.dx = dx; 18 | this.dy = dy; 19 | this.dz = dz; 20 | } 21 | 22 | @Override 23 | public void create() { 24 | Vec3f[] vertices = new Vec3f[2]; 25 | 26 | vertices[0] = Vec3f.ZERO; 27 | vertices[1] = new Vec3f(dx, dy, dz); 28 | 29 | setVertices(vertices); 30 | } 31 | 32 | public float getDeltaX() { 33 | return dx; 34 | } 35 | 36 | public float getDeltaY() { 37 | return dy; 38 | } 39 | 40 | public float getDeltaZ() { 41 | return dz; 42 | } 43 | 44 | public static LineMesh getMesh(int dx, int dy, int dz) { 45 | long key = CoordUtil.posAsLong(dx, dy, dz); 46 | 47 | LineMesh mesh = MESH_CACHE.get(key); 48 | 49 | if(mesh == null) { 50 | 51 | mesh = new LineMesh(dx, dy, dz); 52 | 53 | MESH_CACHE.put(key, mesh); 54 | } 55 | 56 | return mesh; 57 | } 58 | 59 | } 60 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/cache/io/serialize/CachedChunkSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.cache.io.serialize; 2 | 3 | import java.util.BitSet; 4 | 5 | import de.stylextv.maple.cache.CachedChunk; 6 | import de.stylextv.maple.io.resource.StreamedResource; 7 | import de.stylextv.maple.io.serialize.Serializer; 8 | 9 | public class CachedChunkSerializer extends Serializer { 10 | 11 | @Override 12 | public CachedChunk readFrom(StreamedResource r) { 13 | int x = Serializer.INTEGER.readFrom(r); 14 | int z = Serializer.INTEGER.readFrom(r); 15 | 16 | int height = Serializer.INTEGER.readFrom(r); 17 | int bottomY = Serializer.INTEGER.readFrom(r); 18 | 19 | BitSet bitSet = Serializer.BIT_SET.readFrom(r); 20 | 21 | return new CachedChunk(x, z, height, bottomY, bitSet); 22 | } 23 | 24 | @Override 25 | public void writeTo(StreamedResource r, CachedChunk c) { 26 | int x = c.getX(); 27 | int z = c.getZ(); 28 | 29 | int height = c.getHeight(); 30 | int bottomY = c.getBottomY(); 31 | 32 | BitSet bitSet = c.getBitSet(); 33 | 34 | Serializer.INTEGER.writeTo(r, x); 35 | Serializer.INTEGER.writeTo(r, z); 36 | 37 | Serializer.INTEGER.writeTo(r, height); 38 | Serializer.INTEGER.writeTo(r, bottomY); 39 | 40 | Serializer.BIT_SET.writeTo(r, bitSet); 41 | } 42 | 43 | } 44 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/input/target/targets/OpenableTarget.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.input.target.targets; 2 | 3 | import de.stylextv.maple.input.InputAction; 4 | import de.stylextv.maple.input.controller.InputController; 5 | import de.stylextv.maple.input.target.BlockTarget; 6 | import de.stylextv.maple.pathing.movement.Movement; 7 | import de.stylextv.maple.world.interact.Openable; 8 | import net.minecraft.block.BlockState; 9 | 10 | public class OpenableTarget extends BlockTarget { 11 | 12 | private Openable openable; 13 | 14 | public OpenableTarget(int x, int y, int z, Openable o) { 15 | super(x, y, z); 16 | 17 | updateOpenable(o); 18 | } 19 | 20 | public void updateOpenable(Openable o) { 21 | this.openable = o; 22 | } 23 | 24 | public boolean continueOpening() { 25 | if(isSelected(true)) { 26 | 27 | InputController.setPressed(InputAction.RIGHT_CLICK, true); 28 | 29 | return true; 30 | } 31 | 32 | return lookAt(false); 33 | } 34 | 35 | public boolean isLocked() { 36 | BlockState state = state(); 37 | 38 | return openable.isLocked(state); 39 | } 40 | 41 | public boolean isOpen(Movement m) { 42 | BlockState state = state(); 43 | 44 | return openable.isOpen(state, m); 45 | } 46 | 47 | public Openable getOpenable() { 48 | return openable; 49 | } 50 | 51 | } 52 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/serialize/serializers/list/ListSerializer.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.serialize.serializers.list; 2 | 3 | import java.util.ArrayList; 4 | import java.util.Arrays; 5 | import java.util.List; 6 | 7 | import de.stylextv.maple.io.resource.StreamedResource; 8 | import de.stylextv.maple.io.serialize.Serializer; 9 | 10 | public class ListSerializer> extends Serializer> { 11 | 12 | private Serializer serializer; 13 | 14 | public ListSerializer(Serializer s) { 15 | this.serializer = s; 16 | } 17 | 18 | @Override 19 | public List readFrom(StreamedResource r) { 20 | int l = Serializer.INTEGER.readFrom(r); 21 | 22 | List list = new ArrayList<>(); 23 | 24 | for(int i = 0; i < l; i++) { 25 | 26 | T t = serializer.readFrom(r); 27 | 28 | list.add(t); 29 | } 30 | 31 | return list; 32 | } 33 | 34 | public void writeTo(StreamedResource r, T[] array) { 35 | List list = Arrays.asList(array); 36 | 37 | writeTo(r, list); 38 | } 39 | 40 | @Override 41 | public void writeTo(StreamedResource r, List list) { 42 | int l = list.size(); 43 | 44 | Serializer.INTEGER.writeTo(r, l); 45 | 46 | list.forEach((t) -> serializer.writeTo(r, t)); 47 | } 48 | 49 | public Serializer getSerializer() { 50 | return serializer; 51 | } 52 | 53 | } 54 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/config/ConfigHelper.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.config; 2 | 3 | import com.google.gson.Gson; 4 | import com.google.gson.GsonBuilder; 5 | 6 | import de.stylextv.maple.io.resource.types.StreamedFile; 7 | import de.stylextv.maple.io.serialize.Serializer; 8 | 9 | public class ConfigHelper { 10 | 11 | private static final String FOLDER = "config/"; 12 | 13 | private static final String FILE_EXTENSION = ".json"; 14 | 15 | private static Gson gson; 16 | 17 | static { 18 | GsonBuilder builder = new GsonBuilder(); 19 | 20 | builder.setPrettyPrinting(); 21 | 22 | gson = builder.create(); 23 | } 24 | 25 | public static T loadFile(String path, Class clazz) { 26 | StreamedFile f = openFile(path); 27 | 28 | T t = null; 29 | 30 | if(f.exists()) { 31 | 32 | String json = Serializer.STRING.readFrom(f); 33 | 34 | t = gson.fromJson(json, clazz); 35 | } 36 | 37 | f.close(); 38 | 39 | return t; 40 | } 41 | 42 | public static void saveFile(String path, Object o) { 43 | StreamedFile f = openFile(path); 44 | 45 | String json = gson.toJson(o); 46 | 47 | Serializer.STRING.writeTo(f, json); 48 | 49 | f.close(); 50 | } 51 | 52 | private static StreamedFile openFile(String path) { 53 | String s = FOLDER + path + FILE_EXTENSION; 54 | 55 | return new StreamedFile(s, false); 56 | } 57 | 58 | } 59 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/ModifiedCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import java.util.ArrayList; 4 | import java.util.List; 5 | 6 | import de.stylextv.maple.command.ArgumentList; 7 | import de.stylextv.maple.command.Command; 8 | import de.stylextv.maple.option.Option; 9 | import de.stylextv.maple.option.Options; 10 | import de.stylextv.maple.util.chat.ChatUtil; 11 | 12 | public class ModifiedCommand extends Command { 13 | 14 | public ModifiedCommand() { 15 | super("modified", "Shows all modified options."); 16 | } 17 | 18 | @Override 19 | public boolean execute(ArgumentList args) { 20 | Integer page = 1; 21 | 22 | if(args.hasAtLeast(1)) { 23 | 24 | page = args.getInt(0); 25 | } 26 | 27 | ChatUtil.send("Modified options:"); 28 | 29 | List list = new ArrayList<>(); 30 | 31 | Option[] options = Options.getOptions(); 32 | 33 | for(Option option : options) { 34 | if(option.wasModified()) { 35 | 36 | String name = option.getName(); 37 | String type = "Boolean"; 38 | 39 | String s = String.format("§7%s §8(%s)", name, type); 40 | 41 | list.add(s); 42 | } 43 | } 44 | 45 | ChatUtil.sendList(list, 7, page, getName()); 46 | 47 | return true; 48 | } 49 | 50 | @Override 51 | public String[] getUsages() { 52 | return new String[] {"[page]"}; 53 | } 54 | 55 | } 56 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/mixin/WorldRendererMixin.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.mixin; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | import org.spongepowered.asm.mixin.injection.At; 5 | import org.spongepowered.asm.mixin.injection.Inject; 6 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 7 | 8 | import de.stylextv.maple.event.EventBus; 9 | import de.stylextv.maple.event.events.RenderWorldEvent; 10 | import net.minecraft.client.render.Camera; 11 | import net.minecraft.client.render.GameRenderer; 12 | import net.minecraft.client.render.LightmapTextureManager; 13 | import net.minecraft.client.render.WorldRenderer; 14 | import net.minecraft.client.util.math.MatrixStack; 15 | import net.minecraft.util.math.Matrix4f; 16 | 17 | @Mixin(WorldRenderer.class) 18 | public class WorldRendererMixin { 19 | 20 | @Inject( 21 | method = "render", 22 | at = @At( 23 | value = "INVOKE", 24 | target = "net/minecraft/client/render/BufferBuilderStorage.getEntityVertexConsumers()Lnet/minecraft/client/render/VertexConsumerProvider$Immediate;" 25 | ) 26 | ) 27 | private void render(MatrixStack stack, float tickDelta, long limitTime, boolean renderBlockOutline, Camera camera, GameRenderer gameRenderer, LightmapTextureManager textureManager, Matrix4f matrix, CallbackInfo info) { 28 | EventBus.onEvent(new RenderWorldEvent(RenderWorldEvent.Type.ENTITIES, stack)); 29 | } 30 | 31 | } 32 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/task/tasks/FollowTask.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.task.tasks; 2 | 3 | import java.util.List; 4 | 5 | import de.stylextv.maple.pathing.calc.goal.CompositeGoal; 6 | import de.stylextv.maple.pathing.calc.goal.NearGoal; 7 | import de.stylextv.maple.util.chat.ChatUtil; 8 | import de.stylextv.maple.world.scan.entity.EntityFilter; 9 | import de.stylextv.maple.world.scan.entity.EntityFilters; 10 | import de.stylextv.maple.world.scan.entity.EntityScanner; 11 | import net.minecraft.entity.Entity; 12 | 13 | public class FollowTask extends CompositeTask { 14 | 15 | private static final float FOLLOW_DISTANCE = 3f; 16 | 17 | private EntityFilters filters; 18 | 19 | public FollowTask(EntityFilter filter) { 20 | super(false); 21 | 22 | this.filters = EntityFilters.fromFilters(filter, EntityFilter.ALIVE); 23 | } 24 | 25 | @Override 26 | public CompositeGoal onRenderTick() { 27 | List entities = EntityScanner.scanWorld(filters); 28 | 29 | return CompositeGoal.fromCollection(entities, e -> new NearGoal(e.getBlockPos(), FOLLOW_DISTANCE)); 30 | } 31 | 32 | @Override 33 | public void onFail() { 34 | ChatUtil.send("Can't get any closer to entities."); 35 | } 36 | 37 | @Override 38 | public void onEmptyGoal() { 39 | ChatUtil.send("Can't find any matching entities nearby."); 40 | } 41 | 42 | public EntityFilters getFilters() { 43 | return filters; 44 | } 45 | 46 | } 47 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/task/tasks/ScanTask.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.task.tasks; 2 | 3 | import java.util.function.Consumer; 4 | 5 | import de.stylextv.maple.util.async.AsyncUtil; 6 | import de.stylextv.maple.world.scan.block.BlockFilters; 7 | import de.stylextv.maple.world.scan.block.BlockScanner; 8 | import net.minecraft.util.math.BlockPos; 9 | 10 | public abstract class ScanTask extends CompositeTask { 11 | 12 | private static final long SCAN_EXPIRATION_TIME = 5000; 13 | 14 | private BlockFilters filters; 15 | 16 | private boolean scanning; 17 | 18 | private long scanEndTime; 19 | 20 | public ScanTask(BlockFilters filters, boolean completeAtGoal) { 21 | super(completeAtGoal); 22 | 23 | this.filters = filters; 24 | } 25 | 26 | public void rescan(Consumer consumer) { 27 | if(scanning) return; 28 | 29 | scanning = true; 30 | 31 | AsyncUtil.runAsync(() -> { 32 | 33 | BlockScanner.scanWorld(filters, consumer); 34 | 35 | scanEndTime = System.currentTimeMillis(); 36 | 37 | scanning = false; 38 | }); 39 | } 40 | 41 | public boolean hasScanExpired() { 42 | long now = System.currentTimeMillis(); 43 | 44 | long elapsedTime = now - scanEndTime; 45 | 46 | return elapsedTime > SCAN_EXPIRATION_TIME; 47 | } 48 | 49 | public boolean isScanning() { 50 | return scanning; 51 | } 52 | 53 | public BlockFilters getFilters() { 54 | return filters; 55 | } 56 | 57 | } 58 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/interact/Openable.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.interact; 2 | 3 | import de.stylextv.maple.pathing.movement.Movement; 4 | import de.stylextv.maple.world.interact.openables.OpenableDoor; 5 | import de.stylextv.maple.world.interact.openables.OpenableFenceGate; 6 | import de.stylextv.maple.world.interact.openables.OpenableTrapdoor; 7 | import net.minecraft.block.Block; 8 | import net.minecraft.block.BlockState; 9 | 10 | public abstract class Openable { 11 | 12 | public static final Openable DOOR = new OpenableDoor(); 13 | 14 | public static final Openable TRAPDOOR = new OpenableTrapdoor(); 15 | 16 | public static final Openable FENCE_GATE = new OpenableFenceGate(); 17 | 18 | private static final Openable[] OPENABLES = new Openable[] { 19 | DOOR, TRAPDOOR, FENCE_GATE 20 | }; 21 | 22 | public abstract boolean matchesBlock(Block block); 23 | 24 | public abstract boolean isLocked(BlockState state); 25 | 26 | public abstract boolean isOpen(BlockState state, Movement m); 27 | 28 | public static Openable fromState(BlockState state) { 29 | Block block = state.getBlock(); 30 | 31 | return fromBlock(block); 32 | } 33 | 34 | public static Openable fromBlock(Block block) { 35 | for(Openable o : OPENABLES) { 36 | 37 | if(o.matchesBlock(block)) return o; 38 | } 39 | 40 | return null; 41 | } 42 | 43 | public static Openable[] getOpenables() { 44 | return OPENABLES; 45 | } 46 | 47 | } 48 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/moves/DescendMove.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.moves; 2 | 3 | import de.stylextv.maple.cache.block.BlockType; 4 | import de.stylextv.maple.pathing.calc.Node; 5 | import de.stylextv.maple.pathing.calc.PathFinder; 6 | import de.stylextv.maple.pathing.movement.Move; 7 | import de.stylextv.maple.pathing.movement.Movement; 8 | import de.stylextv.maple.pathing.movement.movements.DescendMovement; 9 | import de.stylextv.maple.pathing.movement.movements.FallMovement; 10 | 11 | public class DescendMove extends Move { 12 | 13 | public DescendMove(int x, int y, int z) { 14 | super(x, y, z); 15 | } 16 | 17 | @Override 18 | public Movement apply(Node n, PathFinder finder) { 19 | int dx = getDeltaX(); 20 | int dy = getDeltaY(); 21 | int dz = getDeltaZ(); 22 | 23 | Node destination; 24 | 25 | while(true) { 26 | 27 | destination = finder.getAdjacentNode(n, dx, dy, dz); 28 | 29 | if(destination.getY() <= 0 || destination.getType() == BlockType.WATER) break; 30 | 31 | Node below = finder.getAdjacentNode(n, dx, dy - 1, dz); 32 | 33 | BlockType type = below.getType(); 34 | 35 | if(!type.isPassable()) break; 36 | 37 | dy--; 38 | } 39 | 40 | int fallDistance = n.getY() - destination.getY(); 41 | 42 | if(fallDistance == 1) return new DescendMovement(n, destination); 43 | 44 | return new FallMovement(n, destination, fallDistance); 45 | } 46 | 47 | } 48 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/task/TaskManager.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.task; 2 | 3 | import de.stylextv.maple.pathing.PathingCommand; 4 | import de.stylextv.maple.pathing.PathingExecutor; 5 | import de.stylextv.maple.pathing.PathingStatus; 6 | import de.stylextv.maple.pathing.calc.goal.Goal; 7 | import de.stylextv.maple.task.tasks.CustomGoalTask; 8 | 9 | public class TaskManager { 10 | 11 | private static Task task; 12 | 13 | public static void gotoGoal(Goal goal) { 14 | Task task = new CustomGoalTask(goal); 15 | 16 | startTask(task); 17 | } 18 | 19 | public static void startTask(Task t) { 20 | if(hasTask()) stopTask(); 21 | 22 | task = t; 23 | 24 | resumeTask(); 25 | } 26 | 27 | public static void stopTask() { 28 | pauseTask(); 29 | 30 | task = null; 31 | } 32 | 33 | public static void pauseTask() { 34 | task.pause(); 35 | } 36 | 37 | public static void resumeTask() { 38 | task.resume(); 39 | } 40 | 41 | public static void onRenderTick() { 42 | PathingCommand c = null; 43 | 44 | if(hasTask() && !task.isPaused()) { 45 | 46 | PathingStatus status = PathingExecutor.getStatus(); 47 | 48 | c = task.onRenderTick(status); 49 | 50 | if(c == null) stopTask(); 51 | } 52 | 53 | PathingExecutor.processCommand(c); 54 | } 55 | 56 | public static boolean hasTask() { 57 | return task != null; 58 | } 59 | 60 | public static Task getTask() { 61 | return task; 62 | } 63 | 64 | } 65 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/calc/goal/NearGoal.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.calc.goal; 2 | 3 | import de.stylextv.maple.pathing.calc.Node; 4 | import net.minecraft.util.math.BlockPos; 5 | 6 | public class NearGoal extends Goal { 7 | 8 | private BlockPos pos; 9 | 10 | private float dis; 11 | 12 | public NearGoal(int x, int y, int z, float dis) { 13 | this(new BlockPos(x, y, z), dis); 14 | } 15 | 16 | public NearGoal(BlockPos pos, float dis) { 17 | this.pos = pos; 18 | this.dis = dis * dis; 19 | } 20 | 21 | @Override 22 | public double heuristic(Node n) { 23 | int dx = n.getX() - pos.getX(); 24 | int dy = n.getY() - pos.getY(); 25 | int dz = n.getZ() - pos.getZ(); 26 | 27 | return BlockGoal.cost(dx, dy, dz); 28 | } 29 | 30 | @Override 31 | public boolean isFinalNode(Node n) { 32 | return n.squaredDistanceTo(pos) <= dis; 33 | } 34 | 35 | @Override 36 | public boolean equals(Goal other) { 37 | if(!(other instanceof NearGoal)) return false; 38 | 39 | NearGoal g = (NearGoal) other; 40 | 41 | BlockPos otherPos = g.getPos(); 42 | float otherDis = g.getDistance(); 43 | 44 | return otherPos.equals(pos) && otherDis == dis; 45 | } 46 | 47 | public BlockPos getPos() { 48 | return pos; 49 | } 50 | 51 | public float getDistance() { 52 | return dis; 53 | } 54 | 55 | @Override 56 | public String toString() { 57 | return String.format("NearGoal{pos=%s, dis=%s}", pos, dis); 58 | } 59 | 60 | } 61 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/ThisWayCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.command.Command; 5 | import de.stylextv.maple.context.PlayerContext; 6 | import de.stylextv.maple.pathing.calc.goal.Goal; 7 | import de.stylextv.maple.pathing.calc.goal.XZGoal; 8 | import de.stylextv.maple.task.TaskManager; 9 | import de.stylextv.maple.util.chat.ChatUtil; 10 | import net.minecraft.client.network.ClientPlayerEntity; 11 | import net.minecraft.util.math.BlockPos; 12 | 13 | public class ThisWayCommand extends Command { 14 | 15 | private static final int DEFAULT_DISTANCE = 1000; 16 | 17 | public ThisWayCommand() { 18 | super("thisway", "Move a specified number of blocks in the direction you are facing.", "forward"); 19 | } 20 | 21 | @Override 22 | public boolean execute(ArgumentList args) { 23 | int dis = DEFAULT_DISTANCE; 24 | 25 | if(args.hasAtLeast(1)) { 26 | 27 | dis = args.getInt(0); 28 | } 29 | 30 | BlockPos pos = PlayerContext.feetPosition(); 31 | 32 | ClientPlayerEntity p = PlayerContext.player(); 33 | 34 | float yaw = p.getYaw(); 35 | 36 | Goal goal = XZGoal.inDirection(pos, yaw, dis); 37 | 38 | TaskManager.gotoGoal(goal); 39 | 40 | ChatUtil.send("Started."); 41 | 42 | return true; 43 | } 44 | 45 | @Override 46 | public String[] getUsages() { 47 | return new String[] {"[distance]"}; 48 | } 49 | 50 | } 51 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/helper/JumpHelper.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.helper; 2 | 3 | import de.stylextv.maple.context.PlayerContext; 4 | import de.stylextv.maple.input.controller.AwarenessController; 5 | import de.stylextv.maple.pathing.calc.Node; 6 | import de.stylextv.maple.pathing.movement.Movement; 7 | import de.stylextv.maple.util.world.CollisionUtil; 8 | import net.minecraft.util.math.Box; 9 | import net.minecraft.util.math.Vec3d; 10 | 11 | public class JumpHelper extends MovementHelper { 12 | 13 | private static final Box COLLISION_BOX = new Box(-0.5, 0.6, -0.5, 0.5, 1.5, 0.5); 14 | 15 | public JumpHelper(Movement m) { 16 | super(m); 17 | } 18 | 19 | public boolean shouldJump() { 20 | if(!canJump()) return false; 21 | 22 | return isCollisionAhead(); 23 | } 24 | 25 | private boolean isCollisionAhead() { 26 | Node source = getSource(); 27 | Node destination = getDestination(); 28 | 29 | double x = (source.getX() + destination.getX() + 1) * 0.5; 30 | double z = (source.getZ() + destination.getZ() + 1) * 0.5; 31 | 32 | Vec3d v = PlayerContext.position(); 33 | 34 | double y = Math.max(v.getY(), source.getY()); 35 | 36 | if(y >= destination.getY()) return false; 37 | 38 | Box box = COLLISION_BOX.offset(x, y, z); 39 | 40 | return CollisionUtil.collidesWithBlocks(box); 41 | } 42 | 43 | public boolean canJump() { 44 | return AwarenessController.canJump(); 45 | } 46 | 47 | } 48 | -------------------------------------------------------------------------------- /.github/workflows/build.yml: -------------------------------------------------------------------------------- 1 | # Automatically build the project and run any configured tests for every push 2 | # and submitted pull request. This can help catch issues that only occur on 3 | # certain platforms or Java versions, and provides a first line of defence 4 | # against bad commits. 5 | 6 | name: build 7 | on: [pull_request, push] 8 | 9 | jobs: 10 | build: 11 | strategy: 12 | matrix: 13 | # Use these Java versions 14 | java: [ 15 | 17, # Current Java LTS & minimum supported by Minecraft 16 | ] 17 | # and run on both Linux and Windows 18 | os: [ubuntu-20.04, windows-2022] 19 | runs-on: ${{ matrix.os }} 20 | steps: 21 | - name: checkout repository 22 | uses: actions/checkout@v2 23 | - name: validate gradle wrapper 24 | uses: gradle/wrapper-validation-action@v1 25 | - name: setup jdk ${{ matrix.java }} 26 | uses: actions/setup-java@v1 27 | with: 28 | java-version: ${{ matrix.java }} 29 | - name: make gradle wrapper executable 30 | if: ${{ runner.os != 'Windows' }} 31 | run: chmod +x ./gradlew 32 | - name: build 33 | run: ./gradlew build 34 | - name: capture build artifacts 35 | if: ${{ runner.os == 'Linux' && matrix.java == '17' }} # Only upload artifacts built from latest java on one OS 36 | uses: actions/upload-artifact@v2 37 | with: 38 | name: Artifacts 39 | path: build/libs/ 40 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/mixin/MinecraftClientMixin.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.mixin; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | import org.spongepowered.asm.mixin.injection.At; 5 | import org.spongepowered.asm.mixin.injection.Inject; 6 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 7 | 8 | import de.stylextv.maple.context.WorldContext; 9 | import de.stylextv.maple.event.EventBus; 10 | import de.stylextv.maple.event.events.TickEvent; 11 | import de.stylextv.maple.event.events.WorldEvent; 12 | import net.minecraft.client.MinecraftClient; 13 | import net.minecraft.client.gui.screen.Screen; 14 | import net.minecraft.client.world.ClientWorld; 15 | 16 | @Mixin(MinecraftClient.class) 17 | public class MinecraftClientMixin { 18 | 19 | @Inject(method = "tick()V", at = @At("HEAD")) 20 | private void tick(CallbackInfo info) { 21 | EventBus.onEvent(new TickEvent(TickEvent.Type.CLIENT)); 22 | } 23 | 24 | @Inject(method = "joinWorld(Lnet/minecraft/client/world/ClientWorld;)V", at = @At("TAIL")) 25 | private void joinWorld(ClientWorld world, CallbackInfo info) { 26 | EventBus.onEvent(new WorldEvent(WorldEvent.Type.LOAD, world)); 27 | } 28 | 29 | @Inject(method = "disconnect(Lnet/minecraft/client/gui/screen/Screen;)V", at = @At("HEAD")) 30 | private void disconnect(Screen screen, CallbackInfo info) { 31 | ClientWorld world = WorldContext.world(); 32 | 33 | if(world != null) EventBus.onEvent(new WorldEvent(WorldEvent.Type.UNLOAD, world)); 34 | } 35 | 36 | } 37 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/task/Task.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.task; 2 | 3 | import java.util.List; 4 | import java.util.concurrent.CopyOnWriteArrayList; 5 | 6 | import de.stylextv.maple.pathing.PathingCommand; 7 | import de.stylextv.maple.pathing.PathingExecutor; 8 | import de.stylextv.maple.pathing.PathingStatus; 9 | 10 | public abstract class Task { 11 | 12 | private Task parent; 13 | 14 | private List children = new CopyOnWriteArrayList<>(); 15 | 16 | private boolean paused = true; 17 | 18 | public void pause() { 19 | if(isPaused()) return; 20 | 21 | paused = true; 22 | 23 | PathingExecutor.stopPathing(); 24 | } 25 | 26 | public void resume() { 27 | paused = false; 28 | } 29 | 30 | public void appendTask(Task t) { 31 | children.add(t); 32 | 33 | t.setParent(this); 34 | } 35 | 36 | public PathingCommand onRenderTick(PathingStatus status) { 37 | pause(); 38 | 39 | for(Task t : children) { 40 | 41 | PathingCommand c = t.onRenderTick(status); 42 | 43 | if(c != null) return c; 44 | 45 | children.remove(t); 46 | } 47 | 48 | return null; 49 | } 50 | 51 | public boolean hasChildren() { 52 | return !children.isEmpty(); 53 | } 54 | 55 | public Task getParent() { 56 | return parent; 57 | } 58 | 59 | public void setParent(Task parent) { 60 | this.parent = parent; 61 | } 62 | 63 | public List getChildren() { 64 | return children; 65 | } 66 | 67 | public boolean isPaused() { 68 | return paused; 69 | } 70 | 71 | } 72 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/movements/DescendMovement.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.movements; 2 | 3 | import de.stylextv.maple.context.PlayerContext; 4 | import de.stylextv.maple.input.InputAction; 5 | import de.stylextv.maple.pathing.calc.Cost; 6 | import de.stylextv.maple.pathing.calc.Node; 7 | import de.stylextv.maple.pathing.movement.Movement; 8 | 9 | public class DescendMovement extends Movement { 10 | 11 | public DescendMovement(Node source, Node destination) { 12 | super(source, destination); 13 | } 14 | 15 | @Override 16 | public void updateHelpers() { 17 | int height = 3; 18 | 19 | if(isVerticalOnly()) height = 1; 20 | 21 | getBreakHelper().collectBlocks(getDestination(), height); 22 | 23 | getInteractHelper().collectDefaultBlocks(); 24 | } 25 | 26 | @Override 27 | public double cost() { 28 | double cost = isVerticalOnly() ? Cost.FALL_N_BLOCKS[1] : 0; 29 | 30 | cost += getBreakHelper().cost(); 31 | cost += getInteractHelper().cost(); 32 | 33 | return cost + super.cost(); 34 | } 35 | 36 | @Override 37 | public void onRenderTick() { 38 | boolean interacting = getBreakHelper().onRenderTick() || getInteractHelper().onRenderTick(); 39 | 40 | if(interacting) return; 41 | 42 | boolean lookDown = isVerticalOnly(); 43 | 44 | lookAt(getDestination(), lookDown); 45 | 46 | if(isVerticalOnly() && !PlayerContext.isOnGround()) return; 47 | 48 | setPressed(InputAction.MOVE_FORWARD, true); 49 | setPressed(InputAction.SPRINT, true); 50 | } 51 | 52 | } 53 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/GotoCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import de.stylextv.maple.command.ArgumentList; 4 | import de.stylextv.maple.command.Command; 5 | import de.stylextv.maple.pathing.calc.goal.Goal; 6 | import de.stylextv.maple.task.Task; 7 | import de.stylextv.maple.task.TaskManager; 8 | import de.stylextv.maple.task.tasks.GetToBlockTask; 9 | import de.stylextv.maple.util.chat.ChatUtil; 10 | import de.stylextv.maple.world.scan.block.BlockFilter; 11 | 12 | public class GotoCommand extends Command { 13 | 14 | private static final String[] USAGES = new String[] { 15 | " [radius]", 16 | " ", 17 | "", 18 | "" 19 | }; 20 | 21 | public GotoCommand() { 22 | super("goto", "Starts moving to a custom goal."); 23 | } 24 | 25 | @Override 26 | public boolean execute(ArgumentList args) { 27 | if(args.hasExactly(0)) return false; 28 | 29 | String s = args.get(0); 30 | 31 | BlockFilter filter = BlockFilter.fromString(s); 32 | 33 | if(filter != null) { 34 | 35 | Task task = new GetToBlockTask(filter); 36 | 37 | TaskManager.startTask(task); 38 | 39 | ChatUtil.send("Started."); 40 | 41 | return true; 42 | } 43 | 44 | Goal goal = Goal.fromArgs(args); 45 | 46 | if(goal == null) return false; 47 | 48 | TaskManager.gotoGoal(goal); 49 | 50 | ChatUtil.send("Started."); 51 | 52 | return true; 53 | } 54 | 55 | @Override 56 | public String[] getUsages() { 57 | return USAGES; 58 | } 59 | 60 | } 61 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/scheme/Color.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.scheme; 2 | 3 | import net.minecraft.util.math.Vector4f; 4 | 5 | public class Color { 6 | 7 | private int r; 8 | private int g; 9 | private int b; 10 | private int a; 11 | 12 | public Color(int r, int g, int b) { 13 | this(r, g, b, 255); 14 | } 15 | 16 | public Color(int r, int g, int b, int a) { 17 | this.r = r; 18 | this.g = g; 19 | this.b = b; 20 | this.a = a; 21 | } 22 | 23 | public int asRGB() { 24 | int rgb = a; 25 | rgb = (rgb << 8) + r; 26 | rgb = (rgb << 8) + g; 27 | rgb = (rgb << 8) + b; 28 | 29 | return rgb; 30 | } 31 | 32 | public Vector4f asVector() { 33 | float x = r / 255f; 34 | float y = g / 255f; 35 | float z = b / 255f; 36 | float w = a / 255f; 37 | 38 | return new Vector4f(x, y, z, w); 39 | } 40 | 41 | public int getRed() { 42 | return r; 43 | } 44 | 45 | public int getGreen() { 46 | return g; 47 | } 48 | 49 | public int getBlue() { 50 | return b; 51 | } 52 | 53 | public int getAlpha() { 54 | return a; 55 | } 56 | 57 | public static Color blend(Color c1, Color c2, float f) { 58 | int r = blendComponents(c1.getRed(), c2.getRed(), f); 59 | int g = blendComponents(c1.getGreen(), c2.getGreen(), f); 60 | int b = blendComponents(c1.getBlue(), c2.getBlue(), f); 61 | int a = blendComponents(c1.getAlpha(), c2.getAlpha(), f); 62 | 63 | return new Color(r, g, b, a); 64 | } 65 | 66 | private static int blendComponents(int i1, int i2, float f) { 67 | return Math.round(i1 + (i2 - i1) * f); 68 | } 69 | 70 | } 71 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/Maple.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple; 2 | 3 | import de.stylextv.maple.event.EventBus; 4 | import de.stylextv.maple.event.listeners.ChatListener; 5 | import de.stylextv.maple.event.listeners.PlayerListener; 6 | import de.stylextv.maple.event.listeners.RenderListener; 7 | import de.stylextv.maple.event.listeners.TickListener; 8 | import de.stylextv.maple.event.listeners.WorldListener; 9 | import de.stylextv.maple.option.Options; 10 | import de.stylextv.maple.waypoint.Waypoints; 11 | import net.fabricmc.api.ModInitializer; 12 | 13 | public class Maple implements ModInitializer { 14 | 15 | private static Maple instance; 16 | 17 | private Options options; 18 | 19 | public Maple() { 20 | instance = this; 21 | } 22 | 23 | @Override 24 | public void onInitialize() { 25 | registerListeners(); 26 | 27 | loadConfigs(); 28 | 29 | // init 30 | } 31 | 32 | private void registerListeners() { 33 | EventBus.registerListener(new TickListener()); 34 | EventBus.registerListener(new WorldListener()); 35 | EventBus.registerListener(new RenderListener()); 36 | EventBus.registerListener(new PlayerListener()); 37 | EventBus.registerListener(new ChatListener()); 38 | } 39 | 40 | private void loadConfigs() { 41 | options = Options.load(); 42 | 43 | if(options == null) { 44 | options = new Options(); 45 | 46 | options.save(); 47 | } 48 | 49 | Waypoints.load(); 50 | } 51 | 52 | public Options getOptions() { 53 | return options; 54 | } 55 | 56 | public static Maple getInstance() { 57 | return instance; 58 | } 59 | 60 | } 61 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/EventListener.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event; 2 | 3 | import de.stylextv.maple.event.events.BlockUpdateEvent; 4 | import de.stylextv.maple.event.events.ChunkEvent; 5 | import de.stylextv.maple.event.events.ClientChatEvent; 6 | import de.stylextv.maple.event.events.EntityDeathEvent; 7 | import de.stylextv.maple.event.events.EntitySleptEvent; 8 | import de.stylextv.maple.event.events.InventoryUpdateEvent; 9 | import de.stylextv.maple.event.events.PacketEvent; 10 | import de.stylextv.maple.event.events.RenderWorldEvent; 11 | import de.stylextv.maple.event.events.TickEvent; 12 | import de.stylextv.maple.event.events.WorldEvent; 13 | 14 | public interface EventListener { 15 | 16 | public default void onClientTick(TickEvent event) {} 17 | 18 | public default void onRenderTick(TickEvent event) {} 19 | 20 | public default void onEntitiesRender(RenderWorldEvent event) {} 21 | 22 | public default void onWorldLoad(WorldEvent event) {} 23 | 24 | public default void onWorldUnload(WorldEvent event) {} 25 | 26 | public default void onChunkData(ChunkEvent event) {} 27 | 28 | public default void onBlockUpdate(BlockUpdateEvent event) {} 29 | 30 | public default void onPacketSent(PacketEvent event) {} 31 | 32 | public default void onPacketReceived(PacketEvent event) {} 33 | 34 | public default void onInventoryUpdate(InventoryUpdateEvent event) {} 35 | 36 | public default void onEntityDeath(EntityDeathEvent event) {} 37 | 38 | public default void onEntitySlept(EntitySleptEvent event) {} 39 | 40 | public default void onClientChat(ClientChatEvent event) {} 41 | 42 | } 43 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/movements/ParkourMovement.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.movements; 2 | 3 | import de.stylextv.maple.input.InputAction; 4 | import de.stylextv.maple.pathing.calc.Node; 5 | import de.stylextv.maple.pathing.movement.Movement; 6 | import de.stylextv.maple.pathing.movement.helper.ParkourHelper; 7 | 8 | public class ParkourMovement extends Movement { 9 | 10 | private int dx; 11 | private int dy; 12 | private int dz; 13 | 14 | private int distance; 15 | 16 | private ParkourHelper parkourHelper = new ParkourHelper(this); 17 | 18 | public ParkourMovement(Node source, Node destination, int dx, int dy, int dz, int distance) { 19 | super(source, destination); 20 | 21 | this.dx = dx; 22 | this.dy = dy; 23 | this.dz = dz; 24 | this.distance = distance; 25 | } 26 | 27 | @Override 28 | public double cost() { 29 | double cost = parkourHelper.cost(); 30 | 31 | return cost + super.cost(); 32 | } 33 | 34 | @Override 35 | public void onRenderTick() { 36 | boolean sprint = parkourHelper.shouldSprint(); 37 | 38 | setPressed(InputAction.SPRINT, sprint); 39 | 40 | boolean prepared = getPositionHelper().prepareParkourJump(); 41 | 42 | if(!prepared) return; 43 | 44 | boolean jump = getJumpHelper().canJump(); 45 | 46 | setPressed(InputAction.JUMP, jump); 47 | } 48 | 49 | public int getDeltaX() { 50 | return dx; 51 | } 52 | 53 | public int getDeltaY() { 54 | return dy; 55 | } 56 | 57 | public int getDeltaZ() { 58 | return dz; 59 | } 60 | 61 | public int getDistance() { 62 | return distance; 63 | } 64 | 65 | } 66 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/input/target/targets/BreakableTarget.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.input.target.targets; 2 | 3 | import de.stylextv.maple.gui.ToolSet; 4 | import de.stylextv.maple.input.InputAction; 5 | import de.stylextv.maple.input.controller.AwarenessController; 6 | import de.stylextv.maple.input.controller.BreakController; 7 | import de.stylextv.maple.input.controller.GuiController; 8 | import de.stylextv.maple.input.controller.InputController; 9 | import de.stylextv.maple.input.target.BlockTarget; 10 | import de.stylextv.maple.world.BlockInterface; 11 | import net.minecraft.block.BlockState; 12 | import net.minecraft.item.ItemStack; 13 | import net.minecraft.util.math.BlockPos; 14 | 15 | public class BreakableTarget extends BlockTarget { 16 | 17 | public BreakableTarget(int x, int y, int z) { 18 | super(x, y, z); 19 | } 20 | 21 | public BreakableTarget(BlockPos pos) { 22 | super(pos); 23 | } 24 | 25 | public boolean continueBreaking(boolean onlyIfSafe) { 26 | boolean unsafe = onlyIfSafe && !AwarenessController.isSafeToBreak(getPos()); 27 | 28 | if(unsafe || !lookAt(false)) return false; 29 | 30 | BlockPos pos = AwarenessController.getTargetedPos(); 31 | 32 | if(pos == null) return true; 33 | 34 | BlockState state = BlockInterface.getState(pos); 35 | 36 | ToolSet tools = ToolSet.getTools(); 37 | 38 | ItemStack stack = tools.getBestTool(state); 39 | 40 | GuiController.selectItem(stack); 41 | 42 | InputController.setPressed(InputAction.LEFT_CLICK, true); 43 | 44 | return true; 45 | } 46 | 47 | public boolean isBroken() { 48 | BlockPos pos = getPos(); 49 | 50 | return !BreakController.isBreakable(pos); 51 | } 52 | 53 | } 54 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/waypoint/Waypoint.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.waypoint; 2 | 3 | import de.stylextv.maple.context.PlayerContext; 4 | import de.stylextv.maple.context.WorldContext; 5 | import de.stylextv.maple.util.time.TimeFormat; 6 | import net.minecraft.util.math.BlockPos; 7 | 8 | public class Waypoint { 9 | 10 | private String name; 11 | 12 | private WaypointTag tag; 13 | 14 | private String levelName; 15 | 16 | private BlockPos pos; 17 | 18 | private long timeStamp; 19 | 20 | public Waypoint(String name, WaypointTag tag, String levelName, BlockPos pos) { 21 | this.name = name; 22 | this.tag = tag; 23 | this.levelName = levelName; 24 | this.pos = pos; 25 | 26 | this.timeStamp = System.currentTimeMillis(); 27 | } 28 | 29 | public double distance() { 30 | double dis = squaredDistance(); 31 | 32 | return Math.sqrt(dis); 33 | } 34 | 35 | public double squaredDistance() { 36 | if(!isInWorld()) return Double.POSITIVE_INFINITY; 37 | 38 | return PlayerContext.squaredDistanceTo(pos); 39 | } 40 | 41 | public boolean isInWorld() { 42 | String name = WorldContext.getLevelName(); 43 | 44 | return levelName.equals(name); 45 | } 46 | 47 | public String getDisplayName() { 48 | String date = TimeFormat.formatDate(timeStamp); 49 | 50 | return name + " §8@ " + date; 51 | } 52 | 53 | public String getName() { 54 | return name; 55 | } 56 | 57 | public WaypointTag getTag() { 58 | return tag; 59 | } 60 | 61 | public String getLevelName() { 62 | return levelName; 63 | } 64 | 65 | public BlockPos getPos() { 66 | return pos; 67 | } 68 | 69 | public long getTimeStamp() { 70 | return timeStamp; 71 | } 72 | 73 | } 74 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/calc/goal/GetToBlockGoal.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.calc.goal; 2 | 3 | import de.stylextv.maple.event.events.RenderWorldEvent; 4 | import de.stylextv.maple.pathing.calc.Node; 5 | import de.stylextv.maple.render.ShapeRenderer; 6 | import de.stylextv.maple.scheme.Colors; 7 | import net.minecraft.util.math.BlockPos; 8 | 9 | public class GetToBlockGoal extends Goal { 10 | 11 | private BlockPos pos; 12 | 13 | public GetToBlockGoal(int x, int y, int z) { 14 | this(new BlockPos(x, y, z)); 15 | } 16 | 17 | public GetToBlockGoal(BlockPos pos) { 18 | this.pos = pos; 19 | } 20 | 21 | @Override 22 | public double heuristic(Node n) { 23 | int dx = n.getX() - pos.getX(); 24 | int dy = n.getY() - pos.getY(); 25 | int dz = n.getZ() - pos.getZ(); 26 | 27 | return BlockGoal.cost(dx, dy, dz); 28 | } 29 | 30 | @Override 31 | public boolean isFinalNode(Node n) { 32 | int disX = Math.abs(n.getX() - pos.getX()); 33 | int disY = Math.abs(n.getY() - pos.getY()); 34 | int disZ = Math.abs(n.getZ() - pos.getZ()); 35 | 36 | int dis = disX + disY + disZ; 37 | 38 | return dis < 2; 39 | } 40 | 41 | @Override 42 | public void render(RenderWorldEvent event) { 43 | ShapeRenderer.drawBox(event, pos, Colors.GOAL, 2); 44 | } 45 | 46 | @Override 47 | public boolean equals(Goal other) { 48 | if(!(other instanceof GetToBlockGoal)) return false; 49 | 50 | BlockPos otherPos = ((GetToBlockGoal) other).getPos(); 51 | 52 | return otherPos.equals(pos); 53 | } 54 | 55 | @Override 56 | public String toString() { 57 | return String.format("GetToBlockGoal{pos=%s}", pos); 58 | } 59 | 60 | public BlockPos getPos() { 61 | return pos; 62 | } 63 | 64 | } 65 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/task/tasks/CompositeTask.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.task.tasks; 2 | 3 | import de.stylextv.maple.pathing.PathingCommand; 4 | import de.stylextv.maple.pathing.PathingCommandType; 5 | import de.stylextv.maple.pathing.PathingStatus; 6 | import de.stylextv.maple.pathing.calc.goal.CompositeGoal; 7 | import de.stylextv.maple.task.Task; 8 | 9 | public abstract class CompositeTask extends Task { 10 | 11 | private boolean completeAtGoal; 12 | 13 | public CompositeTask(boolean completeAtGoal) { 14 | this.completeAtGoal = completeAtGoal; 15 | } 16 | 17 | public abstract CompositeGoal onRenderTick(); 18 | 19 | public void onComplete() {} 20 | 21 | public abstract void onFail(); 22 | 23 | public abstract void onEmptyGoal(); 24 | 25 | @Override 26 | public PathingCommand onRenderTick(PathingStatus status) { 27 | CompositeGoal goal = onRenderTick(); 28 | 29 | if(goal == null) return PathingCommand.PAUSE; 30 | 31 | boolean empty = goal.isEmpty(); 32 | 33 | if(empty) { 34 | 35 | onEmptyGoal(); 36 | 37 | return super.onRenderTick(status); 38 | } 39 | 40 | boolean atGoal = status.isAtGoal() && status.destinationMatches(goal); 41 | 42 | if(atGoal) { 43 | 44 | if(!completeAtGoal) return PathingCommand.DEFER; 45 | 46 | onComplete(); 47 | 48 | return super.onRenderTick(status); 49 | } 50 | 51 | if(!status.goalMatches(goal)) return new PathingCommand(PathingCommandType.REVALIDATE_GOAL, goal); 52 | 53 | if(status.isPathing()) return PathingCommand.DEFER; 54 | 55 | onFail(); 56 | 57 | return super.onRenderTick(status); 58 | } 59 | 60 | public boolean isCompleteAtGoal() { 61 | return completeAtGoal; 62 | } 63 | 64 | } 65 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/event/listeners/WorldListener.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.event.listeners; 2 | 3 | import de.stylextv.maple.cache.CacheManager; 4 | import de.stylextv.maple.cache.CachedWorld; 5 | import de.stylextv.maple.context.WorldContext; 6 | import de.stylextv.maple.event.EventListener; 7 | import de.stylextv.maple.event.events.BlockUpdateEvent; 8 | import de.stylextv.maple.event.events.ChunkEvent; 9 | import de.stylextv.maple.event.events.WorldEvent; 10 | import net.minecraft.client.world.ClientWorld; 11 | import net.minecraft.util.math.BlockPos; 12 | import net.minecraft.world.chunk.ChunkStatus; 13 | import net.minecraft.world.chunk.WorldChunk; 14 | 15 | public class WorldListener implements EventListener { 16 | 17 | @Override 18 | public void onWorldLoad(WorldEvent event) { 19 | if(!event.getWorld().isClient()) return; 20 | 21 | CacheManager.enterWorld(); 22 | } 23 | 24 | @Override 25 | public void onWorldUnload(WorldEvent event) { 26 | if(!event.getWorld().isClient()) return; 27 | 28 | CacheManager.exitWorld(); 29 | } 30 | 31 | @Override 32 | public void onChunkData(ChunkEvent event) { 33 | int x = event.getX(); 34 | int z = event.getZ(); 35 | 36 | ClientWorld world = WorldContext.world(); 37 | 38 | WorldChunk chunk = world.getChunk(x, z); 39 | 40 | if(chunk.isEmpty() || chunk.getStatus() != ChunkStatus.FULL) return; 41 | 42 | CachedWorld w = CacheManager.getWorld(); 43 | 44 | w.addChunk(chunk); 45 | } 46 | 47 | @Override 48 | public void onBlockUpdate(BlockUpdateEvent event) { 49 | BlockPos pos = event.getPos(); 50 | 51 | CachedWorld w = CacheManager.getWorld(); 52 | 53 | w.updatePos(pos); 54 | 55 | w.updatePos(pos.up()); 56 | w.updatePos(pos.down()); 57 | } 58 | 59 | } 60 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/input/controller/GuiController.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.input.controller; 2 | 3 | import de.stylextv.maple.context.GameContext; 4 | import de.stylextv.maple.context.PlayerContext; 5 | import net.minecraft.client.network.ClientPlayerEntity; 6 | import net.minecraft.client.network.ClientPlayerInteractionManager; 7 | import net.minecraft.entity.player.PlayerInventory; 8 | import net.minecraft.item.ItemStack; 9 | import net.minecraft.screen.slot.SlotActionType; 10 | 11 | public class GuiController { 12 | 13 | public static void selectItem(ItemStack stack) { 14 | int slot = slotOf(stack); 15 | 16 | if(slot == -1) return; 17 | 18 | if(slot < 9) { 19 | 20 | selectSlot(slot); 21 | 22 | return; 23 | } 24 | 25 | moveToHotbar(slot); 26 | } 27 | 28 | public static void selectSlot(int slot) { 29 | PlayerInventory inv = PlayerContext.inventory(); 30 | 31 | inv.selectedSlot = slot; 32 | } 33 | 34 | public static void moveToHotbar(int slot) { 35 | ClientPlayerInteractionManager manager = GameContext.interactionManager(); 36 | 37 | ClientPlayerEntity p = PlayerContext.player(); 38 | 39 | PlayerInventory inv = PlayerContext.inventory(); 40 | 41 | int syncId = p.playerScreenHandler.syncId; 42 | 43 | int moveTo = inv.getSwappableHotbarSlot(); 44 | 45 | manager.clickSlot(syncId, slot, moveTo, SlotActionType.SWAP, p); 46 | } 47 | 48 | public static int slotOf(ItemStack stack) { 49 | PlayerInventory inv = PlayerContext.inventory(); 50 | 51 | for(int i = 0; i < 36; i++) { 52 | 53 | ItemStack other = inv.getStack(i); 54 | 55 | boolean equal = ItemStack.areEqual(stack, other); 56 | 57 | if(equal) return i; 58 | } 59 | 60 | return -1; 61 | } 62 | 63 | } 64 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/movements/StraightMovement.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.movements; 2 | 3 | import de.stylextv.maple.cache.block.BlockType; 4 | import de.stylextv.maple.input.InputAction; 5 | import de.stylextv.maple.pathing.calc.Node; 6 | import de.stylextv.maple.pathing.movement.Movement; 7 | import de.stylextv.maple.pathing.movement.MovementState; 8 | 9 | public class StraightMovement extends Movement { 10 | 11 | public StraightMovement(Node source, Node destination) { 12 | super(source, destination); 13 | } 14 | 15 | @Override 16 | public void updateHelpers() { 17 | Node destination = getDestination(); 18 | 19 | getBreakHelper().collectBlocks(destination, 2); 20 | 21 | BlockType type = destination.getType(); 22 | 23 | if(type != BlockType.WATER) getPlaceHelper().collectBlock(destination, -1); 24 | 25 | getInteractHelper().collectDefaultBlocks(); 26 | } 27 | 28 | @Override 29 | public double cost() { 30 | double cost = getBreakHelper().cost(); 31 | 32 | cost += getPlaceHelper().cost(); 33 | cost += getInteractHelper().cost(); 34 | 35 | return cost + super.cost(); 36 | } 37 | 38 | @Override 39 | public void onRenderTick() { 40 | boolean interacting = getBreakHelper().onRenderTick() || getInteractHelper().onRenderTick(); 41 | 42 | if(interacting) return; 43 | 44 | if(!getPlaceHelper().onRenderTick(false)) { 45 | 46 | lookAt(getDestination()); 47 | 48 | setPressed(InputAction.MOVE_FORWARD, true); 49 | setPressed(InputAction.SPRINT, true); 50 | } 51 | } 52 | 53 | @Override 54 | public MovementState getState() { 55 | if(getPlaceHelper().hasTargets()) return MovementState.PROCEEDING; 56 | 57 | return super.getState(); 58 | } 59 | 60 | } 61 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/calc/goal/TwoBlocksGoal.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.calc.goal; 2 | 3 | import de.stylextv.maple.event.events.RenderWorldEvent; 4 | import de.stylextv.maple.pathing.calc.Node; 5 | import de.stylextv.maple.render.ShapeRenderer; 6 | import de.stylextv.maple.scheme.Colors; 7 | import net.minecraft.util.math.BlockPos; 8 | 9 | public class TwoBlocksGoal extends Goal { 10 | 11 | private BlockPos pos; 12 | 13 | public TwoBlocksGoal(int x, int y, int z) { 14 | this(new BlockPos(x, y, z)); 15 | } 16 | 17 | public TwoBlocksGoal(BlockPos pos) { 18 | this.pos = pos; 19 | } 20 | 21 | @Override 22 | public double heuristic(Node n) { 23 | int dx = n.getX() - pos.getX(); 24 | int dy = n.getY() - pos.getY(); 25 | int dz = n.getZ() - pos.getZ(); 26 | 27 | if(dy < 0) dy++; 28 | 29 | return BlockGoal.cost(dx, dy, dz); 30 | } 31 | 32 | @Override 33 | public boolean isFinalNode(Node n) { 34 | int x = n.getX(); 35 | int y = n.getY(); 36 | int z = n.getZ(); 37 | 38 | return x == pos.getX() && (y == pos.getY() || y == pos.getY() - 1) && z == pos.getZ(); 39 | } 40 | 41 | @Override 42 | public void render(RenderWorldEvent event) { 43 | BlockPos up = pos.up(); 44 | BlockPos down = pos.down(); 45 | 46 | ShapeRenderer.drawBox(event, up, down, Colors.GOAL, 2); 47 | } 48 | 49 | @Override 50 | public boolean equals(Goal other) { 51 | if(!(other instanceof TwoBlocksGoal)) return false; 52 | 53 | BlockPos otherPos = ((TwoBlocksGoal) other).getPos(); 54 | 55 | return otherPos.equals(pos); 56 | } 57 | 58 | @Override 59 | public String toString() { 60 | return String.format("TwoBlocksGoal{pos=%s}", pos); 61 | } 62 | 63 | public BlockPos getPos() { 64 | return pos; 65 | } 66 | 67 | } 68 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/moves/ParkourMove.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.moves; 2 | 3 | import de.stylextv.maple.cache.CacheManager; 4 | import de.stylextv.maple.cache.block.BlockType; 5 | import de.stylextv.maple.pathing.calc.Node; 6 | import de.stylextv.maple.pathing.calc.PathFinder; 7 | import de.stylextv.maple.pathing.movement.Move; 8 | import de.stylextv.maple.pathing.movement.Movement; 9 | import de.stylextv.maple.pathing.movement.helper.ParkourHelper; 10 | import de.stylextv.maple.pathing.movement.movements.ParkourMovement; 11 | 12 | public class ParkourMove extends Move { 13 | 14 | private static final int MAX_DISTANCE = 4; 15 | 16 | public ParkourMove(int x, int y, int z) { 17 | super(x, y, z); 18 | } 19 | 20 | @Override 21 | public Movement apply(Node n, PathFinder finder) { 22 | if(ParkourHelper.isObstructed(n, 2, 1)) return null; 23 | 24 | int dx = getDeltaX(); 25 | int dz = getDeltaZ(); 26 | 27 | int dy = 0; 28 | 29 | int i = 1; 30 | 31 | while(i <= MAX_DISTANCE) { 32 | 33 | int ox = dx * i; 34 | int oz = dz * i; 35 | 36 | Node destination = finder.getAdjacentNode(n, ox, dy, oz); 37 | 38 | if(ParkourHelper.isObstructed(destination, 3)) { 39 | 40 | if(dy == 1) return null; 41 | 42 | dy++; 43 | 44 | continue; 45 | } 46 | 47 | int x = destination.getX(); 48 | int y = destination.getY() - 1; 49 | int z = destination.getZ(); 50 | 51 | BlockType type = CacheManager.getBlockType(x, y, z); 52 | 53 | if(!type.isPassable()) { 54 | 55 | if(i == 1) return null; 56 | 57 | return new ParkourMovement(n, destination, dx, dy, dz, i); 58 | } 59 | 60 | i++; 61 | } 62 | 63 | return null; 64 | } 65 | 66 | } 67 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/input/target/targets/PlaceableTarget.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.input.target.targets; 2 | 3 | import de.stylextv.maple.gui.ToolSet; 4 | import de.stylextv.maple.input.InputAction; 5 | import de.stylextv.maple.input.controller.BreakController; 6 | import de.stylextv.maple.input.controller.GuiController; 7 | import de.stylextv.maple.input.controller.InputController; 8 | import de.stylextv.maple.input.target.BlockTarget; 9 | import net.minecraft.block.Block; 10 | import net.minecraft.item.ItemStack; 11 | import net.minecraft.util.math.BlockPos; 12 | 13 | public class PlaceableTarget extends BlockTarget { 14 | 15 | private Block block; 16 | 17 | public PlaceableTarget(int x, int y, int z, Block block) { 18 | this(x, y, z); 19 | 20 | this.block = block; 21 | } 22 | 23 | public PlaceableTarget(int x, int y, int z) { 24 | super(x, y, z); 25 | } 26 | 27 | public PlaceableTarget(BlockPos pos) { 28 | super(pos); 29 | } 30 | 31 | public boolean continuePlacing() { 32 | if(isSelected(false)) { 33 | 34 | if(hasMaterial()) { 35 | 36 | GuiController.selectItem(getMaterial()); 37 | 38 | InputController.setPressed(InputAction.RIGHT_CLICK, true); 39 | } 40 | 41 | return true; 42 | } 43 | 44 | return lookAt(true); 45 | } 46 | 47 | public boolean hasMaterial() { 48 | return !getMaterial().equals(ItemStack.EMPTY); 49 | } 50 | 51 | public ItemStack getMaterial() { 52 | ToolSet tools = ToolSet.getTools(); 53 | 54 | if(block == null) return tools.getThrowawayBlocks(); 55 | 56 | return tools.getStackOf(block); 57 | } 58 | 59 | public boolean isPlaced() { 60 | BlockPos pos = getPos(); 61 | 62 | return BreakController.isBreakable(pos); 63 | } 64 | 65 | public Block getBlock() { 66 | return block; 67 | } 68 | 69 | } 70 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/io/resource/types/StreamedFile.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.io.resource.types; 2 | 3 | import java.io.File; 4 | import java.io.FileInputStream; 5 | import java.io.FileNotFoundException; 6 | import java.io.FileOutputStream; 7 | import java.io.InputStream; 8 | import java.io.OutputStream; 9 | 10 | import de.stylextv.maple.Constants; 11 | import de.stylextv.maple.context.GameContext; 12 | import de.stylextv.maple.io.resource.StreamedResource; 13 | 14 | public class StreamedFile extends StreamedResource { 15 | 16 | public static final File MOD_FOLDER = new File(GameContext.directory(), "." + Constants.MOD_ID); 17 | 18 | private File file; 19 | 20 | public StreamedFile(String path) { 21 | this(path, true); 22 | } 23 | 24 | public StreamedFile(String path, boolean compress) { 25 | this(new File(MOD_FOLDER, path), compress); 26 | } 27 | 28 | public StreamedFile(File f) { 29 | this(f, true); 30 | } 31 | 32 | public StreamedFile(File f, boolean compress) { 33 | super(compress); 34 | 35 | this.file = f; 36 | 37 | f.getParentFile().mkdirs(); 38 | } 39 | 40 | @Override 41 | protected InputStream inputStream() { 42 | try { 43 | 44 | return new FileInputStream(file); 45 | 46 | } catch (FileNotFoundException ex) { 47 | ex.printStackTrace(); 48 | } 49 | 50 | return null; 51 | } 52 | 53 | @Override 54 | protected OutputStream outputStream() { 55 | try { 56 | 57 | return new FileOutputStream(file); 58 | 59 | } catch (FileNotFoundException ex) { 60 | ex.printStackTrace(); 61 | } 62 | 63 | return null; 64 | } 65 | 66 | @Override 67 | public boolean exists() { 68 | if(!file.exists()) return false; 69 | 70 | return super.exists(); 71 | } 72 | 73 | public File getFile() { 74 | return file; 75 | } 76 | 77 | } 78 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/movements/PillarMovement.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.movements; 2 | 3 | import de.stylextv.maple.context.PlayerContext; 4 | import de.stylextv.maple.input.InputAction; 5 | import de.stylextv.maple.pathing.calc.Cost; 6 | import de.stylextv.maple.pathing.calc.Node; 7 | import de.stylextv.maple.pathing.movement.Movement; 8 | import de.stylextv.maple.pathing.movement.MovementState; 9 | 10 | public class PillarMovement extends Movement { 11 | 12 | public PillarMovement(Node source, Node destination) { 13 | super(source, destination); 14 | } 15 | 16 | @Override 17 | public void updateHelpers() { 18 | getBreakHelper().collectBlocks(getSource(), 2, 1); 19 | getPlaceHelper().collectBlock(getSource()); 20 | 21 | getInteractHelper().collectDefaultBlocks(); 22 | } 23 | 24 | @Override 25 | public double cost() { 26 | double cost = Cost.JUMP; 27 | 28 | cost += getBreakHelper().cost(); 29 | cost += getInteractHelper().cost(); 30 | 31 | if(getPlaceHelper().cost() >= Cost.INFINITY) return Cost.INFINITY; 32 | 33 | cost += Cost.placeCost(); 34 | 35 | return cost + super.cost(); 36 | } 37 | 38 | @Override 39 | public void onRenderTick() { 40 | boolean interacting = getBreakHelper().onRenderTick() || getInteractHelper().onRenderTick(); 41 | 42 | if(interacting) return; 43 | 44 | boolean atCenter = getPositionHelper().centerOnSource(); 45 | 46 | if(!atCenter) return; 47 | 48 | getPlaceHelper().onRenderTick(false); 49 | 50 | boolean jump = getJumpHelper().canJump(); 51 | 52 | setPressed(InputAction.JUMP, jump); 53 | } 54 | 55 | @Override 56 | public MovementState getState() { 57 | if(!PlayerContext.isOnGround()) return MovementState.PROCEEDING; 58 | 59 | return super.getState(); 60 | } 61 | 62 | } 63 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/input/controller/InputController.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.input.controller; 2 | 3 | import java.util.HashSet; 4 | 5 | import de.stylextv.maple.context.GameContext; 6 | import de.stylextv.maple.context.PlayerContext; 7 | import de.stylextv.maple.input.InjectedInput; 8 | import de.stylextv.maple.input.InputAction; 9 | import net.minecraft.client.input.KeyboardInput; 10 | import net.minecraft.client.network.ClientPlayerEntity; 11 | 12 | public class InputController { 13 | 14 | private static HashSet pressedInputs = new HashSet<>(); 15 | 16 | public static void setPressed(InputAction i, boolean pressed) { 17 | if(pressed) pressedInputs.add(i); 18 | else pressedInputs.remove(i); 19 | } 20 | 21 | public static boolean isPressed(InputAction i) { 22 | return pressedInputs.contains(i); 23 | } 24 | 25 | public static void releaseAll() { 26 | pressedInputs.clear(); 27 | } 28 | 29 | public static void onTick() { 30 | ClientPlayerEntity p = PlayerContext.player(); 31 | 32 | boolean injected = p.input.getClass() == InjectedInput.class; 33 | 34 | if(isInControl()) { 35 | 36 | boolean isSneaking = isPressed(InputAction.SNEAK); 37 | 38 | p.setSprinting(!isSneaking && isMoving() && isPressed(InputAction.SPRINT)); 39 | 40 | PlayerContext.setFlying(false); 41 | 42 | if(!injected) { 43 | p.input = new InjectedInput(); 44 | } 45 | 46 | } else { 47 | 48 | if(injected) { 49 | p.input = new KeyboardInput(GameContext.options()); 50 | } 51 | } 52 | } 53 | 54 | public static boolean isMoving() { 55 | for(InputAction i : pressedInputs) { 56 | if(i.isMove()) return true; 57 | } 58 | 59 | return false; 60 | } 61 | 62 | public static boolean isInControl() { 63 | return !pressedInputs.isEmpty(); 64 | } 65 | 66 | } 67 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/calc/goal/BlockGoal.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.calc.goal; 2 | 3 | import de.stylextv.maple.event.events.RenderWorldEvent; 4 | import de.stylextv.maple.pathing.calc.Node; 5 | import de.stylextv.maple.render.ShapeRenderer; 6 | import de.stylextv.maple.scheme.Colors; 7 | import net.minecraft.util.math.BlockPos; 8 | 9 | public class BlockGoal extends Goal { 10 | 11 | private BlockPos pos; 12 | 13 | public BlockGoal(int x, int y, int z) { 14 | this(new BlockPos(x, y, z)); 15 | } 16 | 17 | public BlockGoal(BlockPos pos) { 18 | this.pos = pos; 19 | } 20 | 21 | @Override 22 | public double heuristic(Node n) { 23 | int dx = n.getX() - pos.getX(); 24 | int dy = n.getY() - pos.getY(); 25 | int dz = n.getZ() - pos.getZ(); 26 | 27 | return cost(dx, dy, dz); 28 | } 29 | 30 | @Override 31 | public boolean isFinalNode(Node n) { 32 | int x = n.getX(); 33 | int y = n.getY(); 34 | int z = n.getZ(); 35 | 36 | return x == pos.getX() && y == pos.getY() && z == pos.getZ(); 37 | } 38 | 39 | @Override 40 | public void render(RenderWorldEvent event) { 41 | BlockPos up = pos.up(); 42 | 43 | ShapeRenderer.drawBox(event, pos, up, Colors.GOAL, 2); 44 | } 45 | 46 | @Override 47 | public boolean equals(Goal other) { 48 | if(!(other instanceof BlockGoal)) return false; 49 | 50 | BlockPos otherPos = ((BlockGoal) other).getPos(); 51 | 52 | return otherPos.equals(pos); 53 | } 54 | 55 | @Override 56 | public String toString() { 57 | return String.format("BlockGoal{pos=%s}", pos); 58 | } 59 | 60 | public BlockPos getPos() { 61 | return pos; 62 | } 63 | 64 | public static double cost(int dx, int dy, int dz) { 65 | double cost = XZGoal.cost(dx, dz); 66 | 67 | cost += YLevelGoal.cost(dy, 0); 68 | 69 | return cost; 70 | } 71 | 72 | } 73 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/PathingStatus.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing; 2 | 3 | import de.stylextv.maple.pathing.calc.Node; 4 | import de.stylextv.maple.pathing.calc.Path; 5 | import de.stylextv.maple.pathing.calc.PathState; 6 | import de.stylextv.maple.pathing.calc.goal.Goal; 7 | import de.stylextv.maple.pathing.movement.MovementExecutor; 8 | import net.minecraft.util.math.BlockPos; 9 | 10 | public class PathingStatus { 11 | 12 | private PathingState state = PathingState.IDLE; 13 | 14 | private Goal goal; 15 | 16 | public void clear() { 17 | setGoal(null); 18 | } 19 | 20 | public void setGoal(Goal g) { 21 | goal = g; 22 | 23 | boolean b = g == null; 24 | 25 | state = b ? PathingState.IDLE : PathingState.GOING; 26 | } 27 | 28 | public boolean destinationMatches(Goal g) { 29 | BlockPos pos = MovementExecutor.getDestination(); 30 | 31 | Node n = new Node(pos); 32 | 33 | return g.isFinalNode(n); 34 | } 35 | 36 | public boolean goalMatches(Goal g) { 37 | if(goal == null) return false; 38 | 39 | return goal.equals(g); 40 | } 41 | 42 | public boolean hasFoundGoal() { 43 | Path path = MovementExecutor.getPath(); 44 | 45 | if(path == null) return isAtGoal(); 46 | 47 | PathState state = path.getState(); 48 | 49 | return state == PathState.FOUND_GOAL; 50 | } 51 | 52 | public boolean isIdle() { 53 | return !isPathing() && !isAtGoal(); 54 | } 55 | 56 | public boolean isPathing() { 57 | return state == PathingState.GOING; 58 | } 59 | 60 | public boolean isAtGoal() { 61 | return state == PathingState.AT_GOAL; 62 | } 63 | 64 | public PathingState getState() { 65 | return state; 66 | } 67 | 68 | public void setState(PathingState state) { 69 | this.state = state; 70 | } 71 | 72 | public Goal getGoal() { 73 | return goal; 74 | } 75 | 76 | } 77 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/mixin/ClientConnectionMixin.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.mixin; 2 | 3 | import org.jetbrains.annotations.Nullable; 4 | import org.spongepowered.asm.mixin.Mixin; 5 | import org.spongepowered.asm.mixin.injection.At; 6 | import org.spongepowered.asm.mixin.injection.Inject; 7 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 8 | 9 | import de.stylextv.maple.event.EventBus; 10 | import de.stylextv.maple.event.events.PacketEvent; 11 | import io.netty.channel.ChannelHandlerContext; 12 | import io.netty.util.concurrent.Future; 13 | import io.netty.util.concurrent.GenericFutureListener; 14 | import net.minecraft.network.ClientConnection; 15 | import net.minecraft.network.NetworkSide; 16 | import net.minecraft.network.Packet; 17 | import net.minecraft.network.listener.PacketListener; 18 | 19 | @Mixin(ClientConnection.class) 20 | public class ClientConnectionMixin { 21 | 22 | @Inject(method = "channelRead0", at = @At("TAIL")) 23 | private void channelRead0(ChannelHandlerContext channelHandlerContext, Packet packet, CallbackInfo info) { 24 | ClientConnection connection = (ClientConnection) (Object) this; 25 | 26 | NetworkSide side = connection.getSide(); 27 | 28 | if(side != NetworkSide.CLIENTBOUND) return; 29 | 30 | EventBus.onEvent(new PacketEvent(PacketEvent.Type.RECEIVED, packet)); 31 | } 32 | 33 | @Inject(method = "sendImmediately", at = @At("HEAD")) 34 | private void sendImmediately(Packet packet, @Nullable GenericFutureListener> callback, CallbackInfo info) { 35 | ClientConnection connection = (ClientConnection) (Object) this; 36 | 37 | NetworkSide side = connection.getSide(); 38 | 39 | if(side != NetworkSide.CLIENTBOUND) return; 40 | 41 | EventBus.onEvent(new PacketEvent(PacketEvent.Type.SENT, packet)); 42 | } 43 | 44 | } 45 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/movements/AscendMovement.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.movements; 2 | 3 | import de.stylextv.maple.input.InputAction; 4 | import de.stylextv.maple.pathing.calc.Cost; 5 | import de.stylextv.maple.pathing.calc.Node; 6 | import de.stylextv.maple.pathing.movement.Movement; 7 | import de.stylextv.maple.pathing.movement.MovementState; 8 | 9 | public class AscendMovement extends Movement { 10 | 11 | public AscendMovement(Node source, Node destination) { 12 | super(source, destination); 13 | } 14 | 15 | @Override 16 | public void updateHelpers() { 17 | getBreakHelper().collectBlocks(getDestination(), 2); 18 | getBreakHelper().collectBlocks(getSource(), 2, 1); 19 | 20 | Node destination = getDestination(); 21 | 22 | getPlaceHelper().collectBlock(destination, -1); 23 | 24 | getInteractHelper().collectDefaultBlocks(); 25 | } 26 | 27 | @Override 28 | public double cost() { 29 | double cost = Cost.JUMP + getBreakHelper().cost(); 30 | 31 | cost += getPlaceHelper().cost(); 32 | cost += getInteractHelper().cost(); 33 | 34 | return cost + super.cost(); 35 | } 36 | 37 | @Override 38 | public void onRenderTick() { 39 | boolean interacting = getBreakHelper().onRenderTick() || getInteractHelper().onRenderTick(); 40 | 41 | if(interacting) return; 42 | 43 | if(!getPlaceHelper().onRenderTick(true)) { 44 | 45 | lookAt(getDestination()); 46 | 47 | setPressed(InputAction.MOVE_FORWARD, true); 48 | setPressed(InputAction.SPRINT, true); 49 | 50 | boolean jump = getJumpHelper().shouldJump(); 51 | 52 | setPressed(InputAction.JUMP, jump); 53 | } 54 | } 55 | 56 | @Override 57 | public MovementState getState() { 58 | if(getPlaceHelper().hasTargets()) return MovementState.PROCEEDING; 59 | 60 | return super.getState(); 61 | } 62 | 63 | } 64 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/ArgumentList.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command; 2 | 3 | public class ArgumentList { 4 | 5 | private String[] args; 6 | 7 | public ArgumentList() { 8 | this(new String[0]); 9 | } 10 | 11 | public ArgumentList(String[] args) { 12 | this.args = args; 13 | } 14 | 15 | public boolean isNumeric(int i) { 16 | String s = get(i); 17 | 18 | return ArgumentHelper.isNumeric(s); 19 | } 20 | 21 | public boolean isInt(int i) { 22 | String s = get(i); 23 | 24 | return ArgumentHelper.isInt(s); 25 | } 26 | 27 | public int getCoordinate(int i) { 28 | return getCoordinate(i, i); 29 | } 30 | 31 | public int getCoordinate(int i, int j) { 32 | String s = get(i); 33 | 34 | return ArgumentHelper.toCoordinate(s, j); 35 | } 36 | 37 | public float getFloat(int i) { 38 | String s = get(i); 39 | 40 | return ArgumentHelper.toFloat(s); 41 | } 42 | 43 | public int getInt(int i) { 44 | String s = get(i); 45 | 46 | return ArgumentHelper.toInt(s); 47 | } 48 | 49 | public String get(int i) { 50 | return args[i]; 51 | } 52 | 53 | public boolean hasAtLeast(int l) { 54 | return length() >= l; 55 | } 56 | 57 | public boolean hasAtMost(int l) { 58 | return length() <= l; 59 | } 60 | 61 | public boolean hasMoreThan(int l) { 62 | return length() > l; 63 | } 64 | 65 | public boolean hasLessThan(int l) { 66 | return length() < l; 67 | } 68 | 69 | public boolean hasExactly(int l) { 70 | return length() == l; 71 | } 72 | 73 | public int length() { 74 | return args.length; 75 | } 76 | 77 | public String[] getArguments() { 78 | return args; 79 | } 80 | 81 | public static ArgumentList fromString(String s) { 82 | if(s.isEmpty()) return new ArgumentList(); 83 | 84 | String[] args = s.split(" "); 85 | 86 | return new ArgumentList(args); 87 | } 88 | 89 | } 90 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/helper/BumpHelper.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.helper; 2 | 3 | import de.stylextv.maple.cache.CacheManager; 4 | import de.stylextv.maple.cache.block.BlockType; 5 | import de.stylextv.maple.pathing.calc.Cost; 6 | import de.stylextv.maple.pathing.calc.Node; 7 | import de.stylextv.maple.pathing.movement.Movement; 8 | 9 | public class BumpHelper extends MovementHelper { 10 | 11 | public BumpHelper(Movement m) { 12 | super(m); 13 | } 14 | 15 | @Override 16 | public double cost() { 17 | Movement m = getMovement(); 18 | 19 | if(!m.isDiagonal()) return 0; 20 | 21 | Node source = getSource(); 22 | Node destination = getDestination(); 23 | 24 | if(isBlocked(destination, 2)) return Cost.INFINITY; 25 | 26 | int y = Math.max(source.getY(), destination.getY()); 27 | 28 | boolean b1 = isBlocked(source.getX(), y, destination.getZ(), 2); 29 | boolean b2 = isBlocked(destination.getX(), y, source.getZ(), 2); 30 | 31 | if(b1 && b2) return Cost.INFINITY; 32 | 33 | return b1 || b2 ? Cost.BUMP_INTO_CORNER : 0; 34 | } 35 | 36 | private static boolean isBlocked(Node n, int height) { 37 | int x = n.getX(); 38 | int y = n.getY(); 39 | int z = n.getZ(); 40 | 41 | return isBlocked(x, y, z, height); 42 | } 43 | 44 | private static boolean isBlocked(int x, int y, int z, int height) { 45 | return isBlocked(x, y, z, 0, height); 46 | } 47 | 48 | private static boolean isBlocked(int x, int y, int z, int offset, int height) { 49 | for(int i = 0; i < height; i++) { 50 | 51 | if(isBlocked(x, y + offset + i, z)) return true; 52 | } 53 | 54 | return false; 55 | } 56 | 57 | private static boolean isBlocked(int x, int y, int z) { 58 | BlockType type = CacheManager.getBlockType(x, y, z); 59 | 60 | return !type.isPassable(); 61 | } 62 | 63 | } 64 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/input/controller/PlaceController.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.input.controller; 2 | 3 | import de.stylextv.maple.context.GameContext; 4 | import de.stylextv.maple.context.WorldContext; 5 | import de.stylextv.maple.input.InputAction; 6 | import de.stylextv.maple.mixin.MinecraftClientInvoker; 7 | import de.stylextv.maple.util.world.Offset; 8 | import de.stylextv.maple.world.BlockInterface; 9 | import net.minecraft.block.Block; 10 | import net.minecraft.block.BlockState; 11 | import net.minecraft.client.world.ClientWorld; 12 | import net.minecraft.util.math.BlockPos; 13 | import net.minecraft.util.math.Direction; 14 | import net.minecraft.util.shape.VoxelShape; 15 | 16 | public class PlaceController { 17 | 18 | public static boolean canPlaceAt(BlockPos pos) { 19 | for(Offset o : Offset.DIRECT_BLOCK_NEIGHBOURS) { 20 | 21 | int x = pos.getX() + o.getBlockX(); 22 | int y = pos.getY() + o.getBlockY(); 23 | int z = pos.getZ() + o.getBlockZ(); 24 | 25 | Direction dir = o.getDirection().getOpposite(); 26 | 27 | if(canPlaceAgainst(x, y, z, dir)) return true; 28 | } 29 | 30 | return false; 31 | } 32 | 33 | public static boolean canPlaceAgainst(int x, int y, int z, Direction dir) { 34 | BlockPos pos = new BlockPos(x, y, z); 35 | 36 | BlockState state = BlockInterface.getState(pos); 37 | 38 | ClientWorld world = WorldContext.world(); 39 | 40 | VoxelShape shape = state.getOutlineShape(world, pos); 41 | 42 | return Block.isFaceFullSquare(shape, dir); 43 | } 44 | 45 | public static void onTick() { 46 | boolean b = InputController.isPressed(InputAction.RIGHT_CLICK); 47 | 48 | if(!b) return; 49 | 50 | InputController.setPressed(InputAction.RIGHT_CLICK, false); 51 | 52 | MinecraftClientInvoker invoker = GameContext.clientInvoker(); 53 | 54 | invoker.invokeDoItemUse(); 55 | } 56 | 57 | } 58 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/chat/ChatUtil.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.chat; 2 | 3 | import java.util.List; 4 | 5 | import de.stylextv.maple.Constants; 6 | import de.stylextv.maple.context.PlayerContext; 7 | import de.stylextv.maple.util.math.MathUtil; 8 | import net.minecraft.text.MutableText; 9 | 10 | public class ChatUtil { 11 | 12 | private static final Message PREFIX = new Message(Constants.COLORED_NAME + " §8| §7"); 13 | 14 | public static void sendList(List list, int rows, int page, String command) { 15 | page--; 16 | 17 | int l = list.size(); 18 | 19 | int pages = (int) Math.ceil((double) l / rows); 20 | 21 | if(pages == 0) pages = 1; 22 | 23 | int maxPage = pages - 1; 24 | 25 | page = MathUtil.clamp(page, 0, maxPage); 26 | 27 | int start = page * rows; 28 | 29 | int end = Math.min(start + rows, l) - 1; 30 | 31 | for(int i = start; i <= end; i++) { 32 | String s = list.get(i); 33 | 34 | send("- " + s); 35 | } 36 | 37 | int remaining = rows - (end - start + 1); 38 | 39 | for(int i = 0; i < remaining; i++) { 40 | send("§8--"); 41 | } 42 | 43 | String s = page == 0 ? "§8<< " : String.format("§x[§b<<]{#%s %s} ", command, page); 44 | 45 | s += "§7§ "; 46 | 47 | s += page == maxPage ? "§8>> " : String.format("§x[§b>>]{#%s %s} ", command, page + 2); 48 | 49 | s += String.format("§7%s/%s", page + 1, pages); 50 | 51 | send(s); 52 | } 53 | 54 | public static void send(String... lines) { 55 | for(String s : lines) { 56 | send(s); 57 | } 58 | } 59 | 60 | public static void send(String line) { 61 | Message m = new Message(line); 62 | 63 | send(m); 64 | } 65 | 66 | public static void send(Message m) { 67 | m = PREFIX.append(m); 68 | 69 | MutableText text = m.asText(); 70 | 71 | PlayerContext.player().sendMessage(text, false); 72 | } 73 | 74 | } 75 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/mixin/NetworkHandlerMixin.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.mixin; 2 | 3 | import org.spongepowered.asm.mixin.Mixin; 4 | import org.spongepowered.asm.mixin.injection.At; 5 | import org.spongepowered.asm.mixin.injection.Inject; 6 | import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; 7 | 8 | import de.stylextv.maple.event.EventBus; 9 | import de.stylextv.maple.event.events.BlockUpdateEvent; 10 | import de.stylextv.maple.event.events.ChunkEvent; 11 | import net.minecraft.client.network.ClientPlayNetworkHandler; 12 | import net.minecraft.network.packet.s2c.play.BlockUpdateS2CPacket; 13 | import net.minecraft.network.packet.s2c.play.ChunkDataS2CPacket; 14 | import net.minecraft.network.packet.s2c.play.ChunkDeltaUpdateS2CPacket; 15 | import net.minecraft.util.math.BlockPos; 16 | 17 | @Mixin(ClientPlayNetworkHandler.class) 18 | public class NetworkHandlerMixin { 19 | 20 | @Inject(method = "onChunkData(Lnet/minecraft/network/packet/s2c/play/ChunkDataS2CPacket;)V", at = @At("TAIL")) 21 | private void onChunkData(ChunkDataS2CPacket packet, CallbackInfo info) { 22 | int x = packet.getX(); 23 | int z = packet.getZ(); 24 | 25 | EventBus.onEvent(new ChunkEvent(ChunkEvent.Type.DATA, x, z)); 26 | } 27 | 28 | @Inject(method = "onChunkDeltaUpdate(Lnet/minecraft/network/packet/s2c/play/ChunkDeltaUpdateS2CPacket;)V", at = @At("TAIL")) 29 | private void onChunkDeltaUpdate(ChunkDeltaUpdateS2CPacket packet, CallbackInfo info) { 30 | packet.visitUpdates((pos, state) -> { 31 | 32 | EventBus.onEvent(new BlockUpdateEvent(pos)); 33 | }); 34 | } 35 | 36 | @Inject(method = "onBlockUpdate(Lnet/minecraft/network/packet/s2c/play/BlockUpdateS2CPacket;)V", at = @At("TAIL")) 37 | private void onBlockUpdate(BlockUpdateS2CPacket packet, CallbackInfo info) { 38 | BlockPos pos = packet.getPos(); 39 | 40 | EventBus.onEvent(new BlockUpdateEvent(pos)); 41 | } 42 | 43 | } 44 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/input/target/TargetList.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.input.target; 2 | 3 | import java.util.Iterator; 4 | import java.util.Set; 5 | import java.util.concurrent.ConcurrentHashMap; 6 | 7 | import de.stylextv.maple.pathing.calc.goal.CompositeGoal; 8 | import de.stylextv.maple.pathing.calc.goal.TwoBlocksGoal; 9 | import net.minecraft.util.math.BlockPos; 10 | 11 | public class TargetList implements Iterable { 12 | 13 | private Set set = ConcurrentHashMap.newKeySet(); 14 | 15 | public void add(T target) { 16 | set.add(target); 17 | } 18 | 19 | public void remove(BlockPos pos) { 20 | T target = get(pos); 21 | 22 | if(target != null) remove(target); 23 | } 24 | 25 | public void remove(T target) { 26 | set.remove(target); 27 | } 28 | 29 | public boolean contains(BlockPos pos) { 30 | int x = pos.getX(); 31 | int y = pos.getY(); 32 | int z = pos.getZ(); 33 | 34 | return contains(x, y, z); 35 | } 36 | 37 | public boolean contains(int x, int y, int z) { 38 | return get(x, y, z) != null; 39 | } 40 | 41 | public T get(BlockPos pos) { 42 | int x = pos.getX(); 43 | int y = pos.getY(); 44 | int z = pos.getZ(); 45 | 46 | return get(x, y, z); 47 | } 48 | 49 | public T get(int x, int y, int z) { 50 | for(T target : set) { 51 | 52 | BlockPos pos = target.getPos(); 53 | 54 | if(pos.getX() == x && pos.getY() == y && pos.getZ() == z) return target; 55 | } 56 | 57 | return null; 58 | } 59 | 60 | public CompositeGoal toGoal() { 61 | return CompositeGoal.fromCollection(set, t -> new TwoBlocksGoal(t.getPos())); 62 | } 63 | 64 | @Override 65 | public Iterator iterator() { 66 | return set.iterator(); 67 | } 68 | 69 | public int size() { 70 | return set.size(); 71 | } 72 | 73 | public boolean isEmpty() { 74 | return set.isEmpty(); 75 | } 76 | 77 | public Set getSet() { 78 | return set; 79 | } 80 | 81 | } 82 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/avoidance/Avoidance.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.avoidance; 2 | 3 | import java.util.ArrayList; 4 | import java.util.List; 5 | 6 | import de.stylextv.maple.util.world.CoordUtil; 7 | import de.stylextv.maple.world.scan.entity.EntityScanner; 8 | import it.unimi.dsi.fastutil.longs.Long2DoubleOpenHashMap; 9 | import net.minecraft.entity.Entity; 10 | import net.minecraft.util.math.BlockPos; 11 | 12 | public class Avoidance { 13 | 14 | private BlockPos pos; 15 | 16 | private AvoidanceType type; 17 | 18 | public Avoidance(BlockPos pos, AvoidanceType type) { 19 | this.pos = pos; 20 | this.type = type; 21 | } 22 | 23 | public void apply(Long2DoubleOpenHashMap map) { 24 | int r = type.getRadius(); 25 | 26 | for(int x = -r; x <= r; x++) { 27 | for(int y = -r; y <= r; y++) { 28 | for(int z = -r; z <= r; z++) { 29 | 30 | int dis = x * x + y * y + z * z; 31 | 32 | if(dis <= r * r) { 33 | 34 | int rx = pos.getX() + x; 35 | int ry = pos.getY() + y; 36 | int rz = pos.getZ() + z; 37 | 38 | long hash = CoordUtil.posAsLong(rx, ry, rz); 39 | 40 | double d = type.getCoefficient(); 41 | 42 | d *= map.get(hash); 43 | 44 | map.put(hash, d); 45 | } 46 | } 47 | } 48 | } 49 | } 50 | 51 | public BlockPos getPos() { 52 | return pos; 53 | } 54 | 55 | public AvoidanceType getType() { 56 | return type; 57 | } 58 | 59 | public static List list() { 60 | List list = new ArrayList<>(); 61 | 62 | List entities = EntityScanner.scanWorld(); 63 | 64 | for(Entity e : entities) { 65 | 66 | AvoidanceType type = AvoidanceType.fromEntity(e); 67 | 68 | if(type == null) continue; 69 | 70 | BlockPos pos = e.getBlockPos(); 71 | 72 | Avoidance a = new Avoidance(pos, type); 73 | 74 | list.add(a); 75 | } 76 | 77 | return list; 78 | } 79 | 80 | } 81 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/world/avoidance/AvoidanceFilter.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.world.avoidance; 2 | 3 | import java.util.HashMap; 4 | import java.util.function.Predicate; 5 | 6 | import net.minecraft.entity.Entity; 7 | import net.minecraft.entity.mob.MagmaCubeEntity; 8 | import net.minecraft.entity.mob.SlimeEntity; 9 | import net.minecraft.entity.mob.SpiderEntity; 10 | 11 | public class AvoidanceFilter { 12 | 13 | private static HashMap, AvoidanceFilter> map = new HashMap<>(); 14 | 15 | public static final AvoidanceFilter SPIDER = new AvoidanceFilter<>(SpiderEntity.class, (spider) -> { 16 | return spider.getBrightnessAtEyes() < 0.5f; 17 | }); 18 | 19 | public static final AvoidanceFilter SLIME = new AvoidanceFilter<>(SlimeEntity.class, (slime) -> { 20 | return slime.getSize() > 1; 21 | }); 22 | 23 | public static final AvoidanceFilter MAGMA_CUBE = new AvoidanceFilter<>(MagmaCubeEntity.class, (magmaCube) -> { 24 | return magmaCube.getSize() > 1; 25 | }); 26 | 27 | private Class entityClass; 28 | 29 | private Predicate predicate; 30 | 31 | public AvoidanceFilter(Class entityClass, Predicate predicate) { 32 | this.entityClass = entityClass; 33 | this.predicate = predicate; 34 | 35 | registerFilter(this); 36 | } 37 | 38 | public boolean ignores(Entity e) { 39 | if(predicate == null) return false; 40 | 41 | T t = entityClass.cast(e); 42 | 43 | return !predicate.test(t); 44 | } 45 | 46 | public Class getEntityClass() { 47 | return entityClass; 48 | } 49 | 50 | private static void registerFilter(AvoidanceFilter filter) { 51 | map.put(filter.getEntityClass(), filter); 52 | } 53 | 54 | public static boolean shouldIgnore(Entity e) { 55 | Class clazz = e.getClass(); 56 | 57 | AvoidanceFilter filter = map.get(clazz); 58 | 59 | if(filter == null) return false; 60 | 61 | return filter.ignores(e); 62 | } 63 | 64 | } 65 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/cache/CacheManager.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.cache; 2 | 3 | import java.util.HashMap; 4 | 5 | import de.stylextv.maple.cache.block.BlockType; 6 | import de.stylextv.maple.context.WorldContext; 7 | import de.stylextv.maple.util.world.CoordUtil; 8 | import de.stylextv.maple.world.WorldBorderInterface; 9 | import net.minecraft.util.math.BlockPos; 10 | 11 | public class CacheManager { 12 | 13 | private static HashMap worlds = new HashMap<>(); 14 | 15 | private static CachedWorld world; 16 | 17 | public static void enterWorld() { 18 | String name = WorldContext.getLevelName(); 19 | 20 | CachedWorld w = getWorld(name); 21 | 22 | if(w.equals(world)) return; 23 | 24 | exitWorld(); 25 | 26 | world = w; 27 | 28 | world.enter(); 29 | } 30 | 31 | public static void exitWorld() { 32 | if(world == null) return; 33 | 34 | world.exit(); 35 | 36 | world = null; 37 | } 38 | 39 | public static BlockType getBlockType(double x, double y, double z) { 40 | int blockX = CoordUtil.unitToBlockPos(x); 41 | int blockY = CoordUtil.unitToBlockPos(y); 42 | int blockZ = CoordUtil.unitToBlockPos(z); 43 | 44 | return getBlockType(blockX, blockY, blockZ); 45 | } 46 | 47 | public static BlockType getBlockType(BlockPos pos) { 48 | int x = pos.getX(); 49 | int y = pos.getY(); 50 | int z = pos.getZ(); 51 | 52 | return getBlockType(x, y, z); 53 | } 54 | 55 | public static BlockType getBlockType(int x, int y, int z) { 56 | if(!WorldBorderInterface.isInside(x, z)) return BlockType.UNBREAKABLE; 57 | 58 | return world.getBlockType(x, y, z); 59 | } 60 | 61 | private static CachedWorld getWorld(String name) { 62 | CachedWorld cache = worlds.get(name); 63 | 64 | if(cache == null) { 65 | cache = new CachedWorld(name); 66 | 67 | worlds.put(name, cache); 68 | } 69 | 70 | return cache; 71 | } 72 | 73 | public static CachedWorld getWorld() { 74 | return world; 75 | } 76 | 77 | } 78 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/task/tasks/GetToBlockTask.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.task.tasks; 2 | 3 | import java.util.Set; 4 | import java.util.concurrent.ConcurrentHashMap; 5 | 6 | import de.stylextv.maple.pathing.calc.goal.CompositeGoal; 7 | import de.stylextv.maple.pathing.calc.goal.GetToBlockGoal; 8 | import de.stylextv.maple.util.chat.ChatUtil; 9 | import de.stylextv.maple.world.BlockInterface; 10 | import de.stylextv.maple.world.scan.block.BlockFilter; 11 | import de.stylextv.maple.world.scan.block.BlockFilters; 12 | import net.minecraft.block.BlockState; 13 | import net.minecraft.util.math.BlockPos; 14 | 15 | public class GetToBlockTask extends ScanTask { 16 | 17 | private Set positions = ConcurrentHashMap.newKeySet(); 18 | 19 | public GetToBlockTask(BlockFilter filter) { 20 | this(BlockFilters.fromFilter(filter)); 21 | } 22 | 23 | public GetToBlockTask(BlockFilters filters) { 24 | super(filters, true); 25 | } 26 | 27 | @Override 28 | public CompositeGoal onRenderTick() { 29 | if(positions.isEmpty() && hasScanExpired()) { 30 | 31 | if(!isScanning()) { 32 | 33 | rescan((pos) -> { 34 | 35 | boolean contains = positions.contains(pos); 36 | 37 | if(!contains) positions.add(pos); 38 | 39 | }); 40 | } 41 | 42 | return null; 43 | } 44 | 45 | for(BlockPos pos : positions) { 46 | 47 | BlockState state = BlockInterface.getState(pos); 48 | 49 | boolean matches = getFilters().matches(state); 50 | 51 | if(!matches) positions.remove(pos); 52 | } 53 | 54 | return CompositeGoal.fromCollection(positions, pos -> new GetToBlockGoal(pos)); 55 | } 56 | 57 | @Override 58 | public void onComplete() { 59 | ChatUtil.send("Destination reached."); 60 | } 61 | 62 | @Override 63 | public void onFail() { 64 | ChatUtil.send("Can't get any closer to blocks."); 65 | } 66 | 67 | @Override 68 | public void onEmptyGoal() { 69 | ChatUtil.send("Can't find any matching blocks nearby."); 70 | } 71 | 72 | } 73 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/helper/DangerHelper.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.helper; 2 | 3 | import de.stylextv.maple.cache.CacheManager; 4 | import de.stylextv.maple.cache.block.BlockType; 5 | import de.stylextv.maple.pathing.calc.Cost; 6 | import de.stylextv.maple.pathing.calc.Node; 7 | import de.stylextv.maple.pathing.movement.Movement; 8 | 9 | public class DangerHelper extends MovementHelper { 10 | 11 | public DangerHelper(Movement m) { 12 | super(m); 13 | } 14 | 15 | @Override 16 | public double cost() { 17 | Node source = getSource(); 18 | Node destination = getDestination(); 19 | 20 | if(isNearDanger(destination)) return Cost.INFINITY; 21 | 22 | int x = destination.getX(); 23 | int y = destination.getY(); 24 | int z = destination.getZ(); 25 | 26 | BlockType type = CacheManager.getBlockType(x, y + 1, z); 27 | 28 | if(type == BlockType.WATER) return Cost.INFINITY; 29 | 30 | Movement m = getMovement(); 31 | 32 | if(!m.isDiagonal()) return 0; 33 | 34 | int x2 = source.getX(); 35 | int z2 = source.getZ(); 36 | 37 | int y2 = Math.max(source.getY(), destination.getY()); 38 | 39 | boolean b = isNearDanger(x, y2, z2) || isNearDanger(x2, y2, z); 40 | 41 | return b ? Cost.INFINITY : 0; 42 | } 43 | 44 | private static boolean isNearDanger(Node n) { 45 | int x = n.getX(); 46 | int y = n.getY(); 47 | int z = n.getZ(); 48 | 49 | return isNearDanger(x, y, z); 50 | } 51 | 52 | private static boolean isNearDanger(int x, int y, int z) { 53 | return isDangerous(x, y, z, -1, 3); 54 | } 55 | 56 | private static boolean isDangerous(int x, int y, int z, int offset, int height) { 57 | for(int i = 0; i < height; i++) { 58 | 59 | if(isDangerous(x, y + offset + i, z)) return true; 60 | } 61 | 62 | return false; 63 | } 64 | 65 | private static boolean isDangerous(int x, int y, int z) { 66 | BlockType type = CacheManager.getBlockType(x, y, z); 67 | 68 | return type == BlockType.DANGER; 69 | } 70 | 71 | } 72 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/movement/helper/InteractHelper.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.movement.helper; 2 | 3 | import de.stylextv.maple.input.target.targets.OpenableTarget; 4 | import de.stylextv.maple.pathing.calc.Cost; 5 | import de.stylextv.maple.pathing.calc.Node; 6 | import de.stylextv.maple.pathing.movement.Movement; 7 | import de.stylextv.maple.world.BlockInterface; 8 | import de.stylextv.maple.world.interact.Openable; 9 | import net.minecraft.block.BlockState; 10 | 11 | public class InteractHelper extends TargetHelper { 12 | 13 | public InteractHelper(Movement m) { 14 | super(m); 15 | } 16 | 17 | public void collectDefaultBlocks() { 18 | Node source = getSource(); 19 | Node destination = getDestination(); 20 | 21 | collectBlocks(source, 2); 22 | collectBlocks(destination, 2); 23 | } 24 | 25 | @Override 26 | public void collectBlock(int x, int y, int z) { 27 | BlockState state = BlockInterface.getState(x, y, z); 28 | 29 | Openable o = Openable.fromState(state); 30 | 31 | if(o == null) return; 32 | 33 | OpenableTarget target = getTarget(x, y, z); 34 | 35 | if(target == null) { 36 | 37 | target = new OpenableTarget(x, y, z, o); 38 | 39 | addTarget(target); 40 | 41 | return; 42 | } 43 | 44 | target.updateOpenable(o); 45 | } 46 | 47 | @Override 48 | public double cost() { 49 | Movement m = getMovement(); 50 | 51 | for(OpenableTarget target : getTargets()) { 52 | 53 | boolean locked = target.isLocked(); 54 | 55 | if(locked && !target.isOpen(m)) return Cost.INFINITY; 56 | } 57 | 58 | return 0; 59 | } 60 | 61 | public boolean onRenderTick() { 62 | if(!hasTargets()) return false; 63 | 64 | Movement m = getMovement(); 65 | 66 | for(OpenableTarget target : getTargets()) { 67 | 68 | if(target.isOpen(m)) { 69 | 70 | removeTarget(target); 71 | 72 | continue; 73 | } 74 | 75 | if(target.continueOpening()) return true; 76 | } 77 | 78 | return false; 79 | } 80 | 81 | } 82 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/calc/Cost.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.calc; 2 | 3 | import de.stylextv.maple.context.WorldContext; 4 | import de.stylextv.maple.gui.ToolSet; 5 | import de.stylextv.maple.util.ItemUtil; 6 | import de.stylextv.maple.world.BlockInterface; 7 | import net.minecraft.block.BlockState; 8 | import net.minecraft.client.world.ClientWorld; 9 | import net.minecraft.item.ItemStack; 10 | import net.minecraft.util.math.BlockPos; 11 | 12 | public class Cost { 13 | 14 | public static final double INFINITY = 100000000; 15 | 16 | public static final double WALK_STRAIGHT = 4.6328; 17 | public static final double WALK_DIAGONALLY = 6.5518; 18 | 19 | public static final double SPRINT_STRAIGHT = 3.5638; 20 | public static final double SPRINT_DIAGONALLY = 5.04; 21 | 22 | public static final double JUMP = fallCost(1.25) - fallCost(0.25); 23 | 24 | public static final double[] FALL_N_BLOCKS = new double[384]; 25 | 26 | public static final double BUMP_INTO_CORNER = 3.2; 27 | 28 | private static final int PLACE_BLOCK = 20; 29 | 30 | static { 31 | for(int i = 0; i < FALL_N_BLOCKS.length; i++) { 32 | FALL_N_BLOCKS[i] = fallCost(i); 33 | } 34 | } 35 | 36 | public static double fallCost(double dis) { 37 | if(dis == 0) return 0; 38 | 39 | return Math.sqrt(dis * 25.5102); 40 | } 41 | 42 | public static double breakCost(BlockPos pos) { 43 | ClientWorld world = WorldContext.world(); 44 | 45 | BlockState state = BlockInterface.getState(pos); 46 | 47 | float hardness = state.getHardness(world, pos); 48 | 49 | if(hardness < 0) return INFINITY; 50 | 51 | ToolSet tools = ToolSet.getTools(); 52 | 53 | ItemStack stack = tools.getBestTool(state); 54 | 55 | float f = ItemUtil.getDigSpeed(stack, state); 56 | 57 | float damage = f / hardness; 58 | 59 | return 100 / damage; 60 | } 61 | 62 | public static double placeCost() { 63 | ToolSet tools = ToolSet.getTools(); 64 | 65 | if(!tools.hasThrowawayBlocks()) return INFINITY; 66 | 67 | return PLACE_BLOCK; 68 | } 69 | 70 | } 71 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/render/mesh/BoxMesh.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.render.mesh; 2 | 3 | import java.util.HashMap; 4 | 5 | import de.stylextv.maple.util.world.CoordUtil; 6 | import net.minecraft.util.math.Vec3f; 7 | 8 | public class BoxMesh extends Mesh { 9 | 10 | private static final HashMap MESH_CACHE = new HashMap<>(); 11 | 12 | private int width; 13 | private int height; 14 | private int length; 15 | 16 | public BoxMesh(int width, int height, int length) { 17 | this.width = width; 18 | this.height = height; 19 | this.length = length; 20 | } 21 | 22 | @Override 23 | public void create() { 24 | Vec3f[][][] map = new Vec3f[2][2][2]; 25 | 26 | for(int i = 0; i < 2; i++) { 27 | for(int j = 0; j < 2; j++) { 28 | for(int k = 0; k < 2; k++) { 29 | 30 | float x = width * i; 31 | float y = height * j; 32 | float z = length * k; 33 | 34 | map[i][j][k] = new Vec3f(x, y, z); 35 | } 36 | } 37 | } 38 | 39 | Vec3f[] vertices = new Vec3f[24]; 40 | 41 | int index = 0; 42 | 43 | for(int i = 0; i < 2; i++) { 44 | for(int j = 0; j < 2; j++) { 45 | 46 | vertices[index ] = map[0][i][j]; 47 | vertices[index + 1] = map[1][i][j]; 48 | 49 | vertices[index + 2] = map[i][0][j]; 50 | vertices[index + 3] = map[i][1][j]; 51 | 52 | vertices[index + 4] = map[i][j][0]; 53 | vertices[index + 5] = map[i][j][1]; 54 | 55 | index += 6; 56 | } 57 | } 58 | 59 | setVertices(vertices); 60 | } 61 | 62 | public int getWidth() { 63 | return width; 64 | } 65 | 66 | public int getHeight() { 67 | return height; 68 | } 69 | 70 | public int getLength() { 71 | return length; 72 | } 73 | 74 | public static BoxMesh getMesh(int width, int height, int length) { 75 | long key = CoordUtil.posAsLong(width, height, length); 76 | 77 | BoxMesh mesh = MESH_CACHE.get(key); 78 | 79 | if(mesh == null) { 80 | 81 | mesh = new BoxMesh(width, height, length); 82 | 83 | MESH_CACHE.put(key, mesh); 84 | } 85 | 86 | return mesh; 87 | } 88 | 89 | } 90 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/pathing/calc/goal/StrictDirectionGoal.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.pathing.calc.goal; 2 | 3 | import de.stylextv.maple.pathing.calc.Node; 4 | import net.minecraft.util.math.BlockPos; 5 | import net.minecraft.util.math.Direction; 6 | 7 | public class StrictDirectionGoal extends Goal { 8 | 9 | private static final int DEVIATION_COST = 1000; 10 | 11 | private static final int PROGRESS_BONUS = 100; 12 | 13 | private BlockPos pos; 14 | 15 | private Direction dir; 16 | 17 | public StrictDirectionGoal(int x, int y, int z, Direction dir) { 18 | this(new BlockPos(x, y, z), dir); 19 | } 20 | 21 | public StrictDirectionGoal(BlockPos pos, Direction dir) { 22 | this.pos = pos; 23 | this.dir = dir; 24 | } 25 | 26 | @Override 27 | public double heuristic(Node n) { 28 | int dx = n.getX() - pos.getX(); 29 | int dy = n.getY() - pos.getY(); 30 | int dz = n.getZ() - pos.getZ(); 31 | 32 | int dirX = dir.getOffsetX(); 33 | int dirY = dir.getOffsetY(); 34 | int dirZ = dir.getOffsetZ(); 35 | 36 | int dis = dx * dirX + dy * dirY + dz * dirZ; 37 | 38 | int devX = dx * (Math.abs(dirX) ^ 1); 39 | int devY = dy * (Math.abs(dirY) ^ 1); 40 | int devZ = dz * (Math.abs(dirZ) ^ 1); 41 | 42 | int dev = Math.abs(devX) + Math.abs(devY) + Math.abs(devZ); 43 | 44 | return dev * DEVIATION_COST - dis * PROGRESS_BONUS; 45 | } 46 | 47 | @Override 48 | public boolean isFinalNode(Node n) { 49 | return false; 50 | } 51 | 52 | @Override 53 | public boolean equals(Goal other) { 54 | if(!(other instanceof StrictDirectionGoal)) return false; 55 | 56 | StrictDirectionGoal g = (StrictDirectionGoal) other; 57 | 58 | BlockPos otherPos = g.getPos(); 59 | Direction otherDir = g.getDirection(); 60 | 61 | return otherPos.equals(pos) && otherDir == dir; 62 | } 63 | 64 | public BlockPos getPos() { 65 | return pos; 66 | } 67 | 68 | public Direction getDirection() { 69 | return dir; 70 | } 71 | 72 | @Override 73 | public String toString() { 74 | return String.format("StrictDirectionGoal{pos=%s, dir=%s}", pos, dir); 75 | } 76 | 77 | } 78 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/util/time/TimeUnit.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.util.time; 2 | 3 | public class TimeUnit { 4 | 5 | private static final TimeUnit[] UNITS = new TimeUnit[8]; 6 | 7 | public static final TimeUnit MILLI_SECONDS = new TimeUnit("ms", "ms", 1); 8 | 9 | public static final TimeUnit SECONDS = new TimeUnit("second", "seconds", 1000); 10 | 11 | public static final TimeUnit MINUTES = new TimeUnit("minute", "minutes", 60000); 12 | 13 | public static final TimeUnit HOURS = new TimeUnit("hour", "hours", 3600000); 14 | 15 | public static final TimeUnit DAYS = new TimeUnit("day", "days", 86400000); 16 | 17 | public static final TimeUnit WEEKS = new TimeUnit("week", "weeks", 604800000); 18 | 19 | public static final TimeUnit MONTHS = new TimeUnit("month", "months", 2628002880l); 20 | 21 | public static final TimeUnit YEARS = new TimeUnit("year", "years", 31556952000l); 22 | 23 | private static int pointer; 24 | 25 | private String singular; 26 | private String plural; 27 | 28 | private long duration; 29 | 30 | public TimeUnit(String singular, String plural, long duration) { 31 | this.singular = singular; 32 | this.plural = plural; 33 | 34 | this.duration = duration; 35 | 36 | registerUnit(this); 37 | } 38 | 39 | public long getAmount(long time) { 40 | return time / duration; 41 | } 42 | 43 | public String getName(long amount) { 44 | return amount == 1 ? singular : plural; 45 | } 46 | 47 | public String getSingular() { 48 | return singular; 49 | } 50 | 51 | public String getPlural() { 52 | return plural; 53 | } 54 | 55 | public long getDuration() { 56 | return duration; 57 | } 58 | 59 | private static void registerUnit(TimeUnit u) { 60 | UNITS[pointer] = u; 61 | 62 | pointer++; 63 | } 64 | 65 | public static TimeUnit getUnit(long time) { 66 | for(int i = UNITS.length - 1; i > 0; i--) { 67 | 68 | TimeUnit u = UNITS[i]; 69 | 70 | if(time > u.getDuration()) return u; 71 | } 72 | 73 | return MILLI_SECONDS; 74 | } 75 | 76 | public static TimeUnit[] getUnits() { 77 | return UNITS; 78 | } 79 | 80 | } 81 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/command/commands/HelpCommand.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.command.commands; 2 | 3 | import java.util.ArrayList; 4 | import java.util.List; 5 | 6 | import de.stylextv.maple.command.ArgumentList; 7 | import de.stylextv.maple.command.Command; 8 | import de.stylextv.maple.command.CommandManager; 9 | import de.stylextv.maple.util.TextUtil; 10 | import de.stylextv.maple.util.chat.ChatUtil; 11 | 12 | public class HelpCommand extends Command { 13 | 14 | public HelpCommand() { 15 | super("help", "Gives useful information about commands."); 16 | } 17 | 18 | @Override 19 | public boolean execute(ArgumentList args) { 20 | boolean b = args.hasAtLeast(1); 21 | 22 | if(!b || args.isInt(0)) { 23 | 24 | int page = b ? args.getInt(0) : 1; 25 | 26 | ChatUtil.send("Use §o#help §7to get help for individual commands.", "", "Commands:"); 27 | 28 | List list = new ArrayList<>(); 29 | 30 | for(Command c : CommandManager.getCommands()) { 31 | String name = c.getName(); 32 | 33 | list.add(name); 34 | } 35 | 36 | ChatUtil.sendList(list, 4, page, getName()); 37 | 38 | return true; 39 | } 40 | 41 | String s = args.get(0); 42 | 43 | Command c = CommandManager.getCommand(s); 44 | 45 | if(c == null) { 46 | ChatUtil.send("§cCouldn't find command!"); 47 | 48 | return true; 49 | } 50 | 51 | String name = c.getName(); 52 | String description = c.getDescription(); 53 | String[] aliases = c.getAliases(); 54 | 55 | ChatUtil.send("#" + name + ":", description); 56 | 57 | if(aliases.length != 0) { 58 | 59 | String s2 = TextUtil.combine(aliases, ", "); 60 | 61 | ChatUtil.send("Aliases: " + s2); 62 | } 63 | 64 | String[] usages = c.getUsages(); 65 | 66 | if(usages == null) return true; 67 | 68 | ChatUtil.send("", "Usages:"); 69 | 70 | for(String s2 : usages) { 71 | ChatUtil.send(" - " + name + " " + s2); 72 | } 73 | 74 | return true; 75 | } 76 | 77 | @Override 78 | public String[] getUsages() { 79 | return new String[] {"[page]", "[command]"}; 80 | } 81 | 82 | } 83 | -------------------------------------------------------------------------------- /src/main/java/de/stylextv/maple/input/controller/BreakController.java: -------------------------------------------------------------------------------- 1 | package de.stylextv.maple.input.controller; 2 | 3 | import de.stylextv.maple.context.GameContext; 4 | import de.stylextv.maple.context.WorldContext; 5 | import de.stylextv.maple.input.InputAction; 6 | import de.stylextv.maple.mixin.MinecraftClientInvoker; 7 | import de.stylextv.maple.util.world.Offset; 8 | import de.stylextv.maple.world.BlockInterface; 9 | import net.minecraft.block.BlockState; 10 | import net.minecraft.client.world.ClientWorld; 11 | import net.minecraft.util.math.BlockPos; 12 | import net.minecraft.util.shape.VoxelShape; 13 | 14 | public class BreakController { 15 | 16 | public static boolean isSafeToBreak(BlockPos pos) { 17 | BlockState state = BlockInterface.getState(pos); 18 | 19 | boolean inFluid = !state.getFluidState().isEmpty(); 20 | 21 | if(inFluid) return true; 22 | 23 | for(Offset o : Offset.UPPER_DIRECT_BLOCK_NEIGHBOURS) { 24 | 25 | int dx = o.getBlockX(); 26 | int dy = o.getBlockY(); 27 | int dz = o.getBlockZ(); 28 | 29 | int x = pos.getX() + dx; 30 | int y = pos.getY() + dy; 31 | int z = pos.getZ() + dz; 32 | 33 | state = BlockInterface.getState(x, y, z); 34 | 35 | int level = state.getFluidState().getLevel(); 36 | 37 | if(level == 0) continue; 38 | 39 | if(dy == 1 || level > 1) return false; 40 | } 41 | 42 | return true; 43 | } 44 | 45 | public static boolean isBreakable(int x, int y, int z) { 46 | BlockPos pos = new BlockPos(x, y, z); 47 | 48 | return isBreakable(pos); 49 | } 50 | 51 | public static boolean isBreakable(BlockPos pos) { 52 | BlockState state = BlockInterface.getState(pos); 53 | 54 | ClientWorld world = WorldContext.world(); 55 | 56 | VoxelShape shape = state.getOutlineShape(world, pos); 57 | 58 | return !shape.isEmpty(); 59 | } 60 | 61 | public static void onTick() { 62 | boolean b = InputController.isPressed(InputAction.LEFT_CLICK); 63 | 64 | if(!b) return; 65 | 66 | InputController.setPressed(InputAction.LEFT_CLICK, false); 67 | 68 | MinecraftClientInvoker invoker = GameContext.clientInvoker(); 69 | 70 | invoker.invokeHandleBlockBreaking(true); 71 | } 72 | 73 | } 74 | --------------------------------------------------------------------------------