+1
-1
@@ -11,7 +11,7 @@ yarn_mappings=1.21.4+build.7
|
|||||||
loader_version=0.16.10
|
loader_version=0.16.10
|
||||||
fabric_version=0.114.0+1.21.4
|
fabric_version=0.114.0+1.21.4
|
||||||
|
|
||||||
mod_version = 0.0.6-beta1
|
mod_version = 0.0.7-alpha1
|
||||||
maven_group = org.saturnclient
|
maven_group = org.saturnclient
|
||||||
archives_base_name = saturnclient
|
archives_base_name = saturnclient
|
||||||
|
|
||||||
|
|||||||
@@ -22,7 +22,11 @@ public class ModManager {
|
|||||||
new DayCounter(),
|
new DayCounter(),
|
||||||
new Speedometer(),
|
new Speedometer(),
|
||||||
new Zoom(),
|
new Zoom(),
|
||||||
new HealthDisplay()
|
new HealthDisplay(),
|
||||||
|
new Nametags(),
|
||||||
|
new Ping(),
|
||||||
|
new Tps(),
|
||||||
|
new Clock()
|
||||||
};
|
};
|
||||||
|
|
||||||
public static void init() {
|
public static void init() {
|
||||||
|
|||||||
@@ -0,0 +1,77 @@
|
|||||||
|
package org.saturnclient.modules.mods;
|
||||||
|
|
||||||
|
import java.time.format.DateTimeFormatter;
|
||||||
|
import java.time.LocalTime;
|
||||||
|
|
||||||
|
import org.saturnclient.modules.HudMod;
|
||||||
|
import org.saturnclient.modules.ModDimensions;
|
||||||
|
import org.saturnclient.modules.Module;
|
||||||
|
import org.saturnclient.modules.ModuleDetails;
|
||||||
|
import org.saturnclient.saturnclient.config.Property;
|
||||||
|
import org.saturnclient.ui2.RenderScope;
|
||||||
|
import org.saturnclient.ui2.resources.Fonts;
|
||||||
|
|
||||||
|
public class Clock extends Module implements HudMod {
|
||||||
|
private static Property<Boolean> enabled = Property.bool(false);
|
||||||
|
private static Property<Integer> format = Property.select(0, "24 hour", "12 hour");
|
||||||
|
private static Property<Boolean> seconds = Property.bool(false);
|
||||||
|
private static ModDimensions dimensions = new ModDimensions(60, Fonts.getHeight());
|
||||||
|
|
||||||
|
public Clock() {
|
||||||
|
super(new ModuleDetails("Clock", "clock")
|
||||||
|
.description("Displays the current real-world time")
|
||||||
|
.version("v0.1.0")
|
||||||
|
.tags("Utility"),
|
||||||
|
enabled.named("Enabled"),
|
||||||
|
format.named("Format"),
|
||||||
|
seconds.named("Show seconds"),
|
||||||
|
dimensions.prop()
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void renderDummy(RenderScope scope) {
|
||||||
|
renderClock(scope);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void renderHud(RenderScope scope) {
|
||||||
|
renderClock(scope);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void renderClock(RenderScope scope) {
|
||||||
|
String text = "";
|
||||||
|
LocalTime currentTime = LocalTime.now();
|
||||||
|
|
||||||
|
switch (format.value) {
|
||||||
|
case 0:
|
||||||
|
if (seconds.value) { text = currentTime.format(DateTimeFormatter.ofPattern("HH:mm:ss")); }
|
||||||
|
else { text = currentTime.format(DateTimeFormatter.ofPattern("HH:mm")); }
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
if (seconds.value) { text = currentTime.format(DateTimeFormatter.ofPattern("hh:mm:ss a")); }
|
||||||
|
else { text = currentTime.format(DateTimeFormatter.ofPattern("hh:mm a")); }
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
scope.drawText(text,
|
||||||
|
0, 0, dimensions.font.value, dimensions.fgColor.value);
|
||||||
|
dimensions.width = Fonts.getWidth(text, dimensions.font.value);
|
||||||
|
dimensions.height = 18 * text.split("\n").length;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isEnabled() {
|
||||||
|
return enabled.value;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public ModDimensions getDimensions() {
|
||||||
|
return dimensions;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onEnabled(boolean e) {
|
||||||
|
enabled.value = e;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -34,7 +34,7 @@ public class HealthDisplay extends Module implements HudMod {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void renderDummy(RenderScope scope) {
|
public void renderDummy(RenderScope scope) {
|
||||||
renderSpeed(10, scope);
|
renderHealth(10, scope);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -44,10 +44,10 @@ public class HealthDisplay extends Module implements HudMod {
|
|||||||
case 1:
|
case 1:
|
||||||
health = health / 2;
|
health = health / 2;
|
||||||
}
|
}
|
||||||
renderSpeed(health, scope);
|
renderHealth(health, scope);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void renderSpeed(float health, RenderScope scope) {
|
public void renderHealth(float health, RenderScope scope) {
|
||||||
String text = "";
|
String text = "";
|
||||||
|
|
||||||
switch (decimals.value) {
|
switch (decimals.value) {
|
||||||
|
|||||||
@@ -0,0 +1,148 @@
|
|||||||
|
package org.saturnclient.modules.mods;
|
||||||
|
|
||||||
|
import org.saturnclient.modules.Module;
|
||||||
|
import org.saturnclient.modules.ModuleDetails;
|
||||||
|
import org.saturnclient.modules.mods.utils.HealthRenderState;
|
||||||
|
import org.saturnclient.saturnclient.config.Property;
|
||||||
|
|
||||||
|
import net.minecraft.client.render.entity.state.LivingEntityRenderState;
|
||||||
|
|
||||||
|
// todo: rendering modes, custom names
|
||||||
|
|
||||||
|
public class Nametags extends Module {
|
||||||
|
private static Property<Boolean> enabled = Property.bool(false);
|
||||||
|
private static Property<Boolean> healthDisplay = Property.bool(false);
|
||||||
|
private static Property<Boolean> players = Property.bool(true);
|
||||||
|
private static Property<Boolean> hostile = Property.bool(false);
|
||||||
|
private static Property<Boolean> passive = Property.bool(false);
|
||||||
|
private static Property<Boolean> heartEmoji = Property.bool(true);
|
||||||
|
private static Property<Boolean> obfuscate = Property.bool(false);
|
||||||
|
private static Property<Integer> unit = Property.select(0, "Health", "Hearts");
|
||||||
|
private static Property<Integer> format = Property.select(0, "Value", "Value / Total", "%");
|
||||||
|
private static Property<Integer> nameColor = Property.select(15,
|
||||||
|
"Black",
|
||||||
|
"Dark Blue",
|
||||||
|
"Dark Green",
|
||||||
|
"Dark Aqua",
|
||||||
|
"Dark Red",
|
||||||
|
"Dark Purple",
|
||||||
|
"Gold",
|
||||||
|
"Gray",
|
||||||
|
"Dark Gray",
|
||||||
|
"Blue",
|
||||||
|
"Green",
|
||||||
|
"Aqua",
|
||||||
|
"Red",
|
||||||
|
"Light Purple",
|
||||||
|
"Yellow",
|
||||||
|
"White"
|
||||||
|
);
|
||||||
|
private static Property<Integer> healthColor = Property.select(12,
|
||||||
|
"Black",
|
||||||
|
"Dark Blue",
|
||||||
|
"Dark Green",
|
||||||
|
"Dark Aqua",
|
||||||
|
"Dark Red",
|
||||||
|
"Dark Purple",
|
||||||
|
"Gold",
|
||||||
|
"Gray",
|
||||||
|
"Dark Gray",
|
||||||
|
"Blue",
|
||||||
|
"Green",
|
||||||
|
"Aqua",
|
||||||
|
"Red",
|
||||||
|
"Light Purple",
|
||||||
|
"Yellow",
|
||||||
|
"White"
|
||||||
|
);
|
||||||
|
|
||||||
|
private static final String[] COLOR_CODES = {
|
||||||
|
"§0", "§1", "§2", "§3", "§4", "§5", "§6", "§7",
|
||||||
|
"§8", "§9", "§a", "§b", "§c", "§d", "§e", "§f"
|
||||||
|
};
|
||||||
|
|
||||||
|
public Nametags() {
|
||||||
|
super(
|
||||||
|
new ModuleDetails("Nametags", "nametags")
|
||||||
|
.description("Allows you to modify entity nametags")
|
||||||
|
.tags("Camera", "Utility")
|
||||||
|
.version("0.1.0"),
|
||||||
|
enabled.named("Enabled"),
|
||||||
|
healthDisplay.named("Display health"),
|
||||||
|
players.named("Players"),
|
||||||
|
hostile.named("Hostile"),
|
||||||
|
passive.named("Passive"),
|
||||||
|
heartEmoji.named("Heart emoji"),
|
||||||
|
obfuscate.named("Obfuscate enemy names"),
|
||||||
|
unit.named("Unit"),
|
||||||
|
format.named("Format"),
|
||||||
|
nameColor.named("Name color"),
|
||||||
|
healthColor.named("Health color")
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void tick() {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
public static String getHealthString(LivingEntityRenderState state, HealthRenderState hrs, float health, float maxHealth) {
|
||||||
|
String ret = "";
|
||||||
|
|
||||||
|
switch (format.value){
|
||||||
|
case 0: // value
|
||||||
|
ret = String.format("%.1f", health / (unit.value + 1));
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 1: // value / total
|
||||||
|
ret = String.format("%.1f", health / (unit.value + 1)) + " / " + String.format("%.1f", maxHealth / (unit.value + 1));
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 2: // %
|
||||||
|
ret = String.format("%.0f%%", (health / maxHealth) * 100);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static String getNametagString(LivingEntityRenderState state) {
|
||||||
|
if (state.customName == null) return null;
|
||||||
|
if (!healthDisplay.value) return state.customName.getString(); // name only
|
||||||
|
if (!(state instanceof HealthRenderState hrs)) return null;
|
||||||
|
|
||||||
|
float health = hrs.saturn$getHealth();
|
||||||
|
float maxHealth = hrs.saturn$getMaxHealth();
|
||||||
|
|
||||||
|
HealthRenderState.EntityType type = hrs.saturn$getEntityType();
|
||||||
|
if (type == HealthRenderState.EntityType.PASSIVE && !passive.value) return null;
|
||||||
|
if (type == HealthRenderState.EntityType.HOSTILE && !hostile.value) return null;
|
||||||
|
if (type == HealthRenderState.EntityType.PLAYER && !players.value) return null;
|
||||||
|
if (type == HealthRenderState.EntityType.OTHER) return null;
|
||||||
|
|
||||||
|
if (health < 0f || maxHealth < 0f || health > maxHealth) return null;
|
||||||
|
|
||||||
|
String hpColor = COLOR_CODES[healthColor.value];
|
||||||
|
String color = COLOR_CODES[nameColor.value];
|
||||||
|
String heart = heartEmoji.value ? " ❤" : "";
|
||||||
|
String obf = obfuscate.value ? "§k" : "";
|
||||||
|
String reset = "§r";
|
||||||
|
|
||||||
|
String ret = color + obf + state.customName.getString() + reset + " " + hpColor + getHealthString(state, hrs, health, maxHealth) + heart;
|
||||||
|
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static boolean shouldReplaceName() {
|
||||||
|
return enabled.value;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onEnabled(boolean e) {
|
||||||
|
enabled.value = e;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isEnabled() {
|
||||||
|
return enabled.value;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,60 @@
|
|||||||
|
package org.saturnclient.modules.mods;
|
||||||
|
|
||||||
|
import org.saturnclient.modules.HudMod;
|
||||||
|
import org.saturnclient.modules.ModDimensions;
|
||||||
|
import org.saturnclient.modules.Module;
|
||||||
|
import org.saturnclient.modules.ModuleDetails;
|
||||||
|
import org.saturnclient.saturnclient.config.Property;
|
||||||
|
import org.saturnclient.ui2.RenderScope;
|
||||||
|
import org.saturnclient.ui2.resources.Fonts;
|
||||||
|
|
||||||
|
import net.minecraft.client.MinecraftClient;
|
||||||
|
import net.minecraft.client.network.ClientPlayNetworkHandler;
|
||||||
|
|
||||||
|
public class Ping extends Module implements HudMod {
|
||||||
|
private static Property<Boolean> enabled = Property.bool(false);
|
||||||
|
private static ModDimensions dimensions = new ModDimensions(60, Fonts.getHeight());
|
||||||
|
|
||||||
|
public Ping() {
|
||||||
|
super(new ModuleDetails("Ping Display", "ping")
|
||||||
|
.description("Displays ping")
|
||||||
|
.version("v0.1.0")
|
||||||
|
.tags("Utility"),
|
||||||
|
enabled.named("Enabled"),
|
||||||
|
dimensions.prop());
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void renderHud(RenderScope scope) {
|
||||||
|
MinecraftClient client = MinecraftClient.getInstance();
|
||||||
|
ClientPlayNetworkHandler handler = client.getNetworkHandler();
|
||||||
|
String text = "0 ms";
|
||||||
|
if (handler != null) {
|
||||||
|
text = String.valueOf(handler.getPlayerListEntry(client.player.getUuid()).getLatency()) + " ms";
|
||||||
|
}
|
||||||
|
scope.drawText(text, 0, 0, dimensions.font.value, dimensions.fgColor.value);
|
||||||
|
dimensions.width = Fonts.getWidth(text, dimensions.font.value);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void renderDummy(RenderScope scope) {
|
||||||
|
String text = "10 ms";
|
||||||
|
scope.drawText(text, 0, 0, dimensions.font.value, dimensions.fgColor.value);
|
||||||
|
dimensions.width = Fonts.getWidth(text, dimensions.font.value);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isEnabled() {
|
||||||
|
return enabled.value;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onEnabled(boolean e) {
|
||||||
|
enabled.value = e;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public ModDimensions getDimensions() {
|
||||||
|
return dimensions;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,99 @@
|
|||||||
|
package org.saturnclient.modules.mods;
|
||||||
|
|
||||||
|
import org.saturnclient.modules.HudMod;
|
||||||
|
import org.saturnclient.modules.ModDimensions;
|
||||||
|
import org.saturnclient.modules.Module;
|
||||||
|
import org.saturnclient.modules.ModuleDetails;
|
||||||
|
import org.saturnclient.saturnclient.config.Property;
|
||||||
|
import org.saturnclient.ui2.RenderScope;
|
||||||
|
import org.saturnclient.ui2.resources.Fonts;
|
||||||
|
|
||||||
|
public class Tps extends Module implements HudMod {
|
||||||
|
private static Property<Boolean> enabled = Property.bool(false);
|
||||||
|
private static ModDimensions dimensions = new ModDimensions(60, Fonts.getHeight());
|
||||||
|
|
||||||
|
private static long lastWorldAge = -1;
|
||||||
|
private static long lastRealTime = -1;
|
||||||
|
private static double currentTps = 20.0;
|
||||||
|
|
||||||
|
private static final int SAMPLE_COUNT = 2;
|
||||||
|
private static final double[] samples = new double[SAMPLE_COUNT];
|
||||||
|
static {
|
||||||
|
java.util.Arrays.fill(samples, 20.0);
|
||||||
|
}
|
||||||
|
private static int sampleIndex = 0;
|
||||||
|
private static int samplesFilled = 0;
|
||||||
|
|
||||||
|
public Tps() {
|
||||||
|
super(new ModuleDetails("TPS Display", "tps")
|
||||||
|
.description("Displays the TPS")
|
||||||
|
.version("v0.1.0")
|
||||||
|
.tags("Utility"),
|
||||||
|
enabled.named("Enabled"),
|
||||||
|
dimensions.prop()
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void onTimePacket(long worldAge) {
|
||||||
|
long now = System.currentTimeMillis();
|
||||||
|
|
||||||
|
if (lastWorldAge != -1 && lastRealTime != -1) {
|
||||||
|
long tickDelta = worldAge - lastWorldAge;
|
||||||
|
long timeDelta = now - lastRealTime;
|
||||||
|
|
||||||
|
if (timeDelta > 0 && tickDelta > 0) {
|
||||||
|
double sample = (tickDelta / (double) timeDelta) * 1000.0;
|
||||||
|
sample = Math.min(sample, 20.0);
|
||||||
|
|
||||||
|
samples[sampleIndex % SAMPLE_COUNT] = sample;
|
||||||
|
sampleIndex++;
|
||||||
|
samplesFilled = Math.min(samplesFilled + 1, SAMPLE_COUNT);
|
||||||
|
|
||||||
|
double sum = 0;
|
||||||
|
for (int i = 0; i < samplesFilled; i++) sum += samples[i];
|
||||||
|
currentTps = sum / samplesFilled;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
lastWorldAge = worldAge;
|
||||||
|
lastRealTime = now;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void reset() {
|
||||||
|
lastWorldAge = -1;
|
||||||
|
lastRealTime = -1;
|
||||||
|
currentTps = 20.0;
|
||||||
|
sampleIndex = 0;
|
||||||
|
samplesFilled = SAMPLE_COUNT;
|
||||||
|
for (int i = 0; i < SAMPLE_COUNT; i++) samples[i] = 20.0;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void renderHud(RenderScope scope) {
|
||||||
|
String text = String.format("%.1f TPS", currentTps);
|
||||||
|
scope.drawText(text, 0, 0, dimensions.font.value, dimensions.fgColor.value);
|
||||||
|
dimensions.width = Fonts.getWidth(text, dimensions.font.value);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void renderDummy(RenderScope scope) {
|
||||||
|
String text = "20.0 TPS";
|
||||||
|
scope.drawText(text, 0, 0, dimensions.font.value, dimensions.fgColor.value);
|
||||||
|
dimensions.width = Fonts.getWidth(text, dimensions.font.value);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isEnabled() {
|
||||||
|
return enabled.value;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onEnabled(boolean e) {
|
||||||
|
enabled.value = e;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public ModDimensions getDimensions() {
|
||||||
|
return dimensions;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,26 @@
|
|||||||
|
package org.saturnclient.modules.mods.mixins;
|
||||||
|
|
||||||
|
import net.minecraft.client.render.entity.state.LivingEntityRenderState;
|
||||||
|
|
||||||
|
import org.saturnclient.modules.mods.utils.HealthRenderState;
|
||||||
|
import org.spongepowered.asm.mixin.Mixin;
|
||||||
|
import org.spongepowered.asm.mixin.Unique;
|
||||||
|
|
||||||
|
@Mixin(LivingEntityRenderState.class)
|
||||||
|
public class LivingEntityRenderStateMixin implements org.saturnclient.modules.mods.utils.HealthRenderState {
|
||||||
|
|
||||||
|
@Unique private float saturn$health = 0f;
|
||||||
|
@Unique private float saturn$maxHealth = 1f;
|
||||||
|
@Unique private HealthRenderState.EntityType saturn$entityType = HealthRenderState.EntityType.OTHER;
|
||||||
|
|
||||||
|
public float saturn$getHealth() { return saturn$health; }
|
||||||
|
public float saturn$getMaxHealth() { return saturn$maxHealth; }
|
||||||
|
public void saturn$setHealth(float health, float maxHealth) {
|
||||||
|
this.saturn$health = health;
|
||||||
|
this.saturn$maxHealth = maxHealth;
|
||||||
|
}
|
||||||
|
|
||||||
|
public HealthRenderState.EntityType saturn$getEntityType() { return saturn$entityType; }
|
||||||
|
public void saturn$setEntityType(HealthRenderState.EntityType type) { this.saturn$entityType = type; }
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,34 @@
|
|||||||
|
package org.saturnclient.modules.mods.mixins;
|
||||||
|
|
||||||
|
import net.minecraft.client.render.entity.LivingEntityRenderer;
|
||||||
|
import net.minecraft.client.render.entity.state.LivingEntityRenderState;
|
||||||
|
import org.saturnclient.modules.mods.utils.HealthRenderState;
|
||||||
|
import net.minecraft.entity.LivingEntity;
|
||||||
|
import net.minecraft.entity.mob.HostileEntity;
|
||||||
|
import net.minecraft.entity.passive.PassiveEntity;
|
||||||
|
import net.minecraft.entity.player.PlayerEntity;
|
||||||
|
import org.spongepowered.asm.mixin.Mixin;
|
||||||
|
import org.spongepowered.asm.mixin.injection.At;
|
||||||
|
import org.spongepowered.asm.mixin.injection.Inject;
|
||||||
|
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||||
|
|
||||||
|
@Mixin(LivingEntityRenderer.class)
|
||||||
|
public abstract class LivingEntityRendererMixin<T extends LivingEntity, S extends LivingEntityRenderState> {
|
||||||
|
|
||||||
|
@Inject(method = "updateRenderState", at = @At("TAIL"))
|
||||||
|
private void saturn$captureHealth(T entity, S state, float tickDelta, CallbackInfo ci) {
|
||||||
|
if (!(state instanceof HealthRenderState hrs)) return;
|
||||||
|
|
||||||
|
hrs.saturn$setHealth(entity.getHealth(), entity.getMaxHealth());
|
||||||
|
|
||||||
|
if (entity instanceof PlayerEntity) {
|
||||||
|
hrs.saturn$setEntityType(HealthRenderState.EntityType.PLAYER);
|
||||||
|
} else if (entity instanceof HostileEntity) {
|
||||||
|
hrs.saturn$setEntityType(HealthRenderState.EntityType.HOSTILE);
|
||||||
|
} else if (entity instanceof PassiveEntity) {
|
||||||
|
hrs.saturn$setEntityType(HealthRenderState.EntityType.PASSIVE);
|
||||||
|
} else {
|
||||||
|
hrs.saturn$setEntityType(HealthRenderState.EntityType.OTHER);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,48 @@
|
|||||||
|
package org.saturnclient.modules.mods.mixins;
|
||||||
|
|
||||||
|
import net.minecraft.client.render.VertexConsumerProvider;
|
||||||
|
import net.minecraft.client.render.entity.EntityRenderer;
|
||||||
|
import net.minecraft.client.render.entity.state.EntityRenderState;
|
||||||
|
import net.minecraft.client.render.entity.state.LivingEntityRenderState;
|
||||||
|
import net.minecraft.client.util.math.MatrixStack;
|
||||||
|
import net.minecraft.text.Text;
|
||||||
|
import org.saturnclient.modules.mods.Nametags;
|
||||||
|
import org.spongepowered.asm.mixin.Mixin;
|
||||||
|
import org.spongepowered.asm.mixin.Shadow;
|
||||||
|
import org.spongepowered.asm.mixin.Unique;
|
||||||
|
import org.spongepowered.asm.mixin.injection.At;
|
||||||
|
import org.spongepowered.asm.mixin.injection.Inject;
|
||||||
|
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||||
|
|
||||||
|
@Mixin(EntityRenderer.class)
|
||||||
|
public abstract class NametagsMixin {
|
||||||
|
|
||||||
|
@Unique
|
||||||
|
private static final ThreadLocal<Boolean> saturn$rendering = ThreadLocal.withInitial(() -> false);
|
||||||
|
|
||||||
|
@Shadow
|
||||||
|
protected abstract <S extends EntityRenderState> void renderLabelIfPresent(
|
||||||
|
S state, Text text, MatrixStack matrices, VertexConsumerProvider vertexConsumers, int light
|
||||||
|
);
|
||||||
|
|
||||||
|
@Inject(method = "renderLabelIfPresent", at = @At("HEAD"), cancellable = true)
|
||||||
|
private <S extends EntityRenderState> void saturn$replaceNametag(S state, Text text,
|
||||||
|
MatrixStack matrices, VertexConsumerProvider vertexConsumers,
|
||||||
|
int light, CallbackInfo ci) {
|
||||||
|
|
||||||
|
if (saturn$rendering.get()) return;
|
||||||
|
if (!Nametags.shouldReplaceName()) return;
|
||||||
|
if (!(state instanceof LivingEntityRenderState living)) return;
|
||||||
|
|
||||||
|
String replacement = Nametags.getNametagString(living);
|
||||||
|
if (replacement == null) return;
|
||||||
|
|
||||||
|
ci.cancel();
|
||||||
|
saturn$rendering.set(true);
|
||||||
|
try {
|
||||||
|
renderLabelIfPresent(state, Text.literal(replacement), matrices, vertexConsumers, light);
|
||||||
|
} finally {
|
||||||
|
saturn$rendering.set(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,18 @@
|
|||||||
|
package org.saturnclient.modules.mods.mixins;
|
||||||
|
|
||||||
|
import net.minecraft.client.network.ClientPlayNetworkHandler;
|
||||||
|
import net.minecraft.network.packet.s2c.play.WorldTimeUpdateS2CPacket;
|
||||||
|
import org.saturnclient.modules.mods.Tps;
|
||||||
|
import org.spongepowered.asm.mixin.Mixin;
|
||||||
|
import org.spongepowered.asm.mixin.injection.At;
|
||||||
|
import org.spongepowered.asm.mixin.injection.Inject;
|
||||||
|
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||||
|
|
||||||
|
@Mixin(ClientPlayNetworkHandler.class)
|
||||||
|
public class TpsMixin {
|
||||||
|
|
||||||
|
@Inject(method = "onWorldTimeUpdate", at = @At("HEAD"))
|
||||||
|
private void onWorldTimeUpdate(WorldTimeUpdateS2CPacket packet, CallbackInfo ci) {
|
||||||
|
Tps.onTimePacket(packet.time());
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,14 @@
|
|||||||
|
package org.saturnclient.modules.mods.utils;
|
||||||
|
|
||||||
|
public interface HealthRenderState {
|
||||||
|
float saturn$getHealth();
|
||||||
|
float saturn$getMaxHealth();
|
||||||
|
void saturn$setHealth(float health, float maxHealth);
|
||||||
|
|
||||||
|
EntityType saturn$getEntityType();
|
||||||
|
void saturn$setEntityType(EntityType type);
|
||||||
|
|
||||||
|
enum EntityType {
|
||||||
|
PLAYER, HOSTILE, PASSIVE, OTHER
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -39,7 +39,7 @@ public class KeyInputHandler {
|
|||||||
client.setScreen(new ShiftMenu());
|
client.setScreen(new ShiftMenu());
|
||||||
}
|
}
|
||||||
|
|
||||||
if (SaturnClientConfig.openEmoteWheel.wasKeyPressed() && client.currentScreen == null) {
|
if (SaturnClientConfig.openEmoteWheel.wasKeyPressed() && client.currentScreen == null && !InputUtil.isKeyPressed(client.getWindow().getHandle(), GLFW.GLFW_KEY_F3)) {
|
||||||
client.setScreen(new EmoteWheel());
|
client.setScreen(new EmoteWheel());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -70,14 +70,14 @@ public class Scroll extends Element {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Element dimensions(int width, int height) {
|
public Element dimensions(int width, int height) {
|
||||||
maxScroll = 0;
|
super.dimensions(width, height);
|
||||||
|
|
||||||
|
maxScroll = 0;
|
||||||
for (Element element : children) {
|
for (Element element : children) {
|
||||||
maxScroll = Math.max(maxScroll, element.y + element.height - height);
|
maxScroll = Math.max(maxScroll, (element.y + element.height + padding) - (height - padding * 2));
|
||||||
}
|
}
|
||||||
|
|
||||||
maxScroll = Math.max(0, maxScroll); // never negative
|
return this;
|
||||||
return super.dimensions(width, height);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int calculateScrollBarHeight() {
|
int calculateScrollBarHeight() {
|
||||||
@@ -88,9 +88,9 @@ public class Scroll extends Element {
|
|||||||
|
|
||||||
int calculateScrollBarY() {
|
int calculateScrollBarY() {
|
||||||
int scrollBarHeight = calculateScrollBarHeight();
|
int scrollBarHeight = calculateScrollBarHeight();
|
||||||
if (maxScroll <= 0)
|
if (maxScroll <= 0) return scrollBarPadding.value;
|
||||||
return scrollBarPadding.value;
|
int y = (scroll * (height - scrollBarHeight - scrollBarPadding.value * 2)) / maxScroll + scrollBarPadding.value;
|
||||||
return (scroll * (height - scrollBarHeight)) / maxScroll + scrollBarPadding.value;
|
return Math.min(y, height - scrollBarHeight - scrollBarPadding.value);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void calculateMaxScroll() {
|
private void calculateMaxScroll() {
|
||||||
|
|||||||
Binary file not shown.
|
After Width: | Height: | Size: 1.0 KiB |
Binary file not shown.
|
After Width: | Height: | Size: 800 B |
Binary file not shown.
|
After Width: | Height: | Size: 197 B |
Binary file not shown.
|
After Width: | Height: | Size: 777 B |
@@ -9,7 +9,11 @@
|
|||||||
"RenderMixin",
|
"RenderMixin",
|
||||||
"LightmapTextureManagerMixin",
|
"LightmapTextureManagerMixin",
|
||||||
"BackgroundRendererMixin",
|
"BackgroundRendererMixin",
|
||||||
"GameRendererMixin"
|
"GameRendererMixin",
|
||||||
|
"NametagsMixin",
|
||||||
|
"LivingEntityRenderStateMixin",
|
||||||
|
"LivingEntityRendererMixin",
|
||||||
|
"TpsMixin"
|
||||||
],
|
],
|
||||||
"injectors": {
|
"injectors": {
|
||||||
"defaultRequire": 1
|
"defaultRequire": 1
|
||||||
|
|||||||
Reference in New Issue
Block a user