beer more complex, advancements tab
This commit is contained in:
@@ -70,7 +70,6 @@ public class TitleScreenBackgroundMixin {
|
||||
private static void loadFrames() {
|
||||
if (framesLoaded) return;
|
||||
framesLoaded = true;
|
||||
|
||||
MinecraftClient client = MinecraftClient.getInstance();
|
||||
ResourceManager resourceManager = client.getResourceManager();
|
||||
|
||||
@@ -91,8 +90,13 @@ public class TitleScreenBackgroundMixin {
|
||||
}
|
||||
|
||||
Identifier frameId = new Identifier("szar", "aprilfools/overlay_frame_" + i);
|
||||
|
||||
// Destroy old texture if it exists
|
||||
client.getTextureManager().destroyTexture(frameId);
|
||||
|
||||
NativeImageBackedTexture texture = new NativeImageBackedTexture(frame);
|
||||
client.getTextureManager().registerTexture(frameId, texture);
|
||||
texture.upload();
|
||||
FRAMES.add(frameId);
|
||||
}
|
||||
|
||||
@@ -102,11 +106,20 @@ public class TitleScreenBackgroundMixin {
|
||||
}
|
||||
}
|
||||
|
||||
@Inject(method = "init", at = @At("HEAD"))
|
||||
private void onInit(CallbackInfo ci) {
|
||||
if (!isAprilFools()) return;
|
||||
framesLoaded = false;
|
||||
FRAMES.clear();
|
||||
currentFrame = 0;
|
||||
lastFrameTime = 0;
|
||||
loadFrames();
|
||||
}
|
||||
|
||||
@Inject(method = "render", at = @At("HEAD"))
|
||||
private void onRenderHead(DrawContext context, int mouseX, int mouseY, float delta, CallbackInfo ci) {
|
||||
if (!isAprilFools()) return;
|
||||
loadFrames();
|
||||
if (FRAMES.isEmpty()) return; // don't advance if nothing loaded
|
||||
if (FRAMES.isEmpty()) return;
|
||||
|
||||
long now = System.currentTimeMillis();
|
||||
if (now - lastFrameTime >= FRAME_DURATION_MS) {
|
||||
@@ -131,10 +144,7 @@ public class TitleScreenBackgroundMixin {
|
||||
context.drawTexture(texture, x, y, width, height, u, v, regionWidth, regionHeight, textureWidth, textureHeight);
|
||||
return;
|
||||
}
|
||||
|
||||
float alpha = getFadeAlpha();
|
||||
if (alpha <= 0f) return; // fully transparent, skip entirely
|
||||
|
||||
float alpha = backgroundFadeStart == 0L ? 1.0f : getFadeAlpha();
|
||||
// Apply alpha via RenderSystem before drawing
|
||||
RenderSystem.enableBlend();
|
||||
RenderSystem.setShaderColor(1.0F, 1.0F, 1.0F, alpha);
|
||||
|
||||
@@ -9,6 +9,7 @@ import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.network.packet.s2c.play.EntityAnimationS2CPacket;
|
||||
import net.minecraft.server.MinecraftServer;
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
import net.minecraft.server.world.ServerWorld;
|
||||
import net.minecraft.sound.SoundCategory;
|
||||
import net.minecraft.sound.SoundEvents;
|
||||
import net.minecraft.text.Text;
|
||||
@@ -24,29 +25,148 @@ public class DrunkEffect extends StatusEffect {
|
||||
|
||||
public enum DrunkType { AGGRESSIVE, STUMBLING, SLEEPY, GENEROUS, PARANOID }
|
||||
|
||||
// Per-player assigned drunk type — assigned when effect is first detected
|
||||
private static final Map<UUID, DrunkType> playerTypes = new HashMap<>();
|
||||
// For sleepy — track how long the player is forced to crouch
|
||||
private static final Map<UUID, Integer> sleepyTimer = new HashMap<>();
|
||||
static String currentDisplayType = "None";
|
||||
|
||||
// Behavior tracking maps — updated via mixins or event hooks
|
||||
public static final Map<UUID, Long> lastAttackTime = new HashMap<>(); // AGGRESSIVE
|
||||
public static final Map<UUID, Long> lastBlockCollisionTime = new HashMap<>(); // STUMBLING
|
||||
public static final Map<UUID, Long> lastSleepTime = new HashMap<>(); // SLEEPY
|
||||
public static final Map<UUID, Integer> recentDropCount = new HashMap<>(); // GENEROUS
|
||||
public static final Map<UUID, Long> lastDropResetTime = new HashMap<>();
|
||||
public static final Map<UUID, Float> lastYaw = new HashMap<>(); // PARANOID
|
||||
public static final Map<UUID, Float> totalYawChange = new HashMap<>();
|
||||
public static final Map<UUID, Long> yawTrackStart = new HashMap<>();
|
||||
|
||||
// Window in ticks for behavior tracking
|
||||
private static final long BEHAVIOR_WINDOW = 6000L; // 5 minutes
|
||||
|
||||
public DrunkEffect() {
|
||||
super(StatusEffectCategory.HARMFUL, 0xFF9900);
|
||||
}
|
||||
|
||||
// Called every tick from server tick event to track yaw changes
|
||||
public static void trackBehavior(MinecraftServer server) {
|
||||
for (var world : server.getWorlds()) {
|
||||
for (ServerPlayerEntity player : world.getPlayers()) {
|
||||
UUID uuid = player.getUuid();
|
||||
long now = world.getTime();
|
||||
|
||||
// Track yaw change for PARANOID — only count large sudden movements
|
||||
float yaw = player.getYaw();
|
||||
Float prev = lastYaw.get(uuid);
|
||||
if (prev != null) {
|
||||
float delta = Math.abs(yaw - prev);
|
||||
if (delta > 180) delta = 360 - delta;
|
||||
// Only count if moved more than 45 degrees in a single tick — sharp spin
|
||||
if (delta > 45f) {
|
||||
totalYawChange.merge(uuid, delta, Float::sum);
|
||||
}
|
||||
}
|
||||
lastYaw.put(uuid, yaw);
|
||||
|
||||
// Reset yaw accumulator every 5 minutes
|
||||
long trackStart = yawTrackStart.getOrDefault(uuid, now);
|
||||
if (now - trackStart > BEHAVIOR_WINDOW) {
|
||||
totalYawChange.put(uuid, 0f);
|
||||
yawTrackStart.put(uuid, now);
|
||||
}
|
||||
|
||||
// Reset drop counter every 5 minutes
|
||||
long dropReset = lastDropResetTime.getOrDefault(uuid, now);
|
||||
if (now - dropReset > BEHAVIOR_WINDOW) {
|
||||
recentDropCount.put(uuid, 0);
|
||||
lastDropResetTime.put(uuid, now);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static DrunkType selectWeightedType(ServerPlayerEntity player, ServerWorld world) {
|
||||
UUID uuid = player.getUuid();
|
||||
long now = world.getTime();
|
||||
|
||||
// Base weight for each type
|
||||
Map<DrunkType, Float> weights = new HashMap<>();
|
||||
for (DrunkType t : DrunkType.values()) weights.put(t, 1.0f);
|
||||
|
||||
// AGGRESSIVE: attacked recently
|
||||
Long lastAttack = lastAttackTime.get(uuid);
|
||||
if (lastAttack != null) {
|
||||
long ticksAgo = now - lastAttack;
|
||||
if (ticksAgo < BEHAVIOR_WINDOW) {
|
||||
// More recent = higher weight, max 5x boost
|
||||
float boost = 1.0f + (4.0f * (1.0f - (float) ticksAgo / BEHAVIOR_WINDOW));
|
||||
weights.merge(DrunkType.AGGRESSIVE, boost, Float::sum);
|
||||
}
|
||||
}
|
||||
|
||||
// STUMBLING: bumped into a block recently
|
||||
Long lastCollision = lastBlockCollisionTime.get(uuid);
|
||||
if (lastCollision != null) {
|
||||
long ticksAgo = now - lastCollision;
|
||||
if (ticksAgo < BEHAVIOR_WINDOW) {
|
||||
float boost = 1.0f + (4.0f * (1.0f - (float) ticksAgo / BEHAVIOR_WINDOW));
|
||||
weights.merge(DrunkType.STUMBLING, boost, Float::sum);
|
||||
}
|
||||
}
|
||||
|
||||
// SLEEPY: slept recently
|
||||
Long lastSleep = lastSleepTime.get(uuid);
|
||||
if (lastSleep != null) {
|
||||
long ticksAgo = now - lastSleep;
|
||||
if (ticksAgo < BEHAVIOR_WINDOW) {
|
||||
float boost = 1.0f + (4.0f * (1.0f - (float) ticksAgo / BEHAVIOR_WINDOW));
|
||||
weights.merge(DrunkType.SLEEPY, boost, Float::sum);
|
||||
}
|
||||
}
|
||||
|
||||
// GENEROUS: dropped many items recently
|
||||
int drops = recentDropCount.getOrDefault(uuid, 0);
|
||||
if (drops > 0) {
|
||||
// Every 5 drops = +1 weight, max 5x boost
|
||||
float boost = Math.min(5.0f, drops / 5.0f);
|
||||
weights.merge(DrunkType.GENEROUS, boost, Float::sum);
|
||||
}
|
||||
|
||||
// PARANOID: spun camera around a lot recently
|
||||
float yawChange = totalYawChange.getOrDefault(uuid, 0f);
|
||||
if (yawChange > 360f) {
|
||||
// Every full rotation = +0.5 weight, max 5x boost
|
||||
float boost = Math.min(5.0f, yawChange / 720f);
|
||||
weights.merge(DrunkType.PARANOID, boost, Float::sum);
|
||||
}
|
||||
|
||||
// Weighted random selection
|
||||
// Weighted random selection
|
||||
float totalWeight = weights.values().stream().reduce(0f, Float::sum);
|
||||
float roll = world.random.nextFloat() * totalWeight;
|
||||
float cumulative = 0f;
|
||||
|
||||
for (DrunkType type : DrunkType.values()) {
|
||||
cumulative += weights.get(type);
|
||||
if (roll < cumulative) {
|
||||
return type;
|
||||
}
|
||||
}
|
||||
|
||||
return DrunkType.values()[world.random.nextInt(DrunkType.values().length)];
|
||||
}
|
||||
|
||||
static void tick(MinecraftServer server) {
|
||||
trackBehavior(server);
|
||||
|
||||
for (var world : server.getWorlds()) {
|
||||
for (ServerPlayerEntity player : world.getPlayers()) {
|
||||
if (!player.hasStatusEffect(Szar.DRUNK_EFFECT)) {
|
||||
// Clean up when effect ends
|
||||
playerTypes.remove(player.getUuid());
|
||||
sleepyTimer.remove(player.getUuid());
|
||||
continue;
|
||||
}
|
||||
|
||||
// Assign type if not yet assigned
|
||||
DrunkType type = playerTypes.computeIfAbsent(player.getUuid(), k -> {
|
||||
DrunkType[] values = DrunkType.values();
|
||||
DrunkType assigned = values[world.random.nextInt(values.length)];
|
||||
DrunkType assigned = selectWeightedType(player, world);
|
||||
|
||||
String typeName = assigned.name().charAt(0)
|
||||
+ assigned.name().substring(1).toLowerCase();
|
||||
@@ -100,7 +220,6 @@ public class DrunkEffect extends StatusEffect {
|
||||
if (world.getTime() % 10 != 0) return;
|
||||
if (world.random.nextInt(4) != 0) return;
|
||||
|
||||
// Add a random sideways velocity push
|
||||
Vec3d current = player.getVelocity();
|
||||
double pushX = (world.random.nextDouble() - 0.5) * 0.4;
|
||||
double pushZ = (world.random.nextDouble() - 0.5) * 0.4;
|
||||
@@ -115,16 +234,14 @@ public class DrunkEffect extends StatusEffect {
|
||||
int timer = sleepyTimer.getOrDefault(uuid, 0);
|
||||
|
||||
if (timer > 0) {
|
||||
// Force crouch and stop movement
|
||||
player.setVelocity(0, player.getVelocity().y, 0);
|
||||
player.velocityModified = true;
|
||||
player.setSneaking(true);
|
||||
sleepyTimer.put(uuid, timer - 1);
|
||||
} else {
|
||||
player.setSneaking(false);
|
||||
// Every 3 seconds, 1 in 4 chance to fall asleep for 1-3 seconds
|
||||
if (world.getTime() % 60 == 0 && world.random.nextInt(4) == 0) {
|
||||
int sleepDuration = 20 + world.random.nextInt(40); // 1-3 seconds
|
||||
int sleepDuration = 20 + world.random.nextInt(40);
|
||||
sleepyTimer.put(uuid, sleepDuration);
|
||||
}
|
||||
}
|
||||
@@ -133,10 +250,9 @@ public class DrunkEffect extends StatusEffect {
|
||||
// --- GENEROUS ---
|
||||
private static void tickGenerous(net.minecraft.server.world.ServerWorld world,
|
||||
ServerPlayerEntity player) {
|
||||
if (world.getTime() % 60 != 0) return; // every 3 seconds
|
||||
if (world.getTime() % 60 != 0) return;
|
||||
if (world.random.nextInt(4) != 0) return;
|
||||
|
||||
// Find a random non-empty slot
|
||||
var inv = player.getInventory();
|
||||
java.util.List<Integer> nonEmpty = new java.util.ArrayList<>();
|
||||
for (int i = 0; i < inv.size(); i++) {
|
||||
@@ -147,7 +263,6 @@ public class DrunkEffect extends StatusEffect {
|
||||
int slot = nonEmpty.get(world.random.nextInt(nonEmpty.size()));
|
||||
ItemStack stack = inv.getStack(slot);
|
||||
|
||||
// Drop one item from the stack
|
||||
ItemStack toDrop = stack.copy();
|
||||
toDrop.setCount(1);
|
||||
stack.decrement(1);
|
||||
@@ -162,14 +277,12 @@ public class DrunkEffect extends StatusEffect {
|
||||
if (world.getTime() % 20 != 0) return;
|
||||
if (world.random.nextInt(3) != 0) return;
|
||||
|
||||
// Play a footstep sound at a random position nearby
|
||||
double offsetX = (world.random.nextDouble() - 0.5) * 10;
|
||||
double offsetZ = (world.random.nextDouble() - 0.5) * 10;
|
||||
double x = player.getX() + offsetX;
|
||||
double y = player.getY();
|
||||
double z = player.getZ() + offsetZ;
|
||||
|
||||
// Pick a random footstep sound
|
||||
net.minecraft.sound.SoundEvent[] footsteps = {
|
||||
SoundEvents.BLOCK_STONE_STEP,
|
||||
SoundEvents.BLOCK_GRAVEL_STEP,
|
||||
@@ -179,7 +292,6 @@ public class DrunkEffect extends StatusEffect {
|
||||
net.minecraft.sound.SoundEvent sound =
|
||||
footsteps[world.random.nextInt(footsteps.length)];
|
||||
|
||||
// Play only to this player
|
||||
player.networkHandler.sendPacket(
|
||||
new net.minecraft.network.packet.s2c.play.PlaySoundS2CPacket(
|
||||
world.getRegistryManager()
|
||||
|
||||
@@ -37,7 +37,7 @@ public class NwordPassItem extends Item {
|
||||
|
||||
// Grant advancement
|
||||
if (user instanceof ServerPlayerEntity serverPlayer) {
|
||||
grantAdvancement(serverPlayer);
|
||||
Szar.grantAdvancement(serverPlayer, "nwordpass");
|
||||
}
|
||||
|
||||
// Consume item
|
||||
@@ -46,23 +46,4 @@ public class NwordPassItem extends Item {
|
||||
|
||||
return TypedActionResult.success(stack, world.isClient);
|
||||
}
|
||||
|
||||
private void grantAdvancement(ServerPlayerEntity player) {
|
||||
ServerAdvancementLoader loader =
|
||||
player.getServer().getAdvancementLoader();
|
||||
|
||||
Advancement advancement =
|
||||
loader.get(new Identifier("szar", "nwordpass"));
|
||||
|
||||
if (advancement == null) return;
|
||||
|
||||
AdvancementProgress progress =
|
||||
player.getAdvancementTracker().getProgress(advancement);
|
||||
|
||||
if (!progress.isDone()) {
|
||||
for (String criterion : progress.getUnobtainedCriteria()) {
|
||||
player.getAdvancementTracker().grantCriterion(advancement, criterion);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -29,11 +29,23 @@ public class ObeliskCoreBlock extends Block implements BlockEntityProvider {
|
||||
|
||||
if (!(world instanceof ServerWorld serverWorld)) return;
|
||||
|
||||
TwoTowersUtil.grantNearbyAdvancement(serverWorld, pos, 100);
|
||||
Szar.grantNearbyAdvancement(serverWorld, pos, 100, "two_towers_explosion");
|
||||
|
||||
// Grant to players who died to plane_crash within 5 seconds and 50 blocks
|
||||
long currentTime = serverWorld.getTime();
|
||||
long fiveSecondsInTicks = 100L;
|
||||
|
||||
serverWorld.getPlayers().forEach(player -> {
|
||||
Long deathTime = Szar.recentPlaneCrashDeaths.get(player.getUuid());
|
||||
if (deathTime == null) return;
|
||||
if (currentTime - deathTime > fiveSecondsInTicks) return;
|
||||
if (player.getPos().distanceTo(net.minecraft.util.math.Vec3d.ofCenter(pos)) > 50) return;
|
||||
Szar.grantAdvancement(player, "two_towers_explosion");
|
||||
});
|
||||
|
||||
BlockEntity be = world.getBlockEntity(pos);
|
||||
if (be instanceof ObeliskCoreBlockEntity core) {
|
||||
core.setHasPlaneMob(false); // reset in case a plane was active
|
||||
core.setHasPlaneMob(false);
|
||||
core.markDirty();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -7,7 +7,9 @@ import net.fabricmc.fabric.api.biome.v1.BiomeModifications;
|
||||
import net.fabricmc.fabric.api.biome.v1.BiomeSelectors;
|
||||
import net.fabricmc.fabric.api.command.v2.CommandRegistrationCallback;
|
||||
import net.fabricmc.fabric.api.entity.event.v1.ServerEntityWorldChangeEvents;
|
||||
import net.fabricmc.fabric.api.entity.event.v1.ServerLivingEntityEvents;
|
||||
import net.fabricmc.fabric.api.entity.event.v1.ServerPlayerEvents;
|
||||
import net.fabricmc.fabric.api.event.lifecycle.v1.ServerEntityEvents;
|
||||
import net.fabricmc.fabric.api.event.lifecycle.v1.ServerLifecycleEvents;
|
||||
import net.fabricmc.fabric.api.event.lifecycle.v1.ServerTickEvents;
|
||||
import net.fabricmc.fabric.api.event.player.AttackEntityCallback;
|
||||
@@ -164,6 +166,7 @@ public class Szar implements ModInitializer {
|
||||
);
|
||||
public static final SoundEvent MERL_SOUND =
|
||||
SoundEvent.of(new Identifier(MOD_ID, "merl"));
|
||||
public static final Map<UUID, Long> recentPlaneCrashDeaths = new java.util.HashMap<>();
|
||||
public static final Identifier PLANE_ANIM_PACKET =
|
||||
new Identifier(MOD_ID, "plane_anim");
|
||||
public static final Identifier NAZI_HAND_GESTURE = new Identifier(MOD_ID, "hit_hand");
|
||||
@@ -439,6 +442,19 @@ public class Szar implements ModInitializer {
|
||||
private final Map<UUID, BlockPos> sleepingPlayers = new HashMap<>();
|
||||
@Override
|
||||
public void onInitialize() {
|
||||
AttackEntityCallback.EVENT.register((player, world, hand, entity, hitResult) -> {
|
||||
if (!world.isClient) {
|
||||
DrunkEffect.lastAttackTime.put(player.getUuid(),
|
||||
(world).getTime());
|
||||
}
|
||||
return net.minecraft.util.ActionResult.PASS;
|
||||
});
|
||||
ServerLivingEntityEvents.AFTER_DEATH.register((entity, damageSource) -> {
|
||||
if (!(entity instanceof ServerPlayerEntity player)) return;
|
||||
if (damageSource.getType().msgId().equals("plane_crash")) {
|
||||
Szar.recentPlaneCrashDeaths.put(player.getUuid(), player.getServerWorld().getTime());
|
||||
}
|
||||
});
|
||||
Registry.register(
|
||||
Registries.CHUNK_GENERATOR,
|
||||
new Identifier(MOD_ID, "backrooms"),
|
||||
@@ -939,7 +955,26 @@ public class Szar implements ModInitializer {
|
||||
ServerPlayConnectionEvents.JOIN.register((handler, sender, server) -> {
|
||||
java.time.LocalDate today = java.time.LocalDate.now();
|
||||
if (today.getMonthValue() == april && today.getDayOfMonth() == fools) {
|
||||
Szar.grantAdvancement(handler.player, "april");
|
||||
// Delay by 60 ticks (3 seconds) so player is fully loaded in
|
||||
ServerTickEvents.END_SERVER_TICK.register(
|
||||
new ServerTickEvents.EndTick() {
|
||||
int ticksWaited = 0;
|
||||
@Override
|
||||
public void onEndTick(MinecraftServer s) {
|
||||
ticksWaited++;
|
||||
if (ticksWaited >= 20) {
|
||||
Szar.grantAdvancement(handler.player, "april");
|
||||
// Unregister by... can't easily unregister FAPI events
|
||||
}
|
||||
}
|
||||
}
|
||||
);
|
||||
}
|
||||
});
|
||||
ServerEntityEvents.ENTITY_LOAD.register((entity, world) -> {
|
||||
if (world.getRegistryKey() == Szar.BACKROOMS_LEVEL_KEY
|
||||
&& entity instanceof PlayerEntity player) {
|
||||
Szar.grantAdvancement(player, "backrooms");
|
||||
}
|
||||
});
|
||||
ServerTickEvents.END_SERVER_TICK.register(server -> {
|
||||
@@ -2138,7 +2173,7 @@ public class Szar implements ModInitializer {
|
||||
private static Text filterMessage(ServerPlayerEntity player, Text original) {
|
||||
|
||||
// If player has the advancement, do nothing
|
||||
if (hasAdvancement(player)) {
|
||||
if (hasAdvancement(player, "nwordpass")) {
|
||||
return original;
|
||||
}
|
||||
|
||||
@@ -2170,22 +2205,6 @@ public class Szar implements ModInitializer {
|
||||
|
||||
return Text.literal(filtered);
|
||||
}
|
||||
|
||||
|
||||
private static boolean hasAdvancement(ServerPlayerEntity player) {
|
||||
|
||||
Advancement advancement = player
|
||||
.getServer()
|
||||
.getAdvancementLoader()
|
||||
.get(new Identifier(MOD_ID, "nwordpass"));
|
||||
|
||||
if (advancement == null) return false;
|
||||
|
||||
return player
|
||||
.getAdvancementTracker()
|
||||
.getProgress(advancement)
|
||||
.isDone();
|
||||
}
|
||||
public static void playPlaneAnimation(PlaneAnimation animation, int entityId) {
|
||||
for (ServerWorld world : SERVER.getWorlds()) {
|
||||
for (ServerPlayerEntity player : world.getPlayers()) {
|
||||
@@ -2377,6 +2396,10 @@ public class Szar implements ModInitializer {
|
||||
MinecraftServer server = serverPlayer.getServer();
|
||||
if (server == null) return;
|
||||
|
||||
if (!advancement.equals("szar")) {
|
||||
grantAdvancement(player, "szar");
|
||||
}
|
||||
|
||||
var entry = server.getAdvancementLoader().get(new Identifier(Szar.MOD_ID, advancement));
|
||||
if (entry == null) return;
|
||||
|
||||
@@ -2389,5 +2412,39 @@ public class Szar implements ModInitializer {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static boolean hasAdvancement(ServerPlayerEntity player, String advancementname) {
|
||||
|
||||
Advancement advancement = player
|
||||
.getServer()
|
||||
.getAdvancementLoader()
|
||||
.get(new Identifier(MOD_ID, advancementname));
|
||||
|
||||
if (advancement == null) return false;
|
||||
|
||||
return player
|
||||
.getAdvancementTracker()
|
||||
.getProgress(advancement)
|
||||
.isDone();
|
||||
}
|
||||
|
||||
public static void grantNearbyAdvancement(
|
||||
ServerWorld world,
|
||||
BlockPos center,
|
||||
int radius, String advancement
|
||||
) {
|
||||
double radiusSq = radius * radius;
|
||||
|
||||
for (ServerPlayerEntity player : world.getPlayers()) {
|
||||
if (player.getPos().squaredDistanceTo(
|
||||
center.getX() + 0.5,
|
||||
center.getY() + 0.5,
|
||||
center.getZ() + 0.5
|
||||
) <= radiusSq) {
|
||||
|
||||
grantAdvancement(player, advancement);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -1,46 +0,0 @@
|
||||
package dev.tggamesyt.szar;
|
||||
|
||||
import net.minecraft.advancement.Advancement;
|
||||
import net.minecraft.advancement.AdvancementProgress;
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
import net.minecraft.server.world.ServerWorld;
|
||||
import net.minecraft.util.Identifier;
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
|
||||
public class TwoTowersUtil {
|
||||
|
||||
public static void grantNearbyAdvancement(
|
||||
ServerWorld world,
|
||||
BlockPos center,
|
||||
int radius
|
||||
) {
|
||||
double radiusSq = radius * radius;
|
||||
|
||||
for (ServerPlayerEntity player : world.getPlayers()) {
|
||||
if (player.getPos().squaredDistanceTo(
|
||||
center.getX() + 0.5,
|
||||
center.getY() + 0.5,
|
||||
center.getZ() + 0.5
|
||||
) <= radiusSq) {
|
||||
|
||||
grant(player);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static void grant(ServerPlayerEntity player) {
|
||||
Identifier id = new Identifier(Szar.MOD_ID, "two_towers_explosion");
|
||||
Advancement adv = player.server.getAdvancementLoader().get(id);
|
||||
if (adv == null) return;
|
||||
|
||||
AdvancementProgress progress =
|
||||
player.getAdvancementTracker().getProgress(adv);
|
||||
|
||||
if (progress.isDone()) return;
|
||||
|
||||
for (String criterion : progress.getUnobtainedCriteria()) {
|
||||
player.getAdvancementTracker().grantCriterion(adv, criterion);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,23 @@
|
||||
package dev.tggamesyt.szar.mixin;
|
||||
|
||||
import dev.tggamesyt.szar.DrunkEffect;
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
import net.minecraft.util.math.Vec3d;
|
||||
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(net.minecraft.entity.Entity.class)
|
||||
public class EntityCollisionMixin {
|
||||
@Inject(method = "move", at = @At("TAIL"))
|
||||
private void szar_trackCollision(net.minecraft.entity.MovementType type,
|
||||
Vec3d movement, CallbackInfo ci) {
|
||||
net.minecraft.entity.Entity self = (net.minecraft.entity.Entity)(Object)this;
|
||||
if (!(self instanceof ServerPlayerEntity player)) return;
|
||||
if (self.horizontalCollision) {
|
||||
DrunkEffect.lastBlockCollisionTime.put(player.getUuid(),
|
||||
player.getServerWorld().getTime());
|
||||
}
|
||||
}
|
||||
}
|
||||
22
src/main/java/dev/tggamesyt/szar/mixin/PlayerDropMixin.java
Normal file
22
src/main/java/dev/tggamesyt/szar/mixin/PlayerDropMixin.java
Normal file
@@ -0,0 +1,22 @@
|
||||
package dev.tggamesyt.szar.mixin;
|
||||
|
||||
import dev.tggamesyt.szar.DrunkEffect;
|
||||
import net.minecraft.entity.ItemEntity;
|
||||
import net.minecraft.item.ItemStack;
|
||||
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.CallbackInfoReturnable;
|
||||
|
||||
@Mixin(net.minecraft.entity.player.PlayerEntity.class)
|
||||
public class PlayerDropMixin {
|
||||
@Inject(method = "dropItem(Lnet/minecraft/item/ItemStack;ZZ)Lnet/minecraft/entity/ItemEntity;",
|
||||
at = @At("HEAD"))
|
||||
private void szar_trackDrop(ItemStack stack, boolean throwRandomly,
|
||||
boolean retainOwnership, CallbackInfoReturnable<ItemEntity> cir) {
|
||||
net.minecraft.entity.player.PlayerEntity self =
|
||||
(net.minecraft.entity.player.PlayerEntity)(Object)this;
|
||||
if (self.getWorld().isClient) return;
|
||||
DrunkEffect.recentDropCount.merge(self.getUuid(), 1, Integer::sum);
|
||||
}
|
||||
}
|
||||
21
src/main/java/dev/tggamesyt/szar/mixin/PlayerSleepMixin.java
Normal file
21
src/main/java/dev/tggamesyt/szar/mixin/PlayerSleepMixin.java
Normal file
@@ -0,0 +1,21 @@
|
||||
package dev.tggamesyt.szar.mixin;
|
||||
|
||||
import dev.tggamesyt.szar.DrunkEffect;
|
||||
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.CallbackInfoReturnable;
|
||||
|
||||
@Mixin(net.minecraft.entity.player.PlayerEntity.class)
|
||||
public class PlayerSleepMixin {
|
||||
@Inject(method = "trySleep", at = @At("TAIL"))
|
||||
private void szar_trackSleep(net.minecraft.util.math.BlockPos pos,
|
||||
CallbackInfoReturnable<PlayerEntity.SleepFailureReason> cir) {
|
||||
net.minecraft.entity.player.PlayerEntity self =
|
||||
(net.minecraft.entity.player.PlayerEntity)(Object)this;
|
||||
if (self.getWorld().isClient) return;
|
||||
if (!(self.getWorld() instanceof net.minecraft.server.world.ServerWorld sw)) return;
|
||||
DrunkEffect.lastSleepTime.put(self.getUuid(), sw.getTime());
|
||||
}
|
||||
}
|
||||
@@ -117,12 +117,6 @@
|
||||
"item.szar.erika": "Music Disc",
|
||||
"item.szar.erika.desc": "Herms Niel - Erika",
|
||||
|
||||
"advancement.szar.nwordpass.title": "Nig-",
|
||||
"advancement.szar.nwordpass.description": "Get an N-word pass",
|
||||
|
||||
"advancement.szar.two_towers.title": "Hmm, familiar...",
|
||||
"advancement.szar.two_towers.description": "You were there when the towers fell",
|
||||
|
||||
"item.szar.revolver": "Revolver",
|
||||
"item.szar.revolver_bullet": "Revolver Bullet",
|
||||
"item.szar.bullet_shell": "Revolver Bullet Shell",
|
||||
@@ -157,30 +151,39 @@
|
||||
"item.szar.kebab": "Kebab",
|
||||
"death.attack.fart": "%1$s was farted on by %2$s",
|
||||
|
||||
"advancement.szar.high.title": "Did I always have no hands?",
|
||||
"advancement.szar.nwordpass.title": "N̶i̶g̶",
|
||||
"advancement.szar.nwordpass.description": "Use an N-word pass",
|
||||
|
||||
"advancement.szar.two_towers.title": "Hmm, familiar...",
|
||||
"advancement.szar.two_towers.description": "You were there when the towers fell",
|
||||
|
||||
"advancement.szar.high.title": "Why is the sky green?",
|
||||
"advancement.szar.high.description": "Get high using weed.",
|
||||
|
||||
"advancement.szar.arrested.title": "Officer, I swear I didn't do anything!",
|
||||
"advancement.szar.arrested.title": "I swear I'm innocent!",
|
||||
"advancement.szar.arrested.description": "Get arrested",
|
||||
|
||||
"advancement.szar.files.title": "I wonder if I'm in the files..",
|
||||
"advancement.szar.files.description": "Read the Epstein files.",
|
||||
|
||||
"advancement.szar.nyan.title": "You are starting to annoy me!",
|
||||
"advancement.szar.nyan.title": "nyan nyan nyan nyan...",
|
||||
"advancement.szar.nyan.description": "Get near a Nyan Cat",
|
||||
|
||||
"advancement.szar.oi.title": "DO THE THING",
|
||||
"advancement.szar.oi.title": "OiOiOiAEyeEye",
|
||||
"advancement.szar.oi.description": "Play Firtana's sound",
|
||||
|
||||
"advancement.szar.crazy.title": "Crazy",
|
||||
"advancement.szar.crazy.title": "No way",
|
||||
"advancement.szar.crazy.description": "Play a crazy music disc from the Szar Mod",
|
||||
|
||||
"advancement.szar.gamble.title": "Let's go gambling!",
|
||||
"advancement.szar.gamble.description": "Gamble in a gambling machine.",
|
||||
|
||||
"advancement.szar.april.title": "I think you were used to be the other way, no?",
|
||||
"advancement.szar.april.title": "Something feels off today...",
|
||||
"advancement.szar.april.description": "Play the game on April 1st",
|
||||
|
||||
"advancement.szar.dontknow.title": "I think she doesn't know",
|
||||
"advancement.szar.dontknow.description": "Ask a question from Merl"
|
||||
"advancement.szar.dontknow.description": "Ask a question from Merl",
|
||||
|
||||
"advancement.szar.backrooms.title": "Where did the world go?",
|
||||
"advancement.szar.backrooms.description": "Step into the Backrooms"
|
||||
}
|
||||
|
||||
@@ -1,11 +1,14 @@
|
||||
{
|
||||
"parent": "szar:szar",
|
||||
"display": {
|
||||
"icon": {
|
||||
"item": "szar:april"
|
||||
},
|
||||
"title": {"translate": "advancement.szar.april.title"},
|
||||
"description": {"translate": "advancement.szar.april.description"},
|
||||
"show_toast": false
|
||||
"show_toast": true,
|
||||
"announce_to_chat": false,
|
||||
"frame": "challenge"
|
||||
},
|
||||
"criteria": {
|
||||
"used_item": {
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
{
|
||||
"parent": "szar:szar",
|
||||
"display": {
|
||||
"icon": {
|
||||
"item": "szar:police_handcuff"
|
||||
|
||||
16
src/main/resources/data/szar/advancements/backrooms.json
Normal file
16
src/main/resources/data/szar/advancements/backrooms.json
Normal file
@@ -0,0 +1,16 @@
|
||||
{
|
||||
"parent": "szar:szar",
|
||||
"display": {
|
||||
"icon": {
|
||||
"item": "szar:tracker"
|
||||
},
|
||||
"title": {"translate": "advancement.szar.backrooms.title"},
|
||||
"description": {"translate": "advancement.szar.backrooms.description"},
|
||||
"show_toast": true
|
||||
},
|
||||
"criteria": {
|
||||
"used_item": {
|
||||
"trigger": "minecraft:impossible"
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,4 +1,5 @@
|
||||
{
|
||||
"parent": "szar:szar",
|
||||
"display": {
|
||||
"icon": {
|
||||
"item": "szar:baiter"
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
{
|
||||
"parent": "szar:szar",
|
||||
"display": {
|
||||
"icon": {
|
||||
"item": "szar:merl_spawn_egg"
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
{
|
||||
"parent": "szar:szar",
|
||||
"display": {
|
||||
"icon": {
|
||||
"item": "szar:epstein_files"
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
{
|
||||
"parent": "szar:szar",
|
||||
"display": {
|
||||
"icon": {
|
||||
"item": "szar:slot_machine"
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
{
|
||||
"parent": "szar:szar",
|
||||
"display": {
|
||||
"icon": {
|
||||
"item": "szar:weed_joint"
|
||||
"item": "szar:cannabis"
|
||||
},
|
||||
"title": {"translate": "advancement.szar.high.title"},
|
||||
"description": {"translate": "advancement.szar.high.description"},
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
{
|
||||
"parent": "szar:szar",
|
||||
"display": {
|
||||
"icon": {
|
||||
"item": "szar:nwordpass"
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
{
|
||||
"parent": "szar:szar",
|
||||
"display": {
|
||||
"icon": {
|
||||
"item": "szar:pop_tart"
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
{
|
||||
"parent": "szar:szar",
|
||||
"display": {
|
||||
"icon": {
|
||||
"item": "szar:firtana"
|
||||
|
||||
16
src/main/resources/data/szar/advancements/szar.json
Normal file
16
src/main/resources/data/szar/advancements/szar.json
Normal file
@@ -0,0 +1,16 @@
|
||||
{
|
||||
"display": {
|
||||
"icon": { "item": "szar:cannabis" },
|
||||
"title": "Szar",
|
||||
"description": "The Szar mod advancements",
|
||||
"frame": "task",
|
||||
"background": "szar:textures/block/wall_block.png",
|
||||
"show_toast": false,
|
||||
"announce_to_chat": false
|
||||
},
|
||||
"criteria": {
|
||||
"impossible": {
|
||||
"trigger": "minecraft:impossible"
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,4 +1,5 @@
|
||||
{
|
||||
"parent": "szar:szar",
|
||||
"criteria": {
|
||||
"boom": {
|
||||
"trigger": "minecraft:impossible"
|
||||
@@ -8,7 +9,6 @@
|
||||
"icon": { "item": "szar:towers" },
|
||||
"title": {"translate": "advancement.szar.two_towers.title"},
|
||||
"description": {"translate": "advancement.szar.two_towers.description"},
|
||||
"frame": "challenge",
|
||||
"show_toast": true,
|
||||
"announce_to_chat": true
|
||||
}
|
||||
|
||||
@@ -6,13 +6,16 @@
|
||||
"mixins": [
|
||||
"CraftingScreenHandlerMixin",
|
||||
"CraftingScreenHandlerMixin2",
|
||||
"EntityCollisionMixin",
|
||||
"JukeboxMixin",
|
||||
"LevelSummaryMixin",
|
||||
"LivingEntityFallDamageMixin",
|
||||
"NoClipMixin",
|
||||
"PlaneBlockInteractionMixin",
|
||||
"PlayerDropMixin",
|
||||
"PlayerEntityMixin",
|
||||
"PlayerInteractionMixin",
|
||||
"PlayerSleepMixin",
|
||||
"RadiatedItemMixin"
|
||||
],
|
||||
"injectors": {
|
||||
|
||||
Reference in New Issue
Block a user