Гайд Expensive-like уведы 3.1 ready

драггинги не очень сложно и самому сделать, а по поводу уведомлений по центру норм идея
так это можно сделать написав 15-20 строк. надеюсь ты не будешь выпускать целый пост по поводу этого
 
Обратите внимание, пользователь заблокирован на форуме. Не рекомендуется проводить сделки.
1743075106209.png


Как фиксить
 
Обратите внимание, пользователь заблокирован на форуме. Не рекомендуется проводить сделки.
чо пупсек сливаишь сваи натификации на югеэйм
 
ку гайс, моя первая тема на форуме, я нюгенчик и самый крутой на сайте чат лбгт
надеюсь больше ничего вы от меня тут не увидите, но сегодня исключение.

приступим к самому гайду.
создаем в папке с мейном клиента класс NotificationManager
код:

Java:
Expand Collapse Copy
package im.expensive;

import im.expensive.ui.display.impl.NotificationsRenderer;

public class NotificationManager {

    private static NotificationManager instance;
    private final NotificationsRenderer renderer;

    private NotificationManager() {
        this.renderer = new NotificationsRenderer();
    }

    public static NotificationManager getInstance() {
        if (instance == null) {
            instance = new NotificationManager();
        }
        return instance;
    }

    public void addNotification(String message, boolean enabled) {
        renderer.addNotification(message, enabled);
    }

    public NotificationsRenderer getRenderer() {
        return renderer;
    }
}

дальше в самом мейне клиента:
в функции clientLoad()
перед регистером eventbus ставим:
notificationManager = NotificationManager.getInstance();

не забываем про обработчик
private NotificationManager notificationManager;

дальше идем в папку с рендерами кейбиндов и т.п
создаем класс NotificationsRenderer
код

Java:
Expand Collapse Copy
package im.expensive.ui.display.impl;

import com.mojang.blaze3d.matrix.MatrixStack;
import com.mojang.blaze3d.systems.RenderSystem;
import im.expensive.Expensive;
import im.expensive.events.EventDisplay;
import im.expensive.ui.display.ElementRenderer;
import im.expensive.ui.styles.Style;
import im.expensive.utils.animations.Animation;
import im.expensive.utils.animations.Direction;
import im.expensive.utils.animations.impl.EaseBackIn;
import im.expensive.utils.math.StopWatch;
import im.expensive.utils.render.ColorUtils;
import im.expensive.utils.render.DisplayUtils;
import im.expensive.utils.render.Scissor;
import im.expensive.utils.render.font.Fonts;
import im.expensive.utils.text.GradientUtil;
import lombok.AccessLevel;
import lombok.experimental.FieldDefaults;
import net.minecraft.client.gui.AbstractGui;
import net.minecraft.util.ResourceLocation;
import net.minecraft.util.text.ITextComponent;

import java.util.concurrent.CopyOnWriteArrayList;

@FieldDefaults(level = AccessLevel.PRIVATE)
public class NotificationsRenderer implements ElementRenderer {

    final CopyOnWriteArrayList<Notification> notifications = new CopyOnWriteArrayList<>();
    final ResourceLocation icon = new ResourceLocation("expensive/images/hud/notification.png");

    static final float FONT_SIZE = 7f;
    static final float PADDING = 4f;
    static final float ROUNDING = 5f;
    static final float ICON_SIZE = 10f;
    static final float HEIGHT = FONT_SIZE + PADDING * 2;
    static final int MAX_NOTIFICATIONS = 5;
    static final int DISPLAY_TIME_MS = 3000;

    @Override
    public void render(EventDisplay eventDisplay) {
        if (eventDisplay.getType() != EventDisplay.Type.POST) return;

        MatrixStack matrixStack = eventDisplay.getMatrixStack();
        Style style = Expensive.getInstance().getStyleManager().getCurrentStyle();
        if (style == null) return;

        int screenWidth = mc.getMainWindow().getScaledWidth();
        int screenHeight = mc.getMainWindow().getScaledHeight();

        float posY = screenHeight - HEIGHT - PADDING;

        int notificationCount = Math.min(notifications.size(), MAX_NOTIFICATIONS);
        for (int i = 0; i < notificationCount; i++) {
            Notification notification = notifications.get(i);

            String status = notification.isEnabled ? "включен" : "выключен";
            ITextComponent message = GradientUtil.gradient("Модуль " + notification.moduleName + " был " + status);
            float textWidth = Fonts.sfui.getWidth(message, FONT_SIZE);
            float width = textWidth + ICON_SIZE + PADDING * 5;
            float posX = screenWidth - width - PADDING;

            boolean expired = notification.stopWatch.isReached(DISPLAY_TIME_MS);
            notification.animation.setDirection(expired ? Direction.BACKWARDS : Direction.FORWARDS);
            float animationValue = (float) notification.animation.getOutput();

            if (animationValue <= 0f && expired) {
                notifications.remove(notification);
                continue;
            }

            float halfAnimationValueRest = (1 - animationValue) / 2f;
            float animatedX = posX + (width * halfAnimationValueRest);
            float animatedY = posY + (HEIGHT * halfAnimationValueRest);
            float animatedWidth = width * animationValue;
            float animatedHeight = HEIGHT * animationValue;

            DisplayUtils.drawShadow(posX, posY, width, HEIGHT, 8, style.getFirstColor().getRGB(), style.getSecondColor().getRGB());
            drawStyledRect(posX, posY, width, HEIGHT, ROUNDING, 255);

            Scissor.push();
            Scissor.setFromComponentCoordinates(animatedX, animatedY, animatedWidth - PADDING * 2, animatedHeight);

            mc.getTextureManager().bindTexture(icon);
            RenderSystem.enableBlend();
            RenderSystem.color4f(1f, 1f, 1f, animationValue);
            AbstractGui.blit(matrixStack, (int) (posX + PADDING), (int) (posY + (HEIGHT - ICON_SIZE) / 2),
                    0, 0, (int) ICON_SIZE, (int) ICON_SIZE, (int) ICON_SIZE, (int) ICON_SIZE);

            Fonts.sfui.drawText(matrixStack, message.getString(), posX + PADDING + ICON_SIZE + PADDING, posY + PADDING, -1, FONT_SIZE);

            Scissor.unset();
            Scissor.pop();

            posY -= HEIGHT + PADDING;
        }
    }

    private void drawStyledRect(float x, float y, float rectWidth, float rectHeight, float radius, int alpha) {
        DisplayUtils.drawRoundedRect(x - 0.5f, y - 0.5f, rectWidth + 1, rectHeight + 1, radius + 0.5f,
                ColorUtils.setAlpha(ColorUtils.getColor(0), alpha));
        DisplayUtils.drawRoundedRect(x, y, rectWidth, rectHeight, radius, ColorUtils.rgba(21, 21, 21, alpha)); // Фон
    }

    public void addNotification(String moduleName, boolean isEnabled) {
        notifications.add(0, new Notification(moduleName, isEnabled));
    }

    @FieldDefaults(level = AccessLevel.PRIVATE)
    private static class Notification {
        final String moduleName;
        final boolean isEnabled;
        final StopWatch stopWatch = new StopWatch();
        final Animation animation = new EaseBackIn(400, 1, 1);

        Notification(String moduleName, boolean isEnabled) {
            this.moduleName = moduleName;
            this.isEnabled = isEnabled;
            this.stopWatch.reset();
            this.animation.setDirection(Direction.FORWARDS);
        }
    }
}

дальше идем в im.expensive.functions.api.Function
и меняем setState на это
Java:
Expand Collapse Copy
    public final void setState(boolean newState, boolean config) {
        if (state == newState) {
            return;
        }

        state = newState;

        try {
            if (state) {
                onEnable();
                Expensive.getInstance().getNotificationManager().addNotification(name, true);
            } else {
                onDisable();
                Expensive.getInstance().getNotificationManager().addNotification(name, false);
            }
            if (!config) {
                FunctionRegistry functionRegistry = Expensive.getInstance().getFunctionRegistry();
                ClientSounds clientSounds = functionRegistry.getClientSounds();

                if (clientSounds != null && clientSounds.isState()) {
                    String fileName = clientSounds.getFileName(state);
                    float volume = clientSounds.volume.get();
                    ClientUtil.playSound(fileName, volume, false);
                }
            }
        } catch (Exception e) {
            handleException(state ? "onEnable" : "onDisable", e);
        }
    }

дальше идем в модуль худа и добавляем сеттинг уведомлений
и добавляем рендер уведов, если включены
кому лень писать вот этот микро код
Expensive.getInstance().getNotificationManager().getRenderer().render(e);


дальше ищем иконку нотифа (на размер все равно, он автоматический) и радуемся (если я и моя деменция что-то не забыла)
если столкнулись с ошибкой кроме моего присутсвия на форуме, пишите я постараюсь помочь.

SS: прикрепил
кинь иконку братан
 
Обратите внимание, пользователь заблокирован на форуме. Не рекомендуется проводить сделки.
Имба, но где взять иконки на notification?
 
Обратите внимание, пользователь заблокирован на форуме. Не рекомендуется проводить сделки.
Обратите внимание, пользователь заблокирован на форуме. Не рекомендуется проводить сделки.
мой час насрал
 
Назад
Сверху Снизу