Подписывайтесь на наш Telegram и не пропускайте важные новости! Перейти

Часть функционала FTbaseFinder - ищет базы на фт (1.21.4 Fabric)

Начинающий
Начинающий
Статус
Оффлайн
Регистрация
6 Сен 2025
Сообщения
27
Реакции
0
Выберите загрузчик игры
  1. Fabric
Средний модуль ищет базы на фантайме, есть немного ии кода, логика +- хорошая есть защита от лавы/воды пропасти атаки и другие фишки, не захотел ебаться с баритоном просто написал такой модуль. Кто хочет - пастите.

Может кому пригодиться :3

код:
Expand Collapse Copy
package fun.vortex.features.impl.player;

import fun.vortex.events.player.TickEvent;
import fun.vortex.features.module.ModuleCategory;
import fun.vortex.features.module.setting.implement.SelectSetting;
import fun.vortex.features.module.setting.implement.SliderSettings;
import fun.vortex.utils.client.chat.ChatMessage;
import fun.vortex.utils.client.managers.event.EventHandler;
import fun.vortex.utils.features.aura.warp.TurnsConnection;
import net.minecraft.block.BlockState;
import fun.vortex.events.render.WorldRenderEvent;
import fun.vortex.utils.display.color.ColorAssist;
import net.minecraft.util.math.Box;
import net.minecraft.component.DataComponentTypes;
import net.minecraft.component.type.ItemEnchantmentsComponent;
import net.minecraft.component.type.ToolComponent;
import net.minecraft.enchantment.Enchantment;
import net.minecraft.enchantment.Enchantments;
import net.minecraft.item.ItemStack;
import net.minecraft.item.Items;
import net.minecraft.item.PickaxeItem;
import net.minecraft.network.packet.c2s.play.PlayerActionC2SPacket;
import net.minecraft.network.packet.c2s.play.PlayerInteractBlockC2SPacket;
import net.minecraft.registry.entry.RegistryEntry;
import net.minecraft.util.Hand;
import net.minecraft.util.hit.BlockHitResult;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.Direction;
import net.minecraft.util.math.Vec3d;

import fun.vortex.features.module.Module;
public class FTBaseFinder extends Module {

    private final SelectSetting direction = new SelectSetting("Направление", "Куда копать")
            .value("North", "East", "South", "West").selected("North");

    private final SliderSettings targetY = new SliderSettings("Высота", "Целевая высота")
            .range(-60, 60).setValue(15);

    private final SelectSetting oreType = new SelectSetting("Блок проверки", "Что ставить")
            .value("Diamond Ore", "Emerald Ore").selected("Diamond Ore");

    private final SliderSettings checkDistance = new SliderSettings("Дистанция проверки", "Раз в сколько блоков ставить руду")
            .range(5, 100).setValue(25);

    private boolean diggingDown = true;
    private int distanceCounter = 0;
    private BlockPos blockToBreak = null;

    public FTBaseFinder() {
        super("FT-BaseFinder", "FTBaseFinder", ModuleCategory.PLAYER);
        setup(direction, targetY, oreType, checkDistance);
    }

    @Override
    public void activate() {
        if (mc.player == null) {
            this.switchState();
            return;
        }
        if (!hasRequiredItems()) {
            ChatMessage.brandmessage("§c[Ошибка] §fНет кирки на Шелковое касание или руды в хотбаре!");
            this.switchState();
            return;
        }

        diggingDown = true;
        distanceCounter = 0;
        blockToBreak = null;
        ChatMessage.brandmessage("§a[Старт] §fСпускаюсь на высоту " + targetY.getInt());
        super.activate();
    }

    @Override
    public void deactivate() {
        if (mc.options != null) {
            mc.options.forwardKey.setPressed(false);
        }
        super.deactivate();
    }

    private BlockPos pendingOrePos = null;
    private BlockPos shouldPlaceOreAfterBreak = null;
    private boolean isBypassing = false;
    private int bypassTicks = 0;
    private BlockPos bypassTarget = null;

    @EventHandler
    public void onTick(TickEvent ignored) {
        if (mc.player == null || mc.world == null) return;

        if (mc.player.hurtTime > 0) {

            boolean isEntityDamage = mc.world.getEntitiesByClass(net.minecraft.entity.mob.HostileEntity.class,
                    mc.player.getBoundingBox().expand(5), e -> true).size() > 0;

            if (isEntityDamage && System.currentTimeMillis() - lastDamageTime > 5000) {
                ChatMessage.brandmessage("§c§l[ВНИМАНИЕ] §fВас атакует моб! Остановка.");
                this.switchState();
                return;
            }
        }

        if (pendingOrePos != null && mc.world.isAir(pendingOrePos)) {
            if (!tryPlaceOre(pendingOrePos)) {
                ChatMessage.brandmessage("§6§l[БАЗА!] §fПриват на: §a" + pendingOrePos.toShortString());
                this.switchState();
                return;
            } else {
                mineBackOre(pendingOrePos);
                pendingOrePos = null;
            }
        }

        if (blockToBreak != null) {
            if (mc.world.isAir(blockToBreak)) {
                blockToBreak = null;
            } else {
                processBlockMining(blockToBreak);
                return;
            }
        }

        if (diggingDown) {
            handleDescending();
        } else {
            handleTunneling();
        }
    }

    private BlockPos lastCheckPos = null;
    private long lastDamageTime = 0;

    private void handleDescending() {
        BlockPos playerPos = BlockPos.ofFloored(mc.player.getPos());
        BlockPos underPlayer = playerPos.down();

        if (isLiquidBelow(underPlayer)) {
            ChatMessage.brandmessage("§c[!] §fПод ногами обнаружена жидкость. Запуск сканирования 10x10...");

            BlockPos safePoint = findBestSafePoint(playerPos);

            if (safePoint != null) {
                double distance = Math.sqrt(playerPos.getSquaredDistance(safePoint));
                ChatMessage.brandmessage(String.format("§a[Навигатор] §fНайдена безопасная зона в %.1f м. Обхожу...", distance));
                moveTowards(safePoint);
            } else {
                ChatMessage.brandmessage("§4[Крит] §fВ радиусе 10 блоков нет безопасных мест. Смена вектора...");
                direction.selected(Direction.Type.HORIZONTAL.random(mc.world.random).asString());
            }
            return;
        }

        if (mc.player.getY() <= targetY.getValue()) {
            diggingDown = false;
            ChatMessage.brandmessage("§6[Инфо] §fЦелевая высота " + targetY.getInt() + " достигнута. Начинаю копку туннеля.");
            return;
        }

        if (!mc.world.isAir(underPlayer)) {
            blockToBreak = underPlayer;
        }
    }

    private BlockPos findBestSafePoint(BlockPos startPos) {
        BlockPos bestPos = null;
        double minDistance = Double.MAX_VALUE;

        for (int x = -10; x <= 10; x++) {
            for (int z = -10; z <= 10; z++) {
                BlockPos checkPos = startPos.add(x, 0, z);

                if (isValidSafeSpot(checkPos)) {
                    double dist = startPos.getSquaredDistance(checkPos);
                    if (dist < minDistance) {
                        minDistance = dist;
                        bestPos = checkPos;
                    }
                }
            }
        }
        return bestPos;
    }

    private boolean isValidSafeSpot(BlockPos pos) {
        boolean isSpaceClear = mc.world.getBlockState(pos).isAir() &&
                mc.world.getBlockState(pos.up()).isAir();

        if (!isSpaceClear) return false;

        for (int i = 0; i <= 5; i++) {
            if (mc.world.getBlockState(pos.down(i)).isLiquid()) {
                return false;
            }
        }

        return !mc.world.getBlockState(pos.down()).isAir();
    }

    private boolean isLiquidBelow(BlockPos startPos) {
        for (int i = 0; i < 5; i++) {
            BlockState state = mc.world.getBlockState(startPos.down(i));
            if (state.isLiquid()) return true;
        }
        return false;
    }

    private void tryToBypassDanger(BlockPos currentPos) {

        for (Direction dir : Direction.Type.HORIZONTAL) {
            BlockPos sidePos = currentPos.offset(dir);
            if (!isLiquidBelow(sidePos) && mc.world.isAir(sidePos)) {
                moveTowards(sidePos);
                return;
            }
        }
        ChatMessage.brandmessage("§c[Внимание] §f Безопасный путь не найден. Стоп.");
        this.switchState();
    }

    private void moveTowards(BlockPos pos) {
        if (mc.player == null) return;

        rotateHeadToBlock(pos);

        double dx = pos.getX() + 0.5 - mc.player.getX();
        double dz = pos.getZ() + 0.5 - mc.player.getZ();
        double distance = Math.sqrt(dx * dx + dz * dz);

        if (distance > 0.3) {
            mc.options.forwardKey.setPressed(true);
            if (mc.player.horizontalCollision) {
                mc.options.jumpKey.setPressed(true);
            } else {
                mc.options.jumpKey.setPressed(false);
            }
        } else {
            mc.options.forwardKey.setPressed(false);
            mc.options.jumpKey.setPressed(false);
        }
    }

    private void handleTunneling() {
        Direction dir = Direction.byName(direction.getSelected().toLowerCase());
        if (dir == null) dir = Direction.NORTH;

        BlockPos playerPos = BlockPos.ofFloored(mc.player.getPos());
        BlockPos forwardLower = playerPos.offset(dir);
        BlockPos forwardUpper = forwardLower.up();
        BlockPos gapPos = forwardLower.down();

        // Проверка жидкостей
        if (mc.world.getBlockState(forwardLower).isLiquid() || mc.world.getBlockState(forwardUpper).isLiquid()) {
            direction.selected(dir.rotateYClockwise().asString());
            return;
        }

        if (mc.world.getBlockState(gapPos).isAir() || mc.world.getBlockState(gapPos).isLiquid()) {
            mc.options.forwardKey.setPressed(false);
            placeBridge(gapPos);
            return;
        }

        if (!isBlockPassable(forwardUpper) || !isBlockPassable(forwardLower)) {
            mc.options.forwardKey.setPressed(false);
            blockToBreak = !isBlockPassable(forwardUpper) ? forwardUpper : forwardLower;
        } else {
            mc.options.sneakKey.setPressed(false);
            if (blockToBreak == null && pendingOrePos == null) {
                moveForward();

                // ИНИЦИАЛИЗАЦИЯ ПОЗИЦИИ
                if (lastCheckPos == null) lastCheckPos = playerPos;

                double dist = Math.sqrt(playerPos.getSquaredDistance(lastCheckPos));
                if (dist >= checkDistance.getValue()) {
                    mc.options.forwardKey.setPressed(false);
                    checkBaseWithOre(dir);
                    lastCheckPos = playerPos; // Обнуляем точку отсчета
                }
            }
        }
    }
    private boolean checkForDanger(BlockPos pos) {
        if (mc.world == null) return false;
        BlockState floor = mc.world.getBlockState(pos.down());
        boolean isVoid = floor.isAir();
        boolean isLiquid = mc.world.getBlockState(pos).isLiquid() || floor.isLiquid();
        return isVoid || isLiquid;
    }

    private void processBlockMining(BlockPos pos) {
        if (mc.world == null || mc.player == null || mc.interactionManager == null) return;

        if (checkForLiquids(pos)) {
            ChatMessage.brandmessage("§c[Внимание] §fОбнаружена лава/вода. Остановка.");
            this.switchState();
            return;
        }

        selectBestTool(mc.world.getBlockState(pos));
        rotateHeadToBlock(pos);

        mc.interactionManager.updateBlockBreakingProgress(pos, Direction.UP);
        mc.player.swingHand(Hand.MAIN_HAND);
    }

    private int findFillerBlock() {
        for (int i = 0; i < 9; i++) {
            ItemStack stack = mc.player.getInventory().getStack(i);
            if (stack.isEmpty()) continue;
            String name = stack.getItem().toString();
            if (name.contains("stone") || name.contains("dirt") || name.contains("cobble") ||
                    name.contains("netherrack") || name.contains("deepslate") || name.contains("andesite")) {
                return i;
            }
        }
        return -1;
    }

    private void placeBridge(BlockPos targetPos) {
        int fillerSlot = findFillerBlock();
        if (fillerSlot == -1) {
            ChatMessage.brandmessage("§c[Ошибка] §fНет блоков для застройки!");
            this.switchState();
            return;
        }

        mc.options.forwardKey.setPressed(false);
        mc.options.sneakKey.setPressed(true);
        int oldSlot = mc.player.getInventory().selectedSlot;
        mc.player.getInventory().selectedSlot = fillerSlot;

        rotateHeadToBlock(targetPos);

        BlockHitResult hit = new BlockHitResult(targetPos.toCenterPos(), Direction.UP, targetPos, false);
        mc.interactionManager.interactBlock(mc.player, Hand.MAIN_HAND, hit);
        mc.player.swingHand(Hand.MAIN_HAND);

        mc.player.getInventory().selectedSlot = oldSlot;
    }
    @EventHandler
    public void onRender3D(WorldRenderEvent event) {
        if (!state || mc.world == null || mc.player == null) return;

        if (blockToBreak != null) {
            fun.vortex.utils.display.geometry.Render3D.drawBox(new Box(blockToBreak), ColorAssist.getColor(255, 0, 0, 100), 1);
        }

        if (!diggingDown) {
            Direction dir = Direction.byName(direction.getSelected().toLowerCase());
            if (dir != null) {
                BlockPos p = mc.player.getBlockPos();
                BlockPos f1 = p.offset(dir);
                BlockPos f2 = p.up().offset(dir);

                if (!mc.world.isAir(f1) && !f1.equals(blockToBreak)) fun.vortex.utils.display.geometry.Render3D.drawBox(new Box(f1), ColorAssist.getColor(0, 255, 0, 50), 1);
                if (!mc.world.isAir(f2) && !f2.equals(blockToBreak)) fun.vortex.utils.display.geometry.Render3D.drawBox(new Box(f2), ColorAssist.getColor(0, 255, 0, 50), 1);
            }
        }
    }

    private void checkBaseWithOre(Direction dir) {
        Direction sideDir = dir.rotateYClockwise();
        BlockPos wallPos = mc.player.getBlockPos().offset(sideDir).up();

        if (!mc.world.isAir(wallPos)) {

            blockToBreak = wallPos;
            pendingOrePos = wallPos;
            shouldPlaceOreAfterBreak = wallPos;
        }
    }

    private void selectBestTool(BlockState blockState) {
        if (mc.player == null) return;
        int bestSlot = -1;
        float bestSpeed = 0;
        for (int i = 0; i < 9; i++) {
            ItemStack stack = mc.player.getInventory().getStack(i);
            if (stack.isEmpty()) continue;

            ToolComponent tool = stack.get(DataComponentTypes.TOOL);
            float speed = (tool != null) ? tool.getSpeed(blockState) : 1.0f;

            if (speed > bestSpeed) {
                bestSpeed = speed;
                bestSlot = i;
            }
        }
        if (bestSlot != -1) {
            mc.player.getInventory().selectedSlot = bestSlot;
        }
    }

    private void rotateHeadToBlock(BlockPos pos) {
        if (mc.player == null) return;
        Vec3d target = pos.toCenterPos();
        Vec3d eyePos = mc.player.getEyePos();
        double dx = target.x - eyePos.x;
        double dy = target.y - eyePos.y;
        double dz = target.z - eyePos.z;
        float yaw = (float) Math.toDegrees(Math.atan2(dz, dx)) - 90.0F;
        float pitch = (float) -Math.toDegrees(Math.atan2(dy, Math.sqrt(dx * dx + dz * dz)));
        double gcd = fun.vortex.utils.math.calc.Calculate.computeGcd();
        if (gcd > 0) {
            float lastYaw = TurnsConnection.INSTANCE.getRotation().getYaw();
            float lastPitch = TurnsConnection.INSTANCE.getRotation().getPitch();

            float deltaYaw = yaw - lastYaw;
            float deltaPitch = pitch - lastPitch;

            yaw = lastYaw + (float) (deltaYaw - (deltaYaw % gcd));
            pitch = lastPitch + (float) (deltaPitch - (deltaPitch % gcd));
        }
        pitch = net.minecraft.util.math.MathHelper.clamp(pitch, -90.0f, 90.0f);

        TurnsConnection.INSTANCE.getRotation().setYaw(yaw);
        TurnsConnection.INSTANCE.getRotation().setPitch(pitch);
        mc.player.setYaw(yaw);
        mc.player.setPitch(pitch);
    }

    private void moveForward() {
        if (mc.options == null) return;
        mc.options.forwardKey.setPressed(true);
    }

    private boolean isBlockPassable(BlockPos pos) {
        if (mc.world == null) return false;
        return !mc.world.getBlockState(pos).isOpaque();
    }

    private boolean checkForLiquids(BlockPos pos) {
        if (mc.world == null) return false;
        return mc.world.getBlockState(pos).isLiquid();
    }

    private boolean tryPlaceOre(BlockPos pos) {
        if (mc.player == null || mc.interactionManager == null || mc.world == null) return false;
        int oreSlot = findOreSlot();
        if (oreSlot == -1) return false;

        int oldSlot = mc.player.getInventory().selectedSlot;
        mc.player.getInventory().selectedSlot = oreSlot;

        rotateHeadToBlock(pos);

        BlockHitResult hitResult = new BlockHitResult(pos.toCenterPos(), Direction.UP, pos, false);
        mc.interactionManager.interactBlock(mc.player, Hand.MAIN_HAND, hitResult);
        mc.player.swingHand(Hand.MAIN_HAND);

        boolean placed = !mc.world.getBlockState(pos).isAir();
        mc.player.getInventory().selectedSlot = oldSlot;

        return placed;
    }

    private void mineBackOre(BlockPos pos) {
        if (mc.player == null || mc.player.networkHandler == null) return;
        int pickaxeSlot = findSilkTouchPickaxe();
        if (pickaxeSlot == -1) return;

        int oldSlot = mc.player.getInventory().selectedSlot;
        mc.player.getInventory().selectedSlot = pickaxeSlot;

        mc.player.networkHandler.sendPacket(new PlayerActionC2SPacket(PlayerActionC2SPacket.Action.START_DESTROY_BLOCK, pos, Direction.UP));
        mc.player.networkHandler.sendPacket(new PlayerActionC2SPacket(PlayerActionC2SPacket.Action.STOP_DESTROY_BLOCK, pos, Direction.UP));
        mc.player.swingHand(Hand.MAIN_HAND);

        mc.player.getInventory().selectedSlot = oldSlot;
    }

    private boolean hasRequiredItems() {
        if (mc.player == null) return false;
        return findSilkTouchPickaxe() != -1 && findOreSlot() != -1;
    }

    private int findSilkTouchPickaxe() {
        if (mc.player == null) return -1;
        for (int i = 0; i < 9; i++) {
            ItemStack stack = mc.player.getInventory().getStack(i);
            if (stack.getItem() instanceof PickaxeItem) {
                ItemEnchantmentsComponent enchants = stack.get(DataComponentTypes.ENCHANTMENTS);
                if (enchants != null) {
                    for (RegistryEntry<Enchantment> enchant : enchants.getEnchantments()) {
                        if (enchant.matchesKey(Enchantments.SILK_TOUCH)) return i;
                    }
                }
            }
        }
        return -1;
    }

    private int findOreSlot() {
        if (mc.player == null) return -1;
        for (int i = 0; i < 9; i++) {
            ItemStack s = mc.player.getInventory().getStack(i);
            if (oreType.isSelected("Diamond Ore") && s.isOf(Items.DIAMOND_ORE)) return i;
            if (oreType.isSelected("Emerald Ore") && s.isOf(Items.EMERALD_ORE)) return i;
        }
        return -1;
    }
}
 
Средний модуль ищет базы на фантайме, есть немного ии кода, логика +- хорошая есть защита от лавы/воды пропасти атаки и другие фишки, не захотел ебаться с баритоном просто написал такой модуль. Кто хочет - пастите.

Может кому пригодиться :3

код:
Expand Collapse Copy
package fun.vortex.features.impl.player;

import fun.vortex.events.player.TickEvent;
import fun.vortex.features.module.ModuleCategory;
import fun.vortex.features.module.setting.implement.SelectSetting;
import fun.vortex.features.module.setting.implement.SliderSettings;
import fun.vortex.utils.client.chat.ChatMessage;
import fun.vortex.utils.client.managers.event.EventHandler;
import fun.vortex.utils.features.aura.warp.TurnsConnection;
import net.minecraft.block.BlockState;
import fun.vortex.events.render.WorldRenderEvent;
import fun.vortex.utils.display.color.ColorAssist;
import net.minecraft.util.math.Box;
import net.minecraft.component.DataComponentTypes;
import net.minecraft.component.type.ItemEnchantmentsComponent;
import net.minecraft.component.type.ToolComponent;
import net.minecraft.enchantment.Enchantment;
import net.minecraft.enchantment.Enchantments;
import net.minecraft.item.ItemStack;
import net.minecraft.item.Items;
import net.minecraft.item.PickaxeItem;
import net.minecraft.network.packet.c2s.play.PlayerActionC2SPacket;
import net.minecraft.network.packet.c2s.play.PlayerInteractBlockC2SPacket;
import net.minecraft.registry.entry.RegistryEntry;
import net.minecraft.util.Hand;
import net.minecraft.util.hit.BlockHitResult;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.Direction;
import net.minecraft.util.math.Vec3d;

import fun.vortex.features.module.Module;
public class FTBaseFinder extends Module {

    private final SelectSetting direction = new SelectSetting("Направление", "Куда копать")
            .value("North", "East", "South", "West").selected("North");

    private final SliderSettings targetY = new SliderSettings("Высота", "Целевая высота")
            .range(-60, 60).setValue(15);

    private final SelectSetting oreType = new SelectSetting("Блок проверки", "Что ставить")
            .value("Diamond Ore", "Emerald Ore").selected("Diamond Ore");

    private final SliderSettings checkDistance = new SliderSettings("Дистанция проверки", "Раз в сколько блоков ставить руду")
            .range(5, 100).setValue(25);

    private boolean diggingDown = true;
    private int distanceCounter = 0;
    private BlockPos blockToBreak = null;

    public FTBaseFinder() {
        super("FT-BaseFinder", "FTBaseFinder", ModuleCategory.PLAYER);
        setup(direction, targetY, oreType, checkDistance);
    }

    @Override
    public void activate() {
        if (mc.player == null) {
            this.switchState();
            return;
        }
        if (!hasRequiredItems()) {
            ChatMessage.brandmessage("§c[Ошибка] §fНет кирки на Шелковое касание или руды в хотбаре!");
            this.switchState();
            return;
        }

        diggingDown = true;
        distanceCounter = 0;
        blockToBreak = null;
        ChatMessage.brandmessage("§a[Старт] §fСпускаюсь на высоту " + targetY.getInt());
        super.activate();
    }

    @Override
    public void deactivate() {
        if (mc.options != null) {
            mc.options.forwardKey.setPressed(false);
        }
        super.deactivate();
    }

    private BlockPos pendingOrePos = null;
    private BlockPos shouldPlaceOreAfterBreak = null;
    private boolean isBypassing = false;
    private int bypassTicks = 0;
    private BlockPos bypassTarget = null;

    @EventHandler
    public void onTick(TickEvent ignored) {
        if (mc.player == null || mc.world == null) return;

        if (mc.player.hurtTime > 0) {

            boolean isEntityDamage = mc.world.getEntitiesByClass(net.minecraft.entity.mob.HostileEntity.class,
                    mc.player.getBoundingBox().expand(5), e -> true).size() > 0;

            if (isEntityDamage && System.currentTimeMillis() - lastDamageTime > 5000) {
                ChatMessage.brandmessage("§c§l[ВНИМАНИЕ] §fВас атакует моб! Остановка.");
                this.switchState();
                return;
            }
        }

        if (pendingOrePos != null && mc.world.isAir(pendingOrePos)) {
            if (!tryPlaceOre(pendingOrePos)) {
                ChatMessage.brandmessage("§6§l[БАЗА!] §fПриват на: §a" + pendingOrePos.toShortString());
                this.switchState();
                return;
            } else {
                mineBackOre(pendingOrePos);
                pendingOrePos = null;
            }
        }

        if (blockToBreak != null) {
            if (mc.world.isAir(blockToBreak)) {
                blockToBreak = null;
            } else {
                processBlockMining(blockToBreak);
                return;
            }
        }

        if (diggingDown) {
            handleDescending();
        } else {
            handleTunneling();
        }
    }

    private BlockPos lastCheckPos = null;
    private long lastDamageTime = 0;

    private void handleDescending() {
        BlockPos playerPos = BlockPos.ofFloored(mc.player.getPos());
        BlockPos underPlayer = playerPos.down();

        if (isLiquidBelow(underPlayer)) {
            ChatMessage.brandmessage("§c[!] §fПод ногами обнаружена жидкость. Запуск сканирования 10x10...");

            BlockPos safePoint = findBestSafePoint(playerPos);

            if (safePoint != null) {
                double distance = Math.sqrt(playerPos.getSquaredDistance(safePoint));
                ChatMessage.brandmessage(String.format("§a[Навигатор] §fНайдена безопасная зона в %.1f м. Обхожу...", distance));
                moveTowards(safePoint);
            } else {
                ChatMessage.brandmessage("§4[Крит] §fВ радиусе 10 блоков нет безопасных мест. Смена вектора...");
                direction.selected(Direction.Type.HORIZONTAL.random(mc.world.random).asString());
            }
            return;
        }

        if (mc.player.getY() <= targetY.getValue()) {
            diggingDown = false;
            ChatMessage.brandmessage("§6[Инфо] §fЦелевая высота " + targetY.getInt() + " достигнута. Начинаю копку туннеля.");
            return;
        }

        if (!mc.world.isAir(underPlayer)) {
            blockToBreak = underPlayer;
        }
    }

    private BlockPos findBestSafePoint(BlockPos startPos) {
        BlockPos bestPos = null;
        double minDistance = Double.MAX_VALUE;

        for (int x = -10; x <= 10; x++) {
            for (int z = -10; z <= 10; z++) {
                BlockPos checkPos = startPos.add(x, 0, z);

                if (isValidSafeSpot(checkPos)) {
                    double dist = startPos.getSquaredDistance(checkPos);
                    if (dist < minDistance) {
                        minDistance = dist;
                        bestPos = checkPos;
                    }
                }
            }
        }
        return bestPos;
    }

    private boolean isValidSafeSpot(BlockPos pos) {
        boolean isSpaceClear = mc.world.getBlockState(pos).isAir() &&
                mc.world.getBlockState(pos.up()).isAir();

        if (!isSpaceClear) return false;

        for (int i = 0; i <= 5; i++) {
            if (mc.world.getBlockState(pos.down(i)).isLiquid()) {
                return false;
            }
        }

        return !mc.world.getBlockState(pos.down()).isAir();
    }

    private boolean isLiquidBelow(BlockPos startPos) {
        for (int i = 0; i < 5; i++) {
            BlockState state = mc.world.getBlockState(startPos.down(i));
            if (state.isLiquid()) return true;
        }
        return false;
    }

    private void tryToBypassDanger(BlockPos currentPos) {

        for (Direction dir : Direction.Type.HORIZONTAL) {
            BlockPos sidePos = currentPos.offset(dir);
            if (!isLiquidBelow(sidePos) && mc.world.isAir(sidePos)) {
                moveTowards(sidePos);
                return;
            }
        }
        ChatMessage.brandmessage("§c[Внимание] §f Безопасный путь не найден. Стоп.");
        this.switchState();
    }

    private void moveTowards(BlockPos pos) {
        if (mc.player == null) return;

        rotateHeadToBlock(pos);

        double dx = pos.getX() + 0.5 - mc.player.getX();
        double dz = pos.getZ() + 0.5 - mc.player.getZ();
        double distance = Math.sqrt(dx * dx + dz * dz);

        if (distance > 0.3) {
            mc.options.forwardKey.setPressed(true);
            if (mc.player.horizontalCollision) {
                mc.options.jumpKey.setPressed(true);
            } else {
                mc.options.jumpKey.setPressed(false);
            }
        } else {
            mc.options.forwardKey.setPressed(false);
            mc.options.jumpKey.setPressed(false);
        }
    }

    private void handleTunneling() {
        Direction dir = Direction.byName(direction.getSelected().toLowerCase());
        if (dir == null) dir = Direction.NORTH;

        BlockPos playerPos = BlockPos.ofFloored(mc.player.getPos());
        BlockPos forwardLower = playerPos.offset(dir);
        BlockPos forwardUpper = forwardLower.up();
        BlockPos gapPos = forwardLower.down();

        // Проверка жидкостей
        if (mc.world.getBlockState(forwardLower).isLiquid() || mc.world.getBlockState(forwardUpper).isLiquid()) {
            direction.selected(dir.rotateYClockwise().asString());
            return;
        }

        if (mc.world.getBlockState(gapPos).isAir() || mc.world.getBlockState(gapPos).isLiquid()) {
            mc.options.forwardKey.setPressed(false);
            placeBridge(gapPos);
            return;
        }

        if (!isBlockPassable(forwardUpper) || !isBlockPassable(forwardLower)) {
            mc.options.forwardKey.setPressed(false);
            blockToBreak = !isBlockPassable(forwardUpper) ? forwardUpper : forwardLower;
        } else {
            mc.options.sneakKey.setPressed(false);
            if (blockToBreak == null && pendingOrePos == null) {
                moveForward();

                // ИНИЦИАЛИЗАЦИЯ ПОЗИЦИИ
                if (lastCheckPos == null) lastCheckPos = playerPos;

                double dist = Math.sqrt(playerPos.getSquaredDistance(lastCheckPos));
                if (dist >= checkDistance.getValue()) {
                    mc.options.forwardKey.setPressed(false);
                    checkBaseWithOre(dir);
                    lastCheckPos = playerPos; // Обнуляем точку отсчета
                }
            }
        }
    }
    private boolean checkForDanger(BlockPos pos) {
        if (mc.world == null) return false;
        BlockState floor = mc.world.getBlockState(pos.down());
        boolean isVoid = floor.isAir();
        boolean isLiquid = mc.world.getBlockState(pos).isLiquid() || floor.isLiquid();
        return isVoid || isLiquid;
    }

    private void processBlockMining(BlockPos pos) {
        if (mc.world == null || mc.player == null || mc.interactionManager == null) return;

        if (checkForLiquids(pos)) {
            ChatMessage.brandmessage("§c[Внимание] §fОбнаружена лава/вода. Остановка.");
            this.switchState();
            return;
        }

        selectBestTool(mc.world.getBlockState(pos));
        rotateHeadToBlock(pos);

        mc.interactionManager.updateBlockBreakingProgress(pos, Direction.UP);
        mc.player.swingHand(Hand.MAIN_HAND);
    }

    private int findFillerBlock() {
        for (int i = 0; i < 9; i++) {
            ItemStack stack = mc.player.getInventory().getStack(i);
            if (stack.isEmpty()) continue;
            String name = stack.getItem().toString();
            if (name.contains("stone") || name.contains("dirt") || name.contains("cobble") ||
                    name.contains("netherrack") || name.contains("deepslate") || name.contains("andesite")) {
                return i;
            }
        }
        return -1;
    }

    private void placeBridge(BlockPos targetPos) {
        int fillerSlot = findFillerBlock();
        if (fillerSlot == -1) {
            ChatMessage.brandmessage("§c[Ошибка] §fНет блоков для застройки!");
            this.switchState();
            return;
        }

        mc.options.forwardKey.setPressed(false);
        mc.options.sneakKey.setPressed(true);
        int oldSlot = mc.player.getInventory().selectedSlot;
        mc.player.getInventory().selectedSlot = fillerSlot;

        rotateHeadToBlock(targetPos);

        BlockHitResult hit = new BlockHitResult(targetPos.toCenterPos(), Direction.UP, targetPos, false);
        mc.interactionManager.interactBlock(mc.player, Hand.MAIN_HAND, hit);
        mc.player.swingHand(Hand.MAIN_HAND);

        mc.player.getInventory().selectedSlot = oldSlot;
    }
    @EventHandler
    public void onRender3D(WorldRenderEvent event) {
        if (!state || mc.world == null || mc.player == null) return;

        if (blockToBreak != null) {
            fun.vortex.utils.display.geometry.Render3D.drawBox(new Box(blockToBreak), ColorAssist.getColor(255, 0, 0, 100), 1);
        }

        if (!diggingDown) {
            Direction dir = Direction.byName(direction.getSelected().toLowerCase());
            if (dir != null) {
                BlockPos p = mc.player.getBlockPos();
                BlockPos f1 = p.offset(dir);
                BlockPos f2 = p.up().offset(dir);

                if (!mc.world.isAir(f1) && !f1.equals(blockToBreak)) fun.vortex.utils.display.geometry.Render3D.drawBox(new Box(f1), ColorAssist.getColor(0, 255, 0, 50), 1);
                if (!mc.world.isAir(f2) && !f2.equals(blockToBreak)) fun.vortex.utils.display.geometry.Render3D.drawBox(new Box(f2), ColorAssist.getColor(0, 255, 0, 50), 1);
            }
        }
    }

    private void checkBaseWithOre(Direction dir) {
        Direction sideDir = dir.rotateYClockwise();
        BlockPos wallPos = mc.player.getBlockPos().offset(sideDir).up();

        if (!mc.world.isAir(wallPos)) {

            blockToBreak = wallPos;
            pendingOrePos = wallPos;
            shouldPlaceOreAfterBreak = wallPos;
        }
    }

    private void selectBestTool(BlockState blockState) {
        if (mc.player == null) return;
        int bestSlot = -1;
        float bestSpeed = 0;
        for (int i = 0; i < 9; i++) {
            ItemStack stack = mc.player.getInventory().getStack(i);
            if (stack.isEmpty()) continue;

            ToolComponent tool = stack.get(DataComponentTypes.TOOL);
            float speed = (tool != null) ? tool.getSpeed(blockState) : 1.0f;

            if (speed > bestSpeed) {
                bestSpeed = speed;
                bestSlot = i;
            }
        }
        if (bestSlot != -1) {
            mc.player.getInventory().selectedSlot = bestSlot;
        }
    }

    private void rotateHeadToBlock(BlockPos pos) {
        if (mc.player == null) return;
        Vec3d target = pos.toCenterPos();
        Vec3d eyePos = mc.player.getEyePos();
        double dx = target.x - eyePos.x;
        double dy = target.y - eyePos.y;
        double dz = target.z - eyePos.z;
        float yaw = (float) Math.toDegrees(Math.atan2(dz, dx)) - 90.0F;
        float pitch = (float) -Math.toDegrees(Math.atan2(dy, Math.sqrt(dx * dx + dz * dz)));
        double gcd = fun.vortex.utils.math.calc.Calculate.computeGcd();
        if (gcd > 0) {
            float lastYaw = TurnsConnection.INSTANCE.getRotation().getYaw();
            float lastPitch = TurnsConnection.INSTANCE.getRotation().getPitch();

            float deltaYaw = yaw - lastYaw;
            float deltaPitch = pitch - lastPitch;

            yaw = lastYaw + (float) (deltaYaw - (deltaYaw % gcd));
            pitch = lastPitch + (float) (deltaPitch - (deltaPitch % gcd));
        }
        pitch = net.minecraft.util.math.MathHelper.clamp(pitch, -90.0f, 90.0f);

        TurnsConnection.INSTANCE.getRotation().setYaw(yaw);
        TurnsConnection.INSTANCE.getRotation().setPitch(pitch);
        mc.player.setYaw(yaw);
        mc.player.setPitch(pitch);
    }

    private void moveForward() {
        if (mc.options == null) return;
        mc.options.forwardKey.setPressed(true);
    }

    private boolean isBlockPassable(BlockPos pos) {
        if (mc.world == null) return false;
        return !mc.world.getBlockState(pos).isOpaque();
    }

    private boolean checkForLiquids(BlockPos pos) {
        if (mc.world == null) return false;
        return mc.world.getBlockState(pos).isLiquid();
    }

    private boolean tryPlaceOre(BlockPos pos) {
        if (mc.player == null || mc.interactionManager == null || mc.world == null) return false;
        int oreSlot = findOreSlot();
        if (oreSlot == -1) return false;

        int oldSlot = mc.player.getInventory().selectedSlot;
        mc.player.getInventory().selectedSlot = oreSlot;

        rotateHeadToBlock(pos);

        BlockHitResult hitResult = new BlockHitResult(pos.toCenterPos(), Direction.UP, pos, false);
        mc.interactionManager.interactBlock(mc.player, Hand.MAIN_HAND, hitResult);
        mc.player.swingHand(Hand.MAIN_HAND);

        boolean placed = !mc.world.getBlockState(pos).isAir();
        mc.player.getInventory().selectedSlot = oldSlot;

        return placed;
    }

    private void mineBackOre(BlockPos pos) {
        if (mc.player == null || mc.player.networkHandler == null) return;
        int pickaxeSlot = findSilkTouchPickaxe();
        if (pickaxeSlot == -1) return;

        int oldSlot = mc.player.getInventory().selectedSlot;
        mc.player.getInventory().selectedSlot = pickaxeSlot;

        mc.player.networkHandler.sendPacket(new PlayerActionC2SPacket(PlayerActionC2SPacket.Action.START_DESTROY_BLOCK, pos, Direction.UP));
        mc.player.networkHandler.sendPacket(new PlayerActionC2SPacket(PlayerActionC2SPacket.Action.STOP_DESTROY_BLOCK, pos, Direction.UP));
        mc.player.swingHand(Hand.MAIN_HAND);

        mc.player.getInventory().selectedSlot = oldSlot;
    }

    private boolean hasRequiredItems() {
        if (mc.player == null) return false;
        return findSilkTouchPickaxe() != -1 && findOreSlot() != -1;
    }

    private int findSilkTouchPickaxe() {
        if (mc.player == null) return -1;
        for (int i = 0; i < 9; i++) {
            ItemStack stack = mc.player.getInventory().getStack(i);
            if (stack.getItem() instanceof PickaxeItem) {
                ItemEnchantmentsComponent enchants = stack.get(DataComponentTypes.ENCHANTMENTS);
                if (enchants != null) {
                    for (RegistryEntry<Enchantment> enchant : enchants.getEnchantments()) {
                        if (enchant.matchesKey(Enchantments.SILK_TOUCH)) return i;
                    }
                }
            }
        }
        return -1;
    }

    private int findOreSlot() {
        if (mc.player == null) return -1;
        for (int i = 0; i < 9; i++) {
            ItemStack s = mc.player.getInventory().getStack(i);
            if (oreType.isSelected("Diamond Ore") && s.isOf(Items.DIAMOND_ORE)) return i;
            if (oreType.isSelected("Emerald Ore") && s.isOf(Items.EMERALD_ORE)) return i;
        }
        return -1;
    }
}
/up

Измененно: а не нихуя не ап, каллище ебаное, лучшек бы сделал чтоб ан элитрах летел а не копался, и нахуя кирка на шёлковое касание вобще
 
Последнее редактирование:
эта настройка отвечает за сторону света в которую копать, типо: я ставлю копай на север он копает на север, такая логика, ну я не нашел как сделать лучше :)
 
/up

Измененно: а не нихуя не ап, каллище ебаное, лучшек бы сделал чтоб ан элитрах летел а не копался, и нахуя кирка на шёлковое касание вобще
Функция копается, ставит приват, а киркой на шелк приват ломает
 
/up

Измененно: а не нихуя не ап, каллище ебаное, лучшек бы сделал чтоб ан элитрах летел а не копался, и нахуя кирка на шёлковое касание вобще
Что значит на элитрах летал базы искал? как ты себе это представляешь? Кирка на шелк - что бы блок привата ломать
 
Средний модуль ищет базы на фантайме, есть немного ии кода, логика +- хорошая есть защита от лавы/воды пропасти атаки и другие фишки, не захотел ебаться с баритоном просто написал такой модуль. Кто хочет - пастите.

Может кому пригодиться :3

код:
Expand Collapse Copy
package fun.vortex.features.impl.player;

import fun.vortex.events.player.TickEvent;
import fun.vortex.features.module.ModuleCategory;
import fun.vortex.features.module.setting.implement.SelectSetting;
import fun.vortex.features.module.setting.implement.SliderSettings;
import fun.vortex.utils.client.chat.ChatMessage;
import fun.vortex.utils.client.managers.event.EventHandler;
import fun.vortex.utils.features.aura.warp.TurnsConnection;
import net.minecraft.block.BlockState;
import fun.vortex.events.render.WorldRenderEvent;
import fun.vortex.utils.display.color.ColorAssist;
import net.minecraft.util.math.Box;
import net.minecraft.component.DataComponentTypes;
import net.minecraft.component.type.ItemEnchantmentsComponent;
import net.minecraft.component.type.ToolComponent;
import net.minecraft.enchantment.Enchantment;
import net.minecraft.enchantment.Enchantments;
import net.minecraft.item.ItemStack;
import net.minecraft.item.Items;
import net.minecraft.item.PickaxeItem;
import net.minecraft.network.packet.c2s.play.PlayerActionC2SPacket;
import net.minecraft.network.packet.c2s.play.PlayerInteractBlockC2SPacket;
import net.minecraft.registry.entry.RegistryEntry;
import net.minecraft.util.Hand;
import net.minecraft.util.hit.BlockHitResult;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.Direction;
import net.minecraft.util.math.Vec3d;

import fun.vortex.features.module.Module;
public class FTBaseFinder extends Module {

    private final SelectSetting direction = new SelectSetting("Направление", "Куда копать")
            .value("North", "East", "South", "West").selected("North");

    private final SliderSettings targetY = new SliderSettings("Высота", "Целевая высота")
            .range(-60, 60).setValue(15);

    private final SelectSetting oreType = new SelectSetting("Блок проверки", "Что ставить")
            .value("Diamond Ore", "Emerald Ore").selected("Diamond Ore");

    private final SliderSettings checkDistance = new SliderSettings("Дистанция проверки", "Раз в сколько блоков ставить руду")
            .range(5, 100).setValue(25);

    private boolean diggingDown = true;
    private int distanceCounter = 0;
    private BlockPos blockToBreak = null;

    public FTBaseFinder() {
        super("FT-BaseFinder", "FTBaseFinder", ModuleCategory.PLAYER);
        setup(direction, targetY, oreType, checkDistance);
    }

    @Override
    public void activate() {
        if (mc.player == null) {
            this.switchState();
            return;
        }
        if (!hasRequiredItems()) {
            ChatMessage.brandmessage("§c[Ошибка] §fНет кирки на Шелковое касание или руды в хотбаре!");
            this.switchState();
            return;
        }

        diggingDown = true;
        distanceCounter = 0;
        blockToBreak = null;
        ChatMessage.brandmessage("§a[Старт] §fСпускаюсь на высоту " + targetY.getInt());
        super.activate();
    }

    @Override
    public void deactivate() {
        if (mc.options != null) {
            mc.options.forwardKey.setPressed(false);
        }
        super.deactivate();
    }

    private BlockPos pendingOrePos = null;
    private BlockPos shouldPlaceOreAfterBreak = null;
    private boolean isBypassing = false;
    private int bypassTicks = 0;
    private BlockPos bypassTarget = null;

    @EventHandler
    public void onTick(TickEvent ignored) {
        if (mc.player == null || mc.world == null) return;

        if (mc.player.hurtTime > 0) {

            boolean isEntityDamage = mc.world.getEntitiesByClass(net.minecraft.entity.mob.HostileEntity.class,
                    mc.player.getBoundingBox().expand(5), e -> true).size() > 0;

            if (isEntityDamage && System.currentTimeMillis() - lastDamageTime > 5000) {
                ChatMessage.brandmessage("§c§l[ВНИМАНИЕ] §fВас атакует моб! Остановка.");
                this.switchState();
                return;
            }
        }

        if (pendingOrePos != null && mc.world.isAir(pendingOrePos)) {
            if (!tryPlaceOre(pendingOrePos)) {
                ChatMessage.brandmessage("§6§l[БАЗА!] §fПриват на: §a" + pendingOrePos.toShortString());
                this.switchState();
                return;
            } else {
                mineBackOre(pendingOrePos);
                pendingOrePos = null;
            }
        }

        if (blockToBreak != null) {
            if (mc.world.isAir(blockToBreak)) {
                blockToBreak = null;
            } else {
                processBlockMining(blockToBreak);
                return;
            }
        }

        if (diggingDown) {
            handleDescending();
        } else {
            handleTunneling();
        }
    }

    private BlockPos lastCheckPos = null;
    private long lastDamageTime = 0;

    private void handleDescending() {
        BlockPos playerPos = BlockPos.ofFloored(mc.player.getPos());
        BlockPos underPlayer = playerPos.down();

        if (isLiquidBelow(underPlayer)) {
            ChatMessage.brandmessage("§c[!] §fПод ногами обнаружена жидкость. Запуск сканирования 10x10...");

            BlockPos safePoint = findBestSafePoint(playerPos);

            if (safePoint != null) {
                double distance = Math.sqrt(playerPos.getSquaredDistance(safePoint));
                ChatMessage.brandmessage(String.format("§a[Навигатор] §fНайдена безопасная зона в %.1f м. Обхожу...", distance));
                moveTowards(safePoint);
            } else {
                ChatMessage.brandmessage("§4[Крит] §fВ радиусе 10 блоков нет безопасных мест. Смена вектора...");
                direction.selected(Direction.Type.HORIZONTAL.random(mc.world.random).asString());
            }
            return;
        }

        if (mc.player.getY() <= targetY.getValue()) {
            diggingDown = false;
            ChatMessage.brandmessage("§6[Инфо] §fЦелевая высота " + targetY.getInt() + " достигнута. Начинаю копку туннеля.");
            return;
        }

        if (!mc.world.isAir(underPlayer)) {
            blockToBreak = underPlayer;
        }
    }

    private BlockPos findBestSafePoint(BlockPos startPos) {
        BlockPos bestPos = null;
        double minDistance = Double.MAX_VALUE;

        for (int x = -10; x <= 10; x++) {
            for (int z = -10; z <= 10; z++) {
                BlockPos checkPos = startPos.add(x, 0, z);

                if (isValidSafeSpot(checkPos)) {
                    double dist = startPos.getSquaredDistance(checkPos);
                    if (dist < minDistance) {
                        minDistance = dist;
                        bestPos = checkPos;
                    }
                }
            }
        }
        return bestPos;
    }

    private boolean isValidSafeSpot(BlockPos pos) {
        boolean isSpaceClear = mc.world.getBlockState(pos).isAir() &&
                mc.world.getBlockState(pos.up()).isAir();

        if (!isSpaceClear) return false;

        for (int i = 0; i <= 5; i++) {
            if (mc.world.getBlockState(pos.down(i)).isLiquid()) {
                return false;
            }
        }

        return !mc.world.getBlockState(pos.down()).isAir();
    }

    private boolean isLiquidBelow(BlockPos startPos) {
        for (int i = 0; i < 5; i++) {
            BlockState state = mc.world.getBlockState(startPos.down(i));
            if (state.isLiquid()) return true;
        }
        return false;
    }

    private void tryToBypassDanger(BlockPos currentPos) {

        for (Direction dir : Direction.Type.HORIZONTAL) {
            BlockPos sidePos = currentPos.offset(dir);
            if (!isLiquidBelow(sidePos) && mc.world.isAir(sidePos)) {
                moveTowards(sidePos);
                return;
            }
        }
        ChatMessage.brandmessage("§c[Внимание] §f Безопасный путь не найден. Стоп.");
        this.switchState();
    }

    private void moveTowards(BlockPos pos) {
        if (mc.player == null) return;

        rotateHeadToBlock(pos);

        double dx = pos.getX() + 0.5 - mc.player.getX();
        double dz = pos.getZ() + 0.5 - mc.player.getZ();
        double distance = Math.sqrt(dx * dx + dz * dz);

        if (distance > 0.3) {
            mc.options.forwardKey.setPressed(true);
            if (mc.player.horizontalCollision) {
                mc.options.jumpKey.setPressed(true);
            } else {
                mc.options.jumpKey.setPressed(false);
            }
        } else {
            mc.options.forwardKey.setPressed(false);
            mc.options.jumpKey.setPressed(false);
        }
    }

    private void handleTunneling() {
        Direction dir = Direction.byName(direction.getSelected().toLowerCase());
        if (dir == null) dir = Direction.NORTH;

        BlockPos playerPos = BlockPos.ofFloored(mc.player.getPos());
        BlockPos forwardLower = playerPos.offset(dir);
        BlockPos forwardUpper = forwardLower.up();
        BlockPos gapPos = forwardLower.down();

        // Проверка жидкостей
        if (mc.world.getBlockState(forwardLower).isLiquid() || mc.world.getBlockState(forwardUpper).isLiquid()) {
            direction.selected(dir.rotateYClockwise().asString());
            return;
        }

        if (mc.world.getBlockState(gapPos).isAir() || mc.world.getBlockState(gapPos).isLiquid()) {
            mc.options.forwardKey.setPressed(false);
            placeBridge(gapPos);
            return;
        }

        if (!isBlockPassable(forwardUpper) || !isBlockPassable(forwardLower)) {
            mc.options.forwardKey.setPressed(false);
            blockToBreak = !isBlockPassable(forwardUpper) ? forwardUpper : forwardLower;
        } else {
            mc.options.sneakKey.setPressed(false);
            if (blockToBreak == null && pendingOrePos == null) {
                moveForward();

                // ИНИЦИАЛИЗАЦИЯ ПОЗИЦИИ
                if (lastCheckPos == null) lastCheckPos = playerPos;

                double dist = Math.sqrt(playerPos.getSquaredDistance(lastCheckPos));
                if (dist >= checkDistance.getValue()) {
                    mc.options.forwardKey.setPressed(false);
                    checkBaseWithOre(dir);
                    lastCheckPos = playerPos; // Обнуляем точку отсчета
                }
            }
        }
    }
    private boolean checkForDanger(BlockPos pos) {
        if (mc.world == null) return false;
        BlockState floor = mc.world.getBlockState(pos.down());
        boolean isVoid = floor.isAir();
        boolean isLiquid = mc.world.getBlockState(pos).isLiquid() || floor.isLiquid();
        return isVoid || isLiquid;
    }

    private void processBlockMining(BlockPos pos) {
        if (mc.world == null || mc.player == null || mc.interactionManager == null) return;

        if (checkForLiquids(pos)) {
            ChatMessage.brandmessage("§c[Внимание] §fОбнаружена лава/вода. Остановка.");
            this.switchState();
            return;
        }

        selectBestTool(mc.world.getBlockState(pos));
        rotateHeadToBlock(pos);

        mc.interactionManager.updateBlockBreakingProgress(pos, Direction.UP);
        mc.player.swingHand(Hand.MAIN_HAND);
    }

    private int findFillerBlock() {
        for (int i = 0; i < 9; i++) {
            ItemStack stack = mc.player.getInventory().getStack(i);
            if (stack.isEmpty()) continue;
            String name = stack.getItem().toString();
            if (name.contains("stone") || name.contains("dirt") || name.contains("cobble") ||
                    name.contains("netherrack") || name.contains("deepslate") || name.contains("andesite")) {
                return i;
            }
        }
        return -1;
    }

    private void placeBridge(BlockPos targetPos) {
        int fillerSlot = findFillerBlock();
        if (fillerSlot == -1) {
            ChatMessage.brandmessage("§c[Ошибка] §fНет блоков для застройки!");
            this.switchState();
            return;
        }

        mc.options.forwardKey.setPressed(false);
        mc.options.sneakKey.setPressed(true);
        int oldSlot = mc.player.getInventory().selectedSlot;
        mc.player.getInventory().selectedSlot = fillerSlot;

        rotateHeadToBlock(targetPos);

        BlockHitResult hit = new BlockHitResult(targetPos.toCenterPos(), Direction.UP, targetPos, false);
        mc.interactionManager.interactBlock(mc.player, Hand.MAIN_HAND, hit);
        mc.player.swingHand(Hand.MAIN_HAND);

        mc.player.getInventory().selectedSlot = oldSlot;
    }
    @EventHandler
    public void onRender3D(WorldRenderEvent event) {
        if (!state || mc.world == null || mc.player == null) return;

        if (blockToBreak != null) {
            fun.vortex.utils.display.geometry.Render3D.drawBox(new Box(blockToBreak), ColorAssist.getColor(255, 0, 0, 100), 1);
        }

        if (!diggingDown) {
            Direction dir = Direction.byName(direction.getSelected().toLowerCase());
            if (dir != null) {
                BlockPos p = mc.player.getBlockPos();
                BlockPos f1 = p.offset(dir);
                BlockPos f2 = p.up().offset(dir);

                if (!mc.world.isAir(f1) && !f1.equals(blockToBreak)) fun.vortex.utils.display.geometry.Render3D.drawBox(new Box(f1), ColorAssist.getColor(0, 255, 0, 50), 1);
                if (!mc.world.isAir(f2) && !f2.equals(blockToBreak)) fun.vortex.utils.display.geometry.Render3D.drawBox(new Box(f2), ColorAssist.getColor(0, 255, 0, 50), 1);
            }
        }
    }

    private void checkBaseWithOre(Direction dir) {
        Direction sideDir = dir.rotateYClockwise();
        BlockPos wallPos = mc.player.getBlockPos().offset(sideDir).up();

        if (!mc.world.isAir(wallPos)) {

            blockToBreak = wallPos;
            pendingOrePos = wallPos;
            shouldPlaceOreAfterBreak = wallPos;
        }
    }

    private void selectBestTool(BlockState blockState) {
        if (mc.player == null) return;
        int bestSlot = -1;
        float bestSpeed = 0;
        for (int i = 0; i < 9; i++) {
            ItemStack stack = mc.player.getInventory().getStack(i);
            if (stack.isEmpty()) continue;

            ToolComponent tool = stack.get(DataComponentTypes.TOOL);
            float speed = (tool != null) ? tool.getSpeed(blockState) : 1.0f;

            if (speed > bestSpeed) {
                bestSpeed = speed;
                bestSlot = i;
            }
        }
        if (bestSlot != -1) {
            mc.player.getInventory().selectedSlot = bestSlot;
        }
    }

    private void rotateHeadToBlock(BlockPos pos) {
        if (mc.player == null) return;
        Vec3d target = pos.toCenterPos();
        Vec3d eyePos = mc.player.getEyePos();
        double dx = target.x - eyePos.x;
        double dy = target.y - eyePos.y;
        double dz = target.z - eyePos.z;
        float yaw = (float) Math.toDegrees(Math.atan2(dz, dx)) - 90.0F;
        float pitch = (float) -Math.toDegrees(Math.atan2(dy, Math.sqrt(dx * dx + dz * dz)));
        double gcd = fun.vortex.utils.math.calc.Calculate.computeGcd();
        if (gcd > 0) {
            float lastYaw = TurnsConnection.INSTANCE.getRotation().getYaw();
            float lastPitch = TurnsConnection.INSTANCE.getRotation().getPitch();

            float deltaYaw = yaw - lastYaw;
            float deltaPitch = pitch - lastPitch;

            yaw = lastYaw + (float) (deltaYaw - (deltaYaw % gcd));
            pitch = lastPitch + (float) (deltaPitch - (deltaPitch % gcd));
        }
        pitch = net.minecraft.util.math.MathHelper.clamp(pitch, -90.0f, 90.0f);

        TurnsConnection.INSTANCE.getRotation().setYaw(yaw);
        TurnsConnection.INSTANCE.getRotation().setPitch(pitch);
        mc.player.setYaw(yaw);
        mc.player.setPitch(pitch);
    }

    private void moveForward() {
        if (mc.options == null) return;
        mc.options.forwardKey.setPressed(true);
    }

    private boolean isBlockPassable(BlockPos pos) {
        if (mc.world == null) return false;
        return !mc.world.getBlockState(pos).isOpaque();
    }

    private boolean checkForLiquids(BlockPos pos) {
        if (mc.world == null) return false;
        return mc.world.getBlockState(pos).isLiquid();
    }

    private boolean tryPlaceOre(BlockPos pos) {
        if (mc.player == null || mc.interactionManager == null || mc.world == null) return false;
        int oreSlot = findOreSlot();
        if (oreSlot == -1) return false;

        int oldSlot = mc.player.getInventory().selectedSlot;
        mc.player.getInventory().selectedSlot = oreSlot;

        rotateHeadToBlock(pos);

        BlockHitResult hitResult = new BlockHitResult(pos.toCenterPos(), Direction.UP, pos, false);
        mc.interactionManager.interactBlock(mc.player, Hand.MAIN_HAND, hitResult);
        mc.player.swingHand(Hand.MAIN_HAND);

        boolean placed = !mc.world.getBlockState(pos).isAir();
        mc.player.getInventory().selectedSlot = oldSlot;

        return placed;
    }

    private void mineBackOre(BlockPos pos) {
        if (mc.player == null || mc.player.networkHandler == null) return;
        int pickaxeSlot = findSilkTouchPickaxe();
        if (pickaxeSlot == -1) return;

        int oldSlot = mc.player.getInventory().selectedSlot;
        mc.player.getInventory().selectedSlot = pickaxeSlot;

        mc.player.networkHandler.sendPacket(new PlayerActionC2SPacket(PlayerActionC2SPacket.Action.START_DESTROY_BLOCK, pos, Direction.UP));
        mc.player.networkHandler.sendPacket(new PlayerActionC2SPacket(PlayerActionC2SPacket.Action.STOP_DESTROY_BLOCK, pos, Direction.UP));
        mc.player.swingHand(Hand.MAIN_HAND);

        mc.player.getInventory().selectedSlot = oldSlot;
    }

    private boolean hasRequiredItems() {
        if (mc.player == null) return false;
        return findSilkTouchPickaxe() != -1 && findOreSlot() != -1;
    }

    private int findSilkTouchPickaxe() {
        if (mc.player == null) return -1;
        for (int i = 0; i < 9; i++) {
            ItemStack stack = mc.player.getInventory().getStack(i);
            if (stack.getItem() instanceof PickaxeItem) {
                ItemEnchantmentsComponent enchants = stack.get(DataComponentTypes.ENCHANTMENTS);
                if (enchants != null) {
                    for (RegistryEntry<Enchantment> enchant : enchants.getEnchantments()) {
                        if (enchant.matchesKey(Enchantments.SILK_TOUCH)) return i;
                    }
                }
            }
        }
        return -1;
    }

    private int findOreSlot() {
        if (mc.player == null) return -1;
        for (int i = 0; i < 9; i++) {
            ItemStack s = mc.player.getInventory().getStack(i);
            if (oreType.isSelected("Diamond Ore") && s.isOf(Items.DIAMOND_ORE)) return i;
            if (oreType.isSelected("Emerald Ore") && s.isOf(Items.EMERALD_ORE)) return i;
        }
        return -1;
    }
}
/dell no ss
 
/up

Измененно: а не нихуя не ап, каллище ебаное, лучшек бы сделал чтоб ан элитрах летел а не копался, и нахуя кирка на шёлковое касание вобще
фт за 50 блоков не рендерит игроков, из-за чего на элитрах/флае бесполезно
 
Назад
Сверху Снизу