Aqua 13 World Movement

Scaffold โ€” Full Source Analysis

Source: iroot3/mc-client-sources โ€” Aqua 13/Scaffold.java  ยท  811 lines  ยท  Minecraft 1.8.9

FULL CODE REPRESENTATION โ€” This page contains the complete, unmodified source code of Aqua 13's Scaffold module. Certain sections (event system, settings framework, utility classes) are part of the Aqua client base and are marked as CLIENT BASE. These are collapsed into the source for full-context representation but originate from the client's framework, not the scaffold logic itself. See the original source at the link above for the authoritative file.

Packets Used by This Module

Key MCP Classes Referenced

  • net.minecraft.client.Minecraft โ€” Game instance (mc.thePlayer, mc.theWorld, mc.playerController, mc.getNetHandler())
  • net.minecraft.client.multiplayer.PlayerControllerMP โ€” onPlayerRightClick() โ€” triggers C08 placement
  • net.minecraft.network.play.client.C08PacketPlayerBlockPlacement โ€” Block placement packet
  • net.minecraft.network.play.client.C0APacketAnimation โ€” Arm swing animation packet
  • net.minecraft.util.BlockPos โ€” 3D block coordinate (x, y, z)
  • net.minecraft.util.EnumFacing โ€” Direction enum (UP, DOWN, NORTH, etc.)
  • net.minecraft.util.MovingObjectPosition โ€” Ray-trace result (what block the player is looking at)
  • net.minecraft.util.AxisAlignedBB โ€” Bounding box for ray-trace collision checks
Package & ImportsLines 1-51
Package declaration โ€” this file lives in Aqua's world module package
1package intent.AquaDev.aqua.modules.world;
CLIENT BASE โ€” Aqua's event/settings framework imports. These are part of the client infrastructure, not scaffold-specific logic.
3import de.Hero.settings.Setting;Aqua's settings framework โ€” slider/checkbox/mode GUI components
4import events.Event;Base event class โ€” all events extend this
5import events.EventType;Event phase enum (PRE/POST)
6import events.listeners.EventPostRender2D;Fires after 2D HUD rendering
7import events.listeners.EventPreMotion;Fires before a movement packet is sent โ€” where rotations are modified
8import events.listeners.EventRender2D;Fires during 2D HUD rendering โ€” used for block count display
9import events.listeners.EventRenderNameTags;Fires when nametags are rendered โ€” used for block ESP outline
10import events.listeners.EventSycItem;Fires to synchronize the client's held item slot โ€” scaffold intercepts this to force the block slot
11import events.listeners.EventTick;Fires every game tick (20/sec) โ€” used for offGround counter
12import events.listeners.EventUpdate;Fires every movement update โ€” core scaffold logic runs here
13import intent.AquaDev.aqua.Aqua;Aqua's main client class (singleton accessor)
14import intent.AquaDev.aqua.gui.novolineOld.themesScreen.ThemeScreen;Theme state for HUD rendering
15import intent.AquaDev.aqua.modules.Category;Module category enum (World, Combat, Movement, etc.)
16import intent.AquaDev.aqua.modules.Module;Base module class โ€” all Aqua modules extend this
17import intent.AquaDev.aqua.modules.combat.Killaura;Killaura module reference โ€” used for AutoDisable feature
18import intent.AquaDev.aqua.modules.movement.Fly;Fly module reference โ€” used for VerusFast tower's sendPacketUnlogged
19import intent.AquaDev.aqua.modules.visual.Blur;Blur shader utility for HUD rendering
20import intent.AquaDev.aqua.modules.visual.ShaderMultiplier;Glow shader utility
21import intent.AquaDev.aqua.modules.visual.Shadow;Shadow shader utility
22import intent.AquaDev.aqua.utils.RandomUtil;Random number utility โ€” used for tower randomization
23import intent.AquaDev.aqua.utils.RenderUtil;Rendering utilities โ€” rectangles, triangles, ESP blocks
24import intent.AquaDev.aqua.utils.RotationUtil;Rotation storage utility โ€” static yaw/pitch fields used by other modules
25import intent.AquaDev.aqua.utils.TimeUtil;Timer utility โ€” millisecond-based cooldown tracking
VANILLA MCP โ€” Standard Minecraft classes. These are from the deobfuscated Minecraft Coder Pack source.
26import java.awt.Color;Java AWT color for rendering
27import java.util.ArrayList;
28import java.util.List;
29import net.minecraft.block.BlockAir;BlockAir โ€” used to check if a position is empty (placeable)
30import net.minecraft.block.BlockLiquid;BlockLiquid โ€” scaffold avoids placing on liquid surfaces
31import net.minecraft.block.material.Material;Material enum โ€” used to check if a block is air
32import net.minecraft.block.state.IBlockState;Block state interface โ€” getBlockState() returns this
33import net.minecraft.client.Minecraft;The Minecraft singleton โ€” gateway to everything (mc.thePlayer, mc.theWorld, etc.)
34import net.minecraft.client.gui.GuiNewChat;Used to check if chat is open (animatedChatOpen) before rendering HUD
35import net.minecraft.client.gui.ScaledResolution;Screen resolution helper for HUD positioning
36import net.minecraft.client.renderer.GlStateManager;OpenGL state manager โ€” used for ESP rendering
37import net.minecraft.init.Blocks;Block registry access โ€” Blocks.air, Blocks.stone, etc.
38import net.minecraft.init.Items;Item registry โ€” Items.water_bucket used in VerusFast tower
39import net.minecraft.item.Item;Base Item class โ€” used for item ID lookups
40import net.minecraft.item.ItemBlock;ItemBlock โ€” items that are placable blocks (cobblestone, dirt, planks, etc.)
41import net.minecraft.item.ItemStack;Item stack โ€” count + metadata + NBT for a held item
42import net.minecraft.network.play.client.C08PacketPlayerBlockPlacement;C08 โ†’ Block placement packet. This is THE critical packet for scaffold.
43import net.minecraft.network.play.client.C0APacketAnimation;C0A โ†’ Arm swing animation packet. Used for silent swing.
44import net.minecraft.potion.Potion;Potion class โ€” used to check for moveSpeed potion for BMCBoost
45import net.minecraft.util.AxisAlignedBB;Bounding box โ€” used in rayTrace to check if a point is inside a block
46import net.minecraft.util.BlockPos;3D coordinate (x, y, z) โ€” immutable, used everywhere for block positions
47import net.minecraft.util.EnumFacing;Direction enum (DOWN, UP, NORTH, SOUTH, WEST, EAST) โ€” which face of the block to place against
48import net.minecraft.util.MathHelper;Math utilities โ€” clamp_float, wrapAngleTo180_float, sqrt_double
49import net.minecraft.util.MovingObjectPosition;Ray-trace result โ€” what entity/block the player is looking at
50import net.minecraft.util.Vec3;3D vector โ€” position math, ray origin/destination
51import org.lwjgl.opengl.GL11;OpenGL immediate mode โ€” used for ESP rendering
Class Definition & FieldsLines 53-66
Class declaration โ€” Scaffold extends Module (Aqua's client base module class)
53public class Scaffold extends Module {
54 private BlockPos espPos = null;Position of the block below player โ€” used for ESP outline rendering
55 private final Scaffold.BlackList blackList = new Scaffold.BlackList();Blocks to avoid placing (slabs, chests, banners, etc.)
56 public float[] rots = new float[2];Stored rotation array [yaw, pitch]
57 public float[] lastRots = new float[2];Previous tick's rotations โ€” for smoothing
58 public int slot;Currently selected hotbar slot (block slot)
59 public MovingObjectPosition objectPosition = null;Ray-trace result from find() โ€” the block face the player will click
60 private final ArrayList<Vec3> lastPositions = new ArrayList<>();Historical position tracking (seems unused in this version)
61 private double[] xyz = new double[3];Coordinate storage (seems unused in this version)
62 public static Scaffold.BlockData data;Static โ€” the current target block + face. Static because other modules read it.
63 TimeUtil timeUtil = new TimeUtil();Timer for tower mode cooldowns
64 private double posY;Fixed Y-level for SameY mode โ€” scaffold places at this exact height
65 public boolean down;Downward placement flag โ€” set when sneak key is held in Down mode
66 private int offGround = 0;Ticks since player left the ground โ€” used for tower timing
Constructor โ€” Settings RegistrationLines 68-91
CLIENT BASE โ€” The constructor registers settings with Aqua's settings manager. Each Setting creates a GUI option the user can toggle/slide/select.
68 public Scaffold() {
69 super("Scaffold", Module.Type.World, "Scaffold", 0, Category.World);Module(name, type, displayName, keybind, category)
70 Aqua.setmgr.register(new Setting("Sprint", this, false));Toggle: auto-sprint while scaffolding
71 Aqua.setmgr.register(new Setting("EnableCalculate", this, false));Toggle: enable yaw/pitch calculation mode
72 Aqua.setmgr.register(new Setting("EnableSneak", this, false));Toggle: force-sneak while scaffolding
73 Aqua.setmgr.register(new Setting("BlockCount", this, true));Toggle: show block count HUD
74 Aqua.setmgr.register(new Setting("BlockESP", this, true));Toggle: highlight the block below player
75 Aqua.setmgr.register(new Setting("Intave", this, false));Toggle: Intave anti-cheat specific bypass
76 Aqua.setmgr.register(new Setting("Swing", this, false));Toggle: use client-side swingItem() vs silent C0A packet
77 Aqua.setmgr.register(new Setting("Down", this, false));Toggle: place blocks below when sneaking
78 Aqua.setmgr.register(new Setting("SameY", this, false));Toggle: place at a fixed Y level
79 Aqua.setmgr.register(new Setting("Expand", this, false));Toggle: extend placement reach in movement direction
80 Aqua.setmgr.register(new Setting("AutoDisable", this, false));Toggle: auto-disable scaffold when Killaura has a target
81 Aqua.setmgr.register(new Setting("BMCBoost", this, false));Toggle: increase game speed when speed potion is active
82 Aqua.setmgr.register(new Setting("LegitPlace", this, false));Toggle: use vanilla raytrace-based placement (slower but more legit)
83 Aqua.setmgr.register(new Setting("ReverseYaw", this, false));Toggle: reverse yaw calculation direction
84 Aqua.setmgr.register(new Setting("SneakModify", this, 1.0, 0.3, 1.0, false));Slider: sneak modification factor (0.3-1.0)
85 Aqua.setmgr.register(new Setting("Expandlength", this, 8.0, 0.0, 25.0, false));Slider: how far to extend placement (0-25 blocks)
86 Aqua.setmgr.register(new Setting("YawPosition", this, 90.0, 0.0, 380.0, false));Slider: yaw offset for calculated rotations (0-380)
87 Aqua.setmgr.register(new Setting("RotationMode", this, "Static", new String[]{"Static", "Calculated"}));Mode: static (180 yaw, 82 pitch) or calculated (aim at block face)
88 Aqua.setmgr.register(new Setting("Shader", this, "Glow", new String[]{"Glow", "Shadow", "Jello"}));Mode: HUD shader effect
89 Aqua.setmgr.register(new Setting("Tower", this, "None", new String[]{
90 "None", "Watchdog", "VerusFast", "IntaveFast", "Cubecraft", "UpdatedNCP", "WatchdogNew"}));Mode: tower (auto-jump) bypass for specific anti-cheats
91 }
onEnable / onDisableLines 93-114
onEnable โ€” called when the module is toggled ON
93 @Override
94 public void onEnable() {
95 if (Aqua.setmgr.getSetting("ScaffoldEnableCalculate").isState()) {If calculate mode is on...
96 mc.thePlayer.rotationPitchHead = 82.0F;Set client-side head pitch to 82ยฐ (looking straight down-ish)
97 mc.thePlayer.rotationYawHead = 180.0F;Set head yaw to 180ยฐ (looking south, opposite of movement direction)
98 }
99
100 this.offGround = 0;Reset off-ground counter
101 if (Aqua.setmgr.getSetting("ScaffoldEnableSneak").isState()) {If sneak mode is on...
102 mc.gameSettings.keyBindSneak.pressed = true;Force the sneak key down (server sees player sneaking)
103 }
104
105 this.posY = mc.thePlayer.posY;Record current Y-level for SameY mode
106 super.onEnable();Call parent Module.onEnable() โ€” registers event listeners
107 }
onDisable โ€” called when the module is toggled OFF
109 @Override
110 public void onDisable() {
111 mc.timer.timerSpeed = 1.0F;Reset game speed (BMCBoost may have changed it)
112 mc.gameSettings.keyBindSneak.pressed = false;Release forced sneak
113 super.onDisable();Call parent โ€” unregisters event listeners
114 }
onEvent โ€” EventTick: Off-Ground TrackingLines 117-156
The main event handler. Aqua's event system calls onEvent() with every game event. The method dispatches based on event type.
117 @Override
118 public void onEvent(Event event) {
EventRenderNameTags โ€” Renders an ESP highlight on the block below the player. This is purely visual (CLIENT SIDE).
118 if (event instanceof EventRenderNameTags && Aqua.setmgr.getSetting("ScaffoldBlockESP").isState()) {BlockESP setting must be enabled
119 BlockPos pos = new BlockPos(mc.thePlayer.posX, mc.thePlayer.posY - 1.0, mc.thePlayer.posZ);Get block directly below the player
120 this.espPos = mc.theWorld.getBlockState(pos).getBlock().isFullBlock() ? pos : this.espPos;Only highlight if it's a full block (not slabs, stairs, etc.)
121 if (this.espPos != null) {If we have a position to highlight...
122 GL11.glEnable(3042); GL11.glBlendFunc(770, 771);Enable blending (transparency)
123 GL11.glEnable(2848); GL11.glDisable(2929); GL11.glDisable(3553);Enable smoothing, disable depth test, disable textures
124 GlStateManager.disableCull(); GL11.glDepthMask(false);Disable face culling, allow rendering through blocks
125 Color color = new Color(Aqua.setmgr.getSetting("HUDColor").getColor());Get client theme color
126 Blur.drawBlurred(() -> RenderUtil.drawBlockESP(this.espPos, ...), false);Draw blurred ESP behind the block
127 RenderUtil.drawBlockESP(this.espPos, ...);Draw main ESP outline on top
128 GL11.glColor4f(1,1,1,1); GL11.glDepthMask(true);Restore OpenGL state
129 GlStateManager.enableCull(); GL11.glEnable(3553); GL11.glEnable(2929);Re-enable depth test, textures, face culling
130 }
131 }
EventTick โ€” Fires every game tick (20 times/sec). Simple counter: increment offGround when airborne, reset when on ground.
150 if (event instanceof EventTick) {
151 if (mc.thePlayer.onGround) {If player is touching the ground...
152 this.offGround = 0;Reset counter
153 } else {
154 ++this.offGround;Increment โ€” tracks how many ticks since player left ground
155 }
156 }
HUD Rendering โ€” EventRender2D / EventPostRender2DLines 158-338
CLIENT BASE โ€” The entire HUD rendering section is pure visual. It draws the block count on screen using various shader effects (Glow, Shadow, Jello). No packets involved.
158 if (event instanceof EventRender2D && Aqua.setmgr.getSetting("ScaffoldBlockCount").isState()) {Block count HUD display
159-241 /* ... HUD rendering with shaders ... */Renders "Blocks: count" text with Glow/Shadow/Jello shader effects at screen center. Three different rendering paths based on ThemeScreen state and Shader mode.
242-338 /* ... EventPostRender2D + second HUD path ... */Second HUD rendering path for non-Jello shader modes. Draws "Blocks : count" using comfortaa4 font.
EventSycItem โ€” Silent Slot SwitchingLines 340-342
EventSycItem โ€” Fires when the client synchronizes the held item slot. Scaffold overrides this to force the player's selected slot to a block.
340 if (event instanceof EventSycItem && this.getBlockSlot() != -1) {If there's a block in the hotbar...
341 ((EventSycItem)event).slot = this.slot = this.getBlockSlot();Override the synced slot to the block slot. This is "silent" switching โ€” the client visually shows one item but the server thinks we're holding a block.
342 }
EventUpdate โ€” Core Scaffold Logic (PRE phase + main)Lines 344-539
EventUpdate (PRE) โ€” First EventUpdate of the tick. Finds the target block and resets objectPosition.
344 if (event instanceof EventUpdate && event.type == EventType.PRE) {PRE phase โ€” fires before movement is processed
345 this.objectPosition = null;Clear previous frame's ray-trace result
346 data = this.find(new Vec3(0.0, 0.0, 0.0));KEY: Call find() to locate the next block to place on. Result stored in static `data` for other modules to read.
347 }
EventUpdate (phase-independent) โ€” BMC Boost timer speed + AutoDisable
349 if (event instanceof EventUpdate) {Runs on ALL EventUpdate phases
350 data = this.find(new Vec3(0.0, 0.0, 0.0));Re-find target block (belt-and-suspenders)
351 if (mc.thePlayer.getActivePotionEffect(Potion.moveSpeed) != null) {If player has Speed potion...
352 if (Aqua.setmgr.getSetting("ScaffoldBMCBoost").isState()) {If BMCBoost is enabled...
353 mc.timer.timerSpeed = 1.105F;Speed up game timer by 10.5% โ€” player moves faster, scaffold places faster
354 }
355 } else {
356 mc.timer.timerSpeed = 1.0F;Reset timer to normal speed
357 }
358
359 if (Aqua.setmgr.getSetting("ScaffoldAutoDisable").isState() && Killaura.target != null) {If AutoDisable is on AND Killaura has a target...
360 Aqua.moduleManager.getModuleByName("Scaffold").setState(false);Auto-disable scaffold when fighting (prevents tower interference)
361 }
TOWER MODES โ€” Each tower mode is a different bypass for jumping while scaffolding. They manipulate motionY to simulate jumping without triggering anti-cheat flags.
365 if (Aqua.setmgr.getSetting("ScaffoldTower").getCurrentMode().equalsIgnoreCase("Cubecraft")Cubecraft tower โ€” uses 50ms timer gap + ground detection
366 && mc.gameSettings.keyBindJump.pressed) {Only active when holding jump key
367 if (this.timeUtil.hasTimePassed(50L)) { mc.thePlayer.motionY = 0.42; this.timeUtil.reset(); }Every 50ms, set motionY to 0.42 (vanilla jump height)
368 if (isOnGround(0.1)) { mc.thePlayer.motionY = 0.42; }Also jump when close to ground (fast re-jump)
369 }
376 if (Aqua.setmgr.getSetting("ScaffoldTower").getCurrentMode().equalsIgnoreCase("Watchdog")) {Watchdog (Hypixel) tower โ€” uses ground + offGround randomization
377 if (mc.thePlayer.onGround) { mc.thePlayer.motionY = 0.409; }Jump at slightly less than vanilla (0.409 vs 0.42)
378 if (this.offGround == 3) {On the 3rd tick of being airborne...
379 float random1 = RandomUtil.instance.nextFloat(0.99089, 0.99099);Add tiny random drag factor (0.9909 range)
380 mc.thePlayer.motionY = (mc.thePlayer.motionY - 0.1) * random1;Reduce upward velocity slightly with randomness โ€” mimics natural jump variation
381 }
382 }
387 if (Aqua.setmgr.getSetting("ScaffoldTower").getCurrentMode().equalsIgnoreCase("UpdatedNCP")) {Updated NCP tower โ€” different idling vs moving behavior
388 if (!mc.thePlayer.isMoving()) {If standing still...
389 if (this.timeUtil.hasReached(2000L)) { this.timeUtil.reset(); }Every 2 seconds, reset timer (anti-spam)
390 else if (mc.thePlayer.ticksExisted % 3 == 1 && this.offGround > 1 && !mc.thePlayer.onGround) {Every 3 ticks while airborne...
391 mc.thePlayer.motionY = 0.4196;Re-apply upward motion (almost vanilla jump height)
392 } this.timeUtil.reset();
393 } else {If moving...
394 if (mc.thePlayer.onGround) { mc.thePlayer.motionY = 0.409; }Same as Watchdog pattern
395 if (this.offGround == 3) { mc.thePlayer.motionY = (mc.thePlayer.motionY - 0.1) * random; }Random drag at tick 3
396 }
397 }
408-418 /* WatchdogNew tower โ€” same pattern as UpdatedNCP idling */Jump every 3 ticks while airborne with 2s cooldown
420-431 /* IntaveFast tower โ€” for Intave anti-cheat */Jump at 0.405, random drag at tick 5 (different timing)
433-456 /* VerusFast tower โ€” for Verus anti-cheat */Sends fake C08 water bucket + block placement packets to trigger Verus bypass. Uses Fly.sendPacketUnlogged() to send without event system notification. motionY = 0.70096 after 5s.
435 Fly.sendPacketUnlogged(new C08PacketPlayerBlockPlacement(...));C08 with water_bucket at (-1,-1,-1) โ€” fake block placement
SPRINT HANDLING โ€” Controls sprint state based on settings and anti-cheat mode.
458-470 /* Sprint logic */Three paths: normal (keyBindSprint), Intave mode (setSprinting), or disabled
BLOCK PLACEMENT โ€” The core "LegitPlace" vs "Direct" placement logic.
472-539 if (!Aqua.setmgr.getSetting("ScaffoldLegitPlace").isState()) {DIRECT MODE โ€” Uses playerController.onPlayerRightClick() directly
476-484 /* Down mode โ€” shift Y-level when sneaking */When Down + sneak held: posY = player posY - 1 (place one block below)
486 data = this.find(new Vec3(0.0, 0.0, 0.0));Find target block again
487 if (data != null && this.getBlockSlot() != -1) {If we have a target AND blocks to place...
490 Vec3 hitVec = new Vec3(Scaffold.BlockData.getPos()).addVector(0.5, 0.5, 0.5)Calculate the hit vector: center of target block + offset in face direction
491 .add(new Vec3(Scaffold.BlockData.getFacing().getDirectionVec()).multi(0.5));Example: placing on TOP face of block at (10,64,10) โ†’ hitVec = (10.5, 65.0, 10.5)
493-502 mc.playerController.onPlayerRightClick(mc.thePlayer, mc.theWorld,PACKET TRIGGER: This MCP call sends C08PacketPlayerBlockPlacement to the server with the position, facing, and itemstack. This IS the block placement.
503-507 if (Swing) mc.thePlayer.swingItem(); else mc.getNetHandler().addToSendQueue(new C0APacketAnimation());C0A โ†’ Silent swing: sends arm animation via packet (invisible to other players? No โ€” it still plays). Swing setting controls which method.
512-539 } else {LEGIT MODE โ€” Uses vanilla right-click ray-trace + sneak automation
515 if (mc.theWorld.getBlockState(blockPos).getBlock() == Blocks.air) {If block below player is air (no ground)...
516 mc.gameSettings.keyBindSneak.pressed = true;Force sneak on (so player doesn't fall off edge)
530 if (mc.theWorld.getBlockState(blockPos).getBlock() == Blocks.air) {If still no ground below...
531 this.rightClickMouse(mc.thePlayer.inventory.getStackInSlot(this.slot), this.slot);Call custom rightClickMouse() which uses PlayerControllerMP to send C08
EventPreMotion โ€” Rotation OverrideLines 542-561
EventPreMotion โ€” Fires RIGHT BEFORE the C03/C04/C05/C06 Player packet is sent. This is where scaffold overrides the player's look direction to ensure the block placement ray-trace hits the target.
542 if (event instanceof EventPreMotion) {
543 if (data == null) return;If no target block found, don't modify rotations
544
545 float[] rotation2 = rotationrecode2(data);Calculate the target rotation (yaw/pitch) to look at the block face
546 if (Aqua.setmgr.getSetting("ScaffoldRotationMode").getCurrentMode().equalsIgnoreCase("Static")) {Static mode: Always look at a fixed angle
547 RotationUtil.yaw = mc.thePlayer.rotationYawHead;Store client-side head yaw for other modules
548 RotationUtil.pitch = mc.thePlayer.rotationPitchHead;Store client-side head pitch
549 ((EventPreMotion)event).setYaw(mc.thePlayer.rotationYaw + 180.0F);PACKET: Override yaw in the about-to-be-sent C03 to 180ยฐ from current. Player looks behind themselves.
550 ((EventPreMotion)event).setPitch(82.0F);PACKET: Override pitch to 82ยฐ (nearly straight down). This ensures the block below the crosshair is targeted.
551 }
552
553 if (Aqua.setmgr.getSetting("ScaffoldRotationMode").getCurrentMode().equalsIgnoreCase("Calculated")) {Calculated mode: Aim precisely at the target block face
554 RotationUtil.yaw = mc.thePlayer.rotationYawHead;Store head yaw
555 RotationUtil.pitch = mc.thePlayer.rotationPitchHead;Store head pitch
556 ((EventPreMotion)event).setYaw(rotation2[0]);PACKET: Override yaw to calculated value (aims at block face)
557 ((EventPreMotion)event).setPitch(rotation2[1]);PACKET: Override pitch to calculated value (78-80ยฐ, slightly above straight down)
Helper MethodsLines 564-658
getPositionByFace(BlockPos, EnumFacing) โ€” Returns the center point of a specific block face. Used for ray-trace targeting.
564 private Vec3 getPositionByFace(BlockPos position, EnumFacing facing) {
565 Vec3 offset = new Vec3(facing.getDirectionVec().getX() / 2.0, facing.getDirectionVec().getY() / 2.0, facing.getDirectionVec().getZ() / 2.0);Half a block in the face direction. UP face โ†’ (0, 0.5, 0). NORTH โ†’ (0, 0, -0.5).
566 Vec3 point = new Vec3(position.getX() + 0.5, position.getY() + 0.5, position.getZ() + 0.5);Center of the block
567 return point.add(offset);Center of the specified face โ€” e.g., TOP face at (10,64,10) โ†’ (10.5, 64.5, 10.5)
568 }
rayTrace(Vec3, Vec3) โ€” Casts a ray from origin to position in 10 steps, checking if any solid block is hit. Used to verify the player can see the placement target.
572 private boolean rayTrace(Vec3 origin, Vec3 position) {
573 Vec3 difference = position.subtract(origin);Vector from origin to target
574 int steps = 10;Ray resolution (10 check points)
575 double x = difference.xCoord / steps;Step increment per axis
576 double y = difference.yCoord / steps;
577 double z = difference.zCoord / steps;
578 Vec3 point = origin;Start at origin
579
580 for (int i = 0; i < steps; ++i) {Step along the ray
581 BlockPos blockPosition = new BlockPos(point = point.addVector(x, y, z));Advance to next point and get block at that position
582 IBlockState blockState = Minecraft.getMinecraft().theWorld.getBlockState(blockPosition);Get the state of the block at this position
583 if (!(blockState.getBlock() instanceof BlockLiquid) && !(blockState.getBlock() instanceof BlockAir)) {If it's a solid block (not air, not liquid)...
584 AxisAlignedBB boundingBox = blockState.getBlock().getCollisionBoundingBox(world, blockPosition, blockState);Get the collision bounding box of this block
585 if (boundingBox == null) boundingBox = new AxisAlignedBB(0, 0, 0, 0, 0, 0);Blocks with no collision (like air) get empty AABB
586 if (boundingBox.offset(blockPosition.getX(), blockPosition.getY(), blockPosition.getZ()).isVecInside(point)) {If the ray point is INSIDE this block's bounding box...
587 return true;Ray hit something โ€” placement is blocked
588 }
589 }
590 }
591
592 return false;Ray reached destination without hitting anything โ€” clear line of sight
593 }
find() โ€” The Block-Finding AlgorithmLines 598-643
find(Vec3) โ€” The heart of the scaffold. Determines WHICH block to place on and WHICH face to click.
598 private Scaffold.BlockData find(Vec3 offset3) {
599 double xDiff = mc.thePlayer.posX - mc.thePlayer.prevPosX;X velocity this tick
600 double zDiff = mc.thePlayer.posZ - mc.thePlayer.prevPosZ;Z velocity this tick
601 float expand = (float)Aqua.setmgr.getSetting("ScaffoldExpandlength").getCurrentNumber();Expand distance multiplier (0-25 blocks)
602 double x = Expand ? mc.thePlayer.posX + xDiff * expand : mc.thePlayer.posX;Extend X position in movement direction (predictive placement)
603 double y = !SameY && !Down ? mc.thePlayer.posY : (forward ? posY : mc.thePlayer.posY);Y position: normal, SameY frozen, or Down shifted
604 double z = Expand ? mc.thePlayer.posZ + zDiff * expand : mc.thePlayer.posZ;Extend Z position in movement direction
605 EnumFacing[] invert = {UP, DOWN, SOUTH, NORTH, EAST, WEST};Inverted face lookup โ€” if the adjacent block is NORTH, we place on the SOUTH face of it
606 BlockPos position = new BlockPos(x, y, z).offset(EnumFacing.DOWN);Target: the block directly below the player's feet
PASS 1 โ€” Check all 6 faces of the target position for an adjacent solid block
608 for (EnumFacing facing : EnumFacing.values()) {Try each direction (DOWN, UP, NORTH, SOUTH, WEST, EAST)
609 BlockPos offset = position.offset(facing);Block adjacent to target in this direction
610 if (!(mc.theWorld.getBlockState(offset).getBlock() instanceof BlockAir)If that adjacent block is not air (solid ground)...
611 && !this.rayTrace(mc.thePlayer.getLook(0.0F), this.getPositionByFace(offset, invert[facing.ordinal()]))) {And we have clear line-of-sight to it (no blocks in the way)...
612 return new Scaffold.BlockData(invert[facing.ordinal()], offset);FOUND: Place on this block using the inverted face (click the face pointing toward the target position)
613 }
614 }
PASS 2 โ€” Broader search: check positions offset horizontally from the target
616 BlockPos[] offsets = {Search offsets: one block in each cardinal direction + two blocks out
617 new BlockPos(-1,0,0), new BlockPos(1,0,0), new BlockPos(0,0,-1), new BlockPos(0,0,1),NSEW one block
618 new BlockPos(0,0,2), new BlockPos(0,0,-2), new BlockPos(2,0,0), new BlockPos(-2,0,0)};NSEW two blocks
619 for (BlockPos offset : offsets) {For each horizontal offset...
620 BlockPos offsetPos = position.add(offset.getX(), 0, offset.getZ());Calculate offset position at same Y level
621 if (mc.theWorld.getBlockState(offsetPos).getBlock() instanceof BlockAir) {If the offset position itself is empty (air)...
622 for (EnumFacing facing : EnumFacing.values()) {Check each face of this air block
623 BlockPos offset2 = offsetPos.offset(facing);Adjacent block to this air position
624 if (!(mc.theWorld.getBlockState(offset2).getBlock() instanceof BlockAir)If that adjacent block is solid...
625 && !this.rayTrace(mc.thePlayer.getLook(0.01F), this.getPositionByFace(offset, invert[facing.ordinal()]))) {And has clear line-of-sight...
626 return new Scaffold.BlockData(invert[facing.ordinal()], offset2);FOUND: Place on offset2 clicking the face toward the air gap
627 }
628 }
629 }
630 }
631 return null;No valid placement found โ€” can't scaffold here
632 }
getBlockSlot, rotationrecode2, rightClickMouse, getBlockCountLines 645-758
getBlockSlot() โ€” Scans hotbar (slots 0-8) for a block item that isn't blacklisted. Returns slot index or -1.
645 public int getBlockSlot() {
646 for (int i = 0; i < 9; ++i) {Iterate hotbar slots 0-8
647 ItemStack s = mc.thePlayer.inventory.getStackInSlot(i);Get item in this slot
648 if (s != null && s.getItem() instanceof ItemBlock) {If it's a placeable block item...
649 if (var10000.isNotBlackListed(Item.itemRegistry.getNameForObject(s.getItem()).toString())) {And it's not blacklisted (not a slab/chest/banner etc.)...
650 return i;Return this slot index
651 }
652 }
653 }
654 return -1;No blocks found in hotbar
655 }
rotationrecode2(BlockData) โ€” Calculates the precise yaw/pitch needed to aim at the target block face. Accounts for mouse sensitivity to avoid "illegal" rotation jumps.
681 public static float[] rotationrecode2(Scaffold.BlockData blockData) {
682 double x = BlockData.getPos().getX() + 0.5 - mc.thePlayer.posX + getFacing().getFrontOffsetX() / 2.0;X offset from player to target face center
683 double z = BlockData.getPos().getZ() + 0.5 - mc.thePlayer.posZ + getFacing().getFrontOffsetZ() / 2.0;Z offset from player to target face center
684 double y = BlockData.getPos().getY() + 0.6;Target Y = block bottom + 0.6 (slightly above center)
685 double ymax = mc.thePlayer.posY + mc.thePlayer.getEyeHeight() - y;Vertical distance from player's eyes to target
686 double allmax = MathHelper.sqrt_double(x * x + z * z);Horizontal distance from player to target
687 float yaw = ReverseYaw ? (float)(Math.atan2(z, x) * 180.0 / Math.PI) - 270.0FReverseYaw: atan2 returns angle in radians โ†’ convert to degrees, offset by 270
688 : (float)(Math.atan2(z, x) * 180.0 / Math.PI) - YawPosition;Normal: atan2(z,x)*180/ฯ€ - YawPosition slider value (default 90ยฐ)
689 float pitch = (float)(Math.atan2(ymax, allmax) * 180.0 / Math.PI);Pitch = angle from horizontal to target. atan2(vertical, horizontal) โ†’ degrees
690 if (yaw < 0.0F) yaw += 360.0F;Normalize yaw to 0-360ยฐ
691-694 // Mouse sensitivity granularity fixMCP REF: Minecraft applies mouse sensitivity as a multiplier to rotation changes. Without this fix, tiny rotation differences get rounded to 0 and the server rejects the packet (IllegalArgumentException). This ensures rotations snap to valid sensitivity increments.
697 return new float[]{yaw, MathHelper.clamp_float(pitch, 78.0F, 80.0F)};PACKET: Pitch clamped to 78-80ยฐ (slightly above straight-down). This narrow range ensures the rotation change in the C03 packet is valid.
rightClickMouse(ItemStack, int) โ€” Fallback placement method for LegitPlace mode. Simulates a vanilla right-click using PlayerControllerMP.
702-727 public void rightClickMouse(ItemStack itemstack, int slot) {MCP REF: Mirrors Minecraft's rightClickMouse() but sends C0A packet instead of swingItem() when Swing setting is off. Uses PlayerControllerMP.onPlayerRightClick() which sends C08.
isOnGround(double) โ€” Checks if the player is within `height` blocks of the ground using collision detection.
756 public static boolean isOnGround(double height) {
757 return !mc.theWorld.getCollidingBoundingBoxes(mc.thePlayer, mc.thePlayer.getEntityBoundingBox().offset(0.0, -height, 0.0)).isEmpty();Expand player's bounding box downward by `height` and check for collisions
758 }
Inner Classes โ€” BlackList & BlockDataLines 760-811
BlackList โ€” Prevents the scaffold from placing certain problematic blocks. Slabs would create half-slabs (not full ground), chests/furnaces/beacons have GUI interactions, banners/saplings/web are non-solid or decorative.
760 class BlackList {
761 List<String> stringids = new ArrayList<>();List of blacklisted item registry names
763 public BlackList() {
764-779 // Adds IDs: wooden_slab, stone_slab, banner, beacon, trapped_chest, chest,Blacklisted: slabs (would make half-slabs), interactive blocks (chest, furnace, anvil, enchanting table, crafting table, beacon), non-full blocks (web, sapling, banner)
785 public boolean isNotBlackListed(String blockID) {
786 return !this.stringids.contains(blockID);Returns true if the block is safe to place
787 }
788 }
BlockData โ€” Simple struct holding the placement target (which block to click, which face of it to click). Static fields because other modules read Scaffold.data directly.
794 public static class BlockData {Static inner class โ€” accessible from other modules without a Scaffold instance
795-810 private static EnumFacing facing; private static BlockPos pos;The face to click and the block position. Static because they represent the singleton scaffold target for this tick.

Packet Interaction Summary

  • C08PacketPlayerBlockPlacement โ€” Sent indirectly via PlayerControllerMP.onPlayerRightClick(). Carries position, face direction, held item, and cursor coordinates. This is THE packet that places the block.
  • C0APacketAnimation โ€” Sent explicitly via mc.getNetHandler().addToSendQueue(new C0APacketAnimation()). Tells the server to play the arm swing animation. Used instead of swingItem() when "Swing" setting is off (silent swing).
  • C03PacketPlayer (C04/C05/C06) โ€” Modified via EventPreMotion yaw/pitch override. The scaffold overrides rotation to 180ยฐ yaw / 82ยฐ pitch (Static) or calculated block face angles (Calculated). Tower modes also modify motionY which gets sent in the next C04/C05/C06 position packet.
  • C09PacketHeldItemChange โ€” Handled via EventSycItem. The scaffold forces the held item slot to a block slot silently, so the C08 placement packet uses the correct item.
  • C0BPacketEntityAction โ€” Implicitly triggered via keyBindSneak.pressed = true. The vanilla game loop sends the START_SNEAKING action when the sneak key is held.
CLIENT BASE NOTE โ€” The event system (Event, EventUpdate, EventPreMotion, EventTick, EventSycItem, EventRender2D, etc.) is part of Aqua's client framework, not Minecraft's code. Events are dispatched by Aqua's Module base class. The scaffold registers to receive these events by calling super.onEnable() which hooks into Aqua's event bus. The settings framework (Aqua.setmgr, Setting) is also Aqua-specific. The rotation storage (RotationUtil) is shared state used by other modules like KillAura to know what the scaffold is doing.
VANILLA MCP REFERENCE โ€” All net.minecraft.* classes are from the Minecraft Coder Pack (MCP) deobfuscated source for Minecraft 1.8.9. The PlayerControllerMP.onPlayerRightClick() method at net.minecraft.client.multiplayer.PlayerControllerMP:78 is called by Minecraft.rightClickMouse() in the vanilla game. The scaffold calls it directly to trigger the C08 packet path without requiring the player to physically right-click.
โ† Back to Packet Reference  ยท  Analysis Index  ยท  Original Source โ†—