forked from SteamWar/SteamWar
Turn reward touches into an unlockable Touch setting
Every entry gets a Touch setting next to its design, offering the 16 touches the rewards carried, each unlocked by its reward. The reward designs that the builder can now make are removed; only the underwater rain cloud and the medium, hard and advanced egg hunt designs stay. Reward requirements move to Unlocks, shared by touches, wing images and cosy smoke. The trail duration moves to the particle row to make room in the design row.
This commit is contained in:
@@ -116,6 +116,7 @@ PARTICLE_SLOT_COST = §7Particles per tick§8: §e{0}§8/§7{1}
|
||||
PARTICLE_ENTRY_EDITOR = §0{0}
|
||||
PARTICLE_ENTRY_DESIGN = §7Design§8: {0}
|
||||
PARTICLE_ENTRY_PARTICLE = §7Particle§8: {0}
|
||||
PARTICLE_ENTRY_TOUCH = §7Touch§8: {0}
|
||||
PARTICLE_ENTRY_LOCKED = §cDesign locked, not shown
|
||||
PARTICLE_ENTRY_COST = §7Particles per tick§8: §e{0}
|
||||
PARTICLE_ENTRY_COST_SHARE = §7This entry§8: §e{0}
|
||||
@@ -137,6 +138,7 @@ PARTICLE_DESIGN_WING = §fWings
|
||||
PARTICLE_DESIGN_CLOUD = §fCloud
|
||||
|
||||
PARTICLE_PARAM_PARTICLE = §fParticle
|
||||
PARTICLE_PARAM_TOUCH = §fTouch
|
||||
PARTICLE_PARAM_COUNT = §fAmount
|
||||
PARTICLE_PARAM_SPREAD_X = §fSpread X
|
||||
PARTICLE_PARAM_SPREAD_Y = §fSpread Y
|
||||
@@ -198,6 +200,27 @@ PARTICLE_CHOICE_IMAGE_SWORD = §fSword
|
||||
PARTICLE_CHOICE_IMAGE_BAT = §fBat
|
||||
PARTICLE_CHOICE_IMAGE_BUTTERFLY = §fButterfly
|
||||
PARTICLE_CHOICE_IMAGE_FAIRY = §fFairy
|
||||
PARTICLE_CHOICE_IMAGE_MWGL = §fMiniWarGear League
|
||||
PARTICLE_CHOICE_IMAGE_SW = §fSteamWar
|
||||
PARTICLE_CHOICE_IMAGE_WGS = §fWarGear Season
|
||||
PARTICLE_CHOICE_IMAGE_SWORD_CROSSED = §fCrossed Swords
|
||||
PARTICLE_CHOICE_TOUCH_NONE = §7None
|
||||
PARTICLE_CHOICE_TOUCH_JUMP_CLOUD = §fCloud puff on jumping
|
||||
PARTICLE_CHOICE_TOUCH_JUMP_WINGS = §5Wing beat on jumping
|
||||
PARTICLE_CHOICE_TOUCH_LANDING_SPLASH = §bSplash on landing
|
||||
PARTICLE_CHOICE_TOUCH_CRASH_LANDING = §cCrash landing
|
||||
PARTICLE_CHOICE_TOUCH_LAVA_LANDING = §6Lava on landing
|
||||
PARTICLE_CHOICE_TOUCH_OBSIDIAN_LANDING = §5Obsidian tears on landing
|
||||
PARTICLE_CHOICE_TOUCH_GLYPH_BURST = §dGlyph burst on sneaking
|
||||
PARTICLE_CHOICE_TOUCH_WET_FOOTPRINTS = §bWet footprints
|
||||
PARTICLE_CHOICE_TOUCH_CLOUD_FOOTPRINTS = §fCloud footprints
|
||||
PARTICLE_CHOICE_TOUCH_BLOSSOM_FOOTPRINTS = §aBlossom footprints
|
||||
PARTICLE_CHOICE_TOUCH_WATER_LINK = §bWater link to others with it
|
||||
PARTICLE_CHOICE_TOUCH_BUBBLE_LINK = §3Bubble link to others with it
|
||||
PARTICLE_CHOICE_TOUCH_GLYPH_PULL = §dGlyphs while standing still
|
||||
PARTICLE_CHOICE_TOUCH_STILL_SHIMMER = §3Shimmer while standing still
|
||||
PARTICLE_CHOICE_TOUCH_HEARTBEAT = §cHeartbeat while standing still
|
||||
PARTICLE_CHOICE_TOUCH_DECEMBER_SNOW = §fSnow in December
|
||||
PARTICLE_CHOICE_COLORING_OVER_TIME = §fChange over time
|
||||
PARTICLE_CHOICE_COLORING_ALONG_WING = §fFrom the back to the tips
|
||||
PARTICLE_CHOICE_MOTION_NONE = §fNone
|
||||
@@ -373,21 +396,11 @@ PARTICLE_TEAM_PULSE_LOGO = §fPulse Logo
|
||||
PARTICLE_TEAM_PULSE_HEART_BEAT = §cHeart Beat
|
||||
|
||||
PARTICLE_EVENT_ENCHANTING = §cEnchantment
|
||||
PARTICLE_EVENT_CLOUD = §fClouds
|
||||
PARTICLE_EVENT_SMOKE = §7Smoke
|
||||
PARTICLE_EVENT_WATER = §bWater
|
||||
PARTICLE_EVENT_LAVA = §cLava
|
||||
PARTICLE_EVENT_WINGS = §fWings
|
||||
PARTICLE_EVENT_RAIN_CLOUD = §fRandom Raincloud
|
||||
PARTICLE_EVENT_WGS = §fWGS
|
||||
PARTICLE_EVENT_WARGEARCLASH = §fClash
|
||||
|
||||
PARTICLE_EGG_HUNT_EASY = §aGreenery
|
||||
PARTICLE_EGG_HUNT_MEDIUM = §eHide and Seek
|
||||
PARTICLE_EGG_HUNT_HARD = §cOrbit
|
||||
PARTICLE_EGG_HUNT_EXTREME = §5Purple rain
|
||||
PARTICLE_EGG_HUNT_ADVANCED = §5Lift off
|
||||
PARTICLE_EGG_HUNT_HALF = §fThe hunt is on
|
||||
|
||||
JUMP_AND_RUN_PROGRESS = §e{0}§8/§f{1} §c{2} §7{3}
|
||||
JUMP_AND_RUN_CANCEL = {0}
|
||||
|
||||
@@ -116,6 +116,7 @@ PARTICLE_SLOT_COST = §7Partikel pro Tick§8: §e{0}§8/§7{1}
|
||||
PARTICLE_ENTRY_EDITOR = §0{0}
|
||||
PARTICLE_ENTRY_DESIGN = §7Design§8: {0}
|
||||
PARTICLE_ENTRY_PARTICLE = §7Partikel§8: {0}
|
||||
PARTICLE_ENTRY_TOUCH = §7Akzent§8: {0}
|
||||
PARTICLE_ENTRY_LOCKED = §cDesign gesperrt, wird nicht angezeigt
|
||||
PARTICLE_ENTRY_COST = §7Partikel pro Tick§8: §e{0}
|
||||
PARTICLE_ENTRY_COST_SHARE = §7Dieser Eintrag§8: §e{0}
|
||||
@@ -137,6 +138,7 @@ PARTICLE_DESIGN_WING = §fFlügel
|
||||
PARTICLE_DESIGN_CLOUD = §fWolke
|
||||
|
||||
PARTICLE_PARAM_PARTICLE = §fPartikel
|
||||
PARTICLE_PARAM_TOUCH = §fAkzent
|
||||
PARTICLE_PARAM_COUNT = §fAnzahl
|
||||
PARTICLE_PARAM_SPREAD_X = §fStreuung X
|
||||
PARTICLE_PARAM_SPREAD_Y = §fStreuung Y
|
||||
@@ -198,6 +200,27 @@ PARTICLE_CHOICE_IMAGE_SWORD = §fSchwert
|
||||
PARTICLE_CHOICE_IMAGE_BAT = §fFledermaus
|
||||
PARTICLE_CHOICE_IMAGE_BUTTERFLY = §fSchmetterling
|
||||
PARTICLE_CHOICE_IMAGE_FAIRY = §fFee
|
||||
PARTICLE_CHOICE_IMAGE_MWGL = §fMiniWarGear Liga
|
||||
PARTICLE_CHOICE_IMAGE_SW = §fSteamWar
|
||||
PARTICLE_CHOICE_IMAGE_WGS = §fWarGear Saison
|
||||
PARTICLE_CHOICE_IMAGE_SWORD_CROSSED = §fGekreuzte Schwerter
|
||||
PARTICLE_CHOICE_TOUCH_NONE = §7Keiner
|
||||
PARTICLE_CHOICE_TOUCH_JUMP_CLOUD = §fWolke beim Springen
|
||||
PARTICLE_CHOICE_TOUCH_JUMP_WINGS = §5Flügelschlag beim Springen
|
||||
PARTICLE_CHOICE_TOUCH_LANDING_SPLASH = §bSpritzer beim Landen
|
||||
PARTICLE_CHOICE_TOUCH_CRASH_LANDING = §cBruchlandung
|
||||
PARTICLE_CHOICE_TOUCH_LAVA_LANDING = §6Lava beim Landen
|
||||
PARTICLE_CHOICE_TOUCH_OBSIDIAN_LANDING = §5Obsidiantränen beim Landen
|
||||
PARTICLE_CHOICE_TOUCH_GLYPH_BURST = §dGlyphen beim Schleichen
|
||||
PARTICLE_CHOICE_TOUCH_WET_FOOTPRINTS = §bNasse Fußspuren
|
||||
PARTICLE_CHOICE_TOUCH_CLOUD_FOOTPRINTS = §fWolkenfußspuren
|
||||
PARTICLE_CHOICE_TOUCH_BLOSSOM_FOOTPRINTS = §aBlütenfußspuren
|
||||
PARTICLE_CHOICE_TOUCH_WATER_LINK = §bWasserband zu anderen damit
|
||||
PARTICLE_CHOICE_TOUCH_BUBBLE_LINK = §3Blasenband zu anderen damit
|
||||
PARTICLE_CHOICE_TOUCH_GLYPH_PULL = §dGlyphen im Stillstand
|
||||
PARTICLE_CHOICE_TOUCH_STILL_SHIMMER = §3Schimmer im Stillstand
|
||||
PARTICLE_CHOICE_TOUCH_HEARTBEAT = §cHerzschlag im Stillstand
|
||||
PARTICLE_CHOICE_TOUCH_DECEMBER_SNOW = §fSchnee im Dezember
|
||||
PARTICLE_CHOICE_COLORING_OVER_TIME = §fWechseln mit der Zeit
|
||||
PARTICLE_CHOICE_COLORING_ALONG_WING = §fVom Rücken zu den Spitzen
|
||||
PARTICLE_CHOICE_MOTION_NONE = §fKeine
|
||||
@@ -362,21 +385,11 @@ PARTICLE_PLAYER_10697_AURA = §7Rauchgranate
|
||||
PARTICLE_TEAM_PULSE_HEART_BEAT = §cHerzschlag
|
||||
|
||||
PARTICLE_EVENT_ENCHANTING = §cVerzaubert
|
||||
PARTICLE_EVENT_CLOUD = §fWolken
|
||||
PARTICLE_EVENT_SMOKE = §7Rauch
|
||||
PARTICLE_EVENT_WATER = §bWasser
|
||||
PARTICLE_EVENT_LAVA = §cLava
|
||||
PARTICLE_EVENT_WINGS = §fFlügel
|
||||
PARTICLE_EVENT_RAIN_CLOUD = §fRegenwolke
|
||||
PARTICLE_EVENT_WGS = §fWGS
|
||||
PARTICLE_EVENT_WARGEARCLASH = §fClash
|
||||
|
||||
PARTICLE_EGG_HUNT_EASY = §aGrünplfanzen
|
||||
PARTICLE_EGG_HUNT_MEDIUM = §eVersteckspiel
|
||||
PARTICLE_EGG_HUNT_HARD = §cOrbit
|
||||
PARTICLE_EGG_HUNT_EXTREME = §5Lila regen
|
||||
PARTICLE_EGG_HUNT_ADVANCED = §5Abheben
|
||||
PARTICLE_EGG_HUNT_HALF = §fDie Jagd ist eröffnet
|
||||
|
||||
JUMP_AND_RUN_FINISHED = §aBeendet in {0} mit {1} Fails
|
||||
JUMP_AND_RUN_PERSONAL_BEST = §aNice! Du hast deinen Rekord um {0} verbessert!
|
||||
|
||||
@@ -75,10 +75,10 @@ public class Designs {
|
||||
new ChoiceParameter.Choice<>("butterfly", WingShape.drawn(DrawnWings.BUTTERFLY, Material.PINK_PETALS), false),
|
||||
new ChoiceParameter.Choice<>("fairy", WingShape.drawn(DrawnWings.FAIRY, Material.ALLAY_SPAWN_EGG), false),
|
||||
// Tournament wing images, unlocked by the placement that earns their reward
|
||||
new ChoiceParameter.Choice<>("mwgl", WingShape.image(WingDesign.MWGL, Material.IRON_SWORD), false, () -> RewardDesigns.EVENT_PLACEMENT_MINI_WARGEAR_LIGA.getRequirement()),
|
||||
new ChoiceParameter.Choice<>("sw", WingShape.image(WingDesign.SW, Material.CYAN_CARPET), false, () -> RewardDesigns.EVENT_PLACEMENT_UNDERWATER_MWG.getRequirement()),
|
||||
new ChoiceParameter.Choice<>("wgs", WingShape.image(WingDesign.WGS, Material.DIAMOND_HELMET), false, () -> RewardDesigns.EVENT_PLACEMENT_WARGEAR_SEASON_2022.getRequirement()),
|
||||
new ChoiceParameter.Choice<>("sword_crossed", WingShape.image(WingDesign.SWORD_CROSSED, Material.GOLDEN_SWORD), false, () -> RewardDesigns.EVENT_PLACEMENT_WARGEAR_CLASH.getRequirement()),
|
||||
new ChoiceParameter.Choice<>("mwgl", WingShape.image(WingDesign.MWGL, Material.IRON_SWORD), false, Unlocks.MINI_WARGEAR_LIGA_PLACEMENT),
|
||||
new ChoiceParameter.Choice<>("sw", WingShape.image(WingDesign.SW, Material.CYAN_CARPET), false, Unlocks.UNDERWATER_MWG_PLACEMENT),
|
||||
new ChoiceParameter.Choice<>("wgs", WingShape.image(WingDesign.WGS, Material.DIAMOND_HELMET), false, Unlocks.WARGEAR_SEASON_2022_PLACEMENT),
|
||||
new ChoiceParameter.Choice<>("sword_crossed", WingShape.image(WingDesign.SWORD_CROSSED, Material.GOLDEN_SWORD), false, Unlocks.WARGEAR_CLASH_PLACEMENT),
|
||||
new ChoiceParameter.Choice<>("eclipse", WingShape.image(WingDesign.ECLIPSE), true),
|
||||
new ChoiceParameter.Choice<>("pl", WingShape.image(WingDesign.PL), true),
|
||||
new ChoiceParameter.Choice<>("plompa_easter", WingShape.image(WingDesign.PlompaEasterWings), true),
|
||||
|
||||
@@ -204,8 +204,10 @@ public class EntryParameters {
|
||||
public final ChoiceParameter<Sneak> SNEAK = ChoiceParameter.ofEnum("sneak", "PARTICLE_PARAM_SNEAK", Sneak.ANY);
|
||||
public final ChoiceParameter<Visibility> VISIBILITY = ChoiceParameter.ofEnum("visibility", "PARTICLE_PARAM_VISIBILITY", Visibility.EVERYONE);
|
||||
|
||||
public final ChoiceParameter<Touch> TOUCH = new ChoiceParameter<>("touch", "PARTICLE_PARAM_TOUCH", Touches.NONE, Touches.choices());
|
||||
|
||||
public final List<Parameter<?>> ALL = List.of(
|
||||
PARTICLE, COUNT, SPREAD_X, SPREAD_Y, SPREAD_Z, SPEED, COLORS, BLOCK,
|
||||
TOUCH, PARTICLE, COUNT, SPREAD_X, SPREAD_Y, SPREAD_Z, SPEED, COLORS, BLOCK,
|
||||
TRAIL_DURATION, TRAIL_TARGET_X, TRAIL_TARGET_Y, TRAIL_TARGET_Z,
|
||||
OFFSET_X, OFFSET_Y, OFFSET_Z, PLACEMENT, INTERVAL, TICK_MODE,
|
||||
MOVEMENT, GLIDING, GROUND, SNEAK, VISIBILITY
|
||||
|
||||
@@ -32,8 +32,6 @@ public class FixedDesign extends ParticleDesign {
|
||||
private final int points;
|
||||
private final Consumer<ParameterValues> defaults;
|
||||
private final Supplier<ParticleElement> shape;
|
||||
private Supplier<ParticleElement> touch;
|
||||
private int touchPoints;
|
||||
|
||||
public FixedDesign(String id, Material icon, String nameKey, ParticleRequirement requirement, int points, Consumer<ParameterValues> defaults, Supplier<ParticleElement> shape) {
|
||||
super(id, icon, nameKey, DesignVisibility.REWARD, requirement);
|
||||
@@ -47,21 +45,9 @@ public class FixedDesign extends ParticleDesign {
|
||||
return shape.get();
|
||||
}
|
||||
|
||||
// Adds the reward's unique touch; its points count towards the slot budget
|
||||
public FixedDesign withTouch(int touchPoints, Supplier<ParticleElement> touch) {
|
||||
this.touchPoints = touchPoints;
|
||||
this.touch = touch;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ParticleElement touch() {
|
||||
return touch == null ? null : touch.get();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int points(ParameterValues values) {
|
||||
return points + touchPoints;
|
||||
return points;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -72,11 +72,6 @@ public abstract class ParticleDesign {
|
||||
return false;
|
||||
}
|
||||
|
||||
// An extra the builder cannot make, shown next to the design's look and checked every tick so it never misses
|
||||
// a jump or landing; null for designs without one
|
||||
public ParticleElement touch() {
|
||||
return null;
|
||||
}
|
||||
|
||||
// Called after a design setting changed, to adjust others that depend on it
|
||||
public void adjust(Parameter<?> changed, ParameterValues values) {
|
||||
|
||||
@@ -185,7 +185,7 @@ public enum ParticleType {
|
||||
public ParticleRequirement getRequirement() {
|
||||
return switch (this) {
|
||||
case CHERRY_LEAVES, PALE_OAK_LEAVES, TINTED_LEAVES -> ParticleRequirement.SERVER_TEAM;
|
||||
case CAMPFIRE_COSY_SMOKE -> RewardDesigns.EVENT_PARTICIPATION_HELLS_BELLS.getRequirement();
|
||||
case CAMPFIRE_COSY_SMOKE -> Unlocks.HELLS_BELLS.get();
|
||||
default -> ParticleRequirement.NO_REQUIRMENT;
|
||||
};
|
||||
}
|
||||
|
||||
@@ -19,107 +19,26 @@
|
||||
|
||||
package de.steamwar.lobby.particle.design;
|
||||
|
||||
import de.steamwar.lobby.particle.Gradient;
|
||||
import de.steamwar.lobby.particle.ParticleElement;
|
||||
import de.steamwar.lobby.particle.ParticleRequirement;
|
||||
import de.steamwar.lobby.particle.WingDesign;
|
||||
import de.steamwar.lobby.particle.elements.*;
|
||||
import de.steamwar.lobby.particle.elements.custom.HearthBeat;
|
||||
import de.steamwar.lobby.particle.elements.custom.NonMoving;
|
||||
import de.steamwar.lobby.particle.elements.custom.PulseShimmer;
|
||||
import de.steamwar.lobby.particle.elements.touch.*;
|
||||
import lombok.experimental.UtilityClass;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.Particle;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.util.Vector;
|
||||
|
||||
import java.time.Month;
|
||||
import java.util.List;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import static de.steamwar.lobby.particle.design.EntryParameters.*;
|
||||
|
||||
// Designs earned in tournaments, events and the Easter egg hunt. Rewards whose look the basic designs can build get a
|
||||
// touch the builder cannot make: bursts on jumping, landing or sneaking, footprints, a link to team-mates, a seasonal
|
||||
// extra, a preset-only shape or aimed glyphs.
|
||||
// Reward designs the builder cannot make. Other rewards unlock ingredients instead: wing images, particles and touches.
|
||||
@UtilityClass
|
||||
public class RewardDesigns {
|
||||
|
||||
private final Consumer<ParameterValues> MOVE = values -> {
|
||||
};
|
||||
private final Consumer<ParameterValues> ALWAYS = values -> values.set(TICK_MODE, TickMode.ALWAYS);
|
||||
private final Consumer<ParameterValues> WINGS = values -> values
|
||||
.set(TICK_MODE, TickMode.ALWAYS)
|
||||
.set(INTERVAL, 20)
|
||||
.set(GLIDING, Gliding.NOT_GLIDING);
|
||||
|
||||
public final ParticleDesign EVENT_PLACEMENT_WARGEAR_SEASON = new FixedDesign("event_placement_wargear_season", Material.ENCHANTING_TABLE, "PARTICLE_EVENT_ENCHANTING",
|
||||
ParticleRequirement.eventPlacement(22, 12, 285, 54), 5, MOVE,
|
||||
() -> new Cloud(new Circle(new LocationMutator(new SimpleParticle(Particle.ENCHANT, 0, 0, 0, 0.01), 0, 1.1, 0))))
|
||||
.withTouch(3, () -> new NonMoving(new Glyphs(Glyphs.Path.INTO_PLAYER, 3, 1.5)));
|
||||
public final ParticleDesign EVENT_PLACEMENT_AIRSHIP = new FixedDesign("event_placement_airship", Material.SNOWBALL, "PARTICLE_EVENT_CLOUD",
|
||||
ParticleRequirement.eventPlacement(26, 205, 9, 54, 120, 292), 5, MOVE,
|
||||
() -> new Circle(new LocationMutator(new SimpleParticle(Particle.CLOUD, 0, 0, 0, 0.01), 0, 2.2, 0)))
|
||||
.withTouch(1, () -> new EventBurst(EventBurst.Trigger.JUMP, new SimpleParticle(Particle.CLOUD, 0.3F, 0.05F, 0.3F, 0.02, 12)));
|
||||
public final ParticleDesign EVENT_PLACEMENT_HELLS_BELLS = new FixedDesign("event_placement_hells_bells", Material.TNT_MINECART, "PARTICLE_EVENT_SMOKE",
|
||||
ParticleRequirement.eventPlacement(28, 205, 9, 11), 5, MOVE,
|
||||
() -> new Cloud(new Circle(new LocationMutator(new SimpleParticle(Particle.CAMPFIRE_COSY_SMOKE, 0, 0, 0, 0.01), 0, 2.2, 0))));
|
||||
public final ParticleDesign EVENT_PLACEMENT_UNDERWATER = new FixedDesign("event_placement_underwater", Material.PRISMARINE_SHARD, "PARTICLE_EVENT_WATER",
|
||||
ParticleRequirement.eventPlacement(31, 9, 210, 520), 5, MOVE,
|
||||
() -> new Cloud(new SimpleParticle(Particle.DRIPPING_WATER)))
|
||||
.withTouch(1, () -> new EventBurst(EventBurst.Trigger.LAND, 1, new Ring(new SimpleParticle(Particle.SPLASH, 0, 0, 0, 0, 3), 1, 16)));
|
||||
public final ParticleDesign EVENT_PLACEMENT_ADVENT_WAR_SHIP = new FixedDesign("event_placement_advent_war_ship", Material.PRISMARINE_CRYSTALS, "PARTICLE_EVENT_WATER",
|
||||
ParticleRequirement.eventPlacement(32, 9, 205, 210), 10, ALWAYS,
|
||||
() -> new LocationMutator(new Circle(new Group(new SimpleParticle(Particle.DRIPPING_WATER), new SimpleParticle(Particle.UNDERWATER, 0.2F, 0.2F, 0.2F, 0.01))), 0, 1.1, 0))
|
||||
.withTouch(4, () -> new Footprints(new SimpleParticle(Particle.FISHING, 0.05F, 0, 0.05F, 0, 1), 40));
|
||||
public final ParticleDesign EVENT_PLACEMENT_MINI_WARGEAR_LIGA = wings("event_placement_mini_wargear_liga", Material.IRON_SWORD, "PARTICLE_EVENT_WINGS",
|
||||
ParticleRequirement.eventPlacement(33, 9, 34, 205), Particle.UNDERWATER, 0.15, WingDesign.MWGL);
|
||||
public final ParticleDesign EVENT_PLACEMENT_ABSTURZ = wings("event_placement_absturz", Material.FEATHER, "PARTICLE_EVENT_WINGS",
|
||||
ParticleRequirement.eventPlacement(34, 210, 205, 527, 286), Particle.CRIT, 0.15, WingDesign.SIMPLE)
|
||||
.withTouch(1, () -> new EventBurst(EventBurst.Trigger.LAND, 3, new Group(new SimpleParticle(Particle.EXPLOSION, 0, 0, 0, 0, 1),
|
||||
new Ring(new SimpleParticle(Particle.CRIT, 0, 0.1F, 0, 0.1, 2), 1.2, 16))));
|
||||
public final ParticleDesign EVENT_PLACEMENT_UNDERWATER_MWG = wings("event_placement_underwater_mwg", Material.CYAN_CARPET, "PARTICLE_EVENT_RAIN_CLOUD",
|
||||
ParticleRequirement.eventPlacement(35, 9, 210), Particle.CRIT, 0.15, WingDesign.SW);
|
||||
public final ParticleDesign EVENT_PLACEMENT_WARGEAR_SEASON_2022 = wings("event_placement_wargear_season_2022", Material.DIAMOND_HELMET, "PARTICLE_EVENT_WGS",
|
||||
ParticleRequirement.eventPlacement(37, 285, 210, 122), Particle.FIREWORK, 0.15, WingDesign.WGS);
|
||||
public final ParticleDesign EVENT_PLACEMENT_WARGEAR_CLASH = wings("event_placement_wargear_clash", Material.GOLDEN_SWORD, "PARTICLE_EVENT_WARGEARCLASH",
|
||||
ParticleRequirement.eventPlacement(38, 210, 158, 167, 286), Particle.CRIT, 0.1, WingDesign.SWORD_CROSSED);
|
||||
|
||||
// For taking part in any event
|
||||
public final ParticleDesign EVENT_PARTICIPATION_WATER = new FixedDesign("event_participation_water", Material.WATER_BUCKET, "PARTICLE_EVENT_WATER",
|
||||
ParticleRequirement.EVENT_PARTICIPATION, 5, ALWAYS,
|
||||
() -> new Circle(new LocationMutator(new SimpleParticle(Particle.DRIPPING_WATER), 0, 1.1, 0)))
|
||||
.withTouch(5, () -> new TeamLink("event_participation_water", new SimpleParticle(Particle.DRIPPING_WATER, 0, 0, 0, 0, 1)));
|
||||
public final ParticleDesign EVENT_PARTICIPATION_LAVA = new FixedDesign("event_participation_lava", Material.LAVA_BUCKET, "PARTICLE_EVENT_LAVA",
|
||||
ParticleRequirement.EVENT_PARTICIPATION, 5, ALWAYS,
|
||||
() -> new Circle(new LocationMutator(new SimpleParticle(Particle.DRIPPING_LAVA), 0, 1.1, 0)))
|
||||
.withTouch(1, () -> new EventBurst(EventBurst.Trigger.LAND, 1, new Group(new SimpleParticle(Particle.LAVA, 0.2F, 0, 0.2F, 0, 4),
|
||||
new SimpleParticle(Particle.SMOKE, 0.2F, 0.1F, 0.2F, 0.02, 6))));
|
||||
|
||||
public final ParticleDesign EVENT_PARTICIPATION_WARGEAR_SEASON = new FixedDesign("event_participation_wargear_season", Material.BOOK, "PARTICLE_EVENT_ENCHANTING",
|
||||
ParticleRequirement.eventParticipation(22), 5, MOVE,
|
||||
() -> new SimpleParticle(Particle.ENCHANT))
|
||||
.withTouch(1, () -> new EventBurst(EventBurst.Trigger.SNEAK, new Glyphs(Glyphs.Path.OUT_OF_PLAYER, 16, 1.5)));
|
||||
public final ParticleDesign EVENT_PARTICIPATION_AIRSHIP = new FixedDesign("event_participation_airship", Material.SNOW_BLOCK, "PARTICLE_EVENT_CLOUD",
|
||||
ParticleRequirement.eventParticipation(26), 5, MOVE,
|
||||
() -> new SimpleParticle(Particle.CLOUD))
|
||||
.withTouch(4, () -> new Footprints(new SimpleParticle(Particle.CLOUD, 0.05F, 0, 0.05F, 0, 1), 40));
|
||||
public final ParticleDesign EVENT_PARTICIPATION_HELLS_BELLS = new FixedDesign("event_participation_hells_bells", Material.TNT, "PARTICLE_EVENT_SMOKE",
|
||||
ParticleRequirement.eventParticipation(28), 5, MOVE,
|
||||
() -> new Circle(new SimpleParticle(Particle.CAMPFIRE_COSY_SMOKE, 0, 0, 0, 0.01)));
|
||||
public final ParticleDesign EVENT_PARTICIPATION_UNDERWATER = new FixedDesign("event_participation_underwater", Material.PRISMARINE_BRICKS, "PARTICLE_EVENT_WATER",
|
||||
ParticleRequirement.eventParticipation(31), 5, MOVE,
|
||||
() -> new SimpleParticle(Particle.DRIPPING_WATER))
|
||||
.withTouch(5, () -> new TeamLink("event_participation_underwater", new SimpleParticle(Particle.DRIPPING_WATER, 0, 0, 0, 0, 1)));
|
||||
public final ParticleDesign EVENT_PARTICIPATION_ADVENT_WAR_SHIP = new FixedDesign("event_participation_advent_war_ship", Material.PRISMARINE_WALL, "PARTICLE_EVENT_WATER",
|
||||
ParticleRequirement.eventParticipation(32), 10, MOVE,
|
||||
() -> new Group(new SimpleParticle(Particle.DRIPPING_WATER), new SimpleParticle(Particle.UNDERWATER, 0.2F, 0.2F, 0.2F, 0.01)))
|
||||
.withTouch(2, () -> new Seasonal(Month.DECEMBER, new LocationMutator(new SimpleParticle(Particle.SNOWFLAKE, 1.2F, 0.3F, 1.2F, 0.01, 2), 0, 2.4, 0)));
|
||||
public final ParticleDesign EVENT_PARTICIPATION_MINI_WARGEAR_LIGA = new FixedDesign("event_participation_mini_wargear_liga", Material.PRISMARINE_SLAB, "PARTICLE_EVENT_WATER",
|
||||
ParticleRequirement.eventParticipation(33), 5, MOVE,
|
||||
() -> new Circle(new SimpleParticle(Particle.UNDERWATER, 0, 0, 0, 0)))
|
||||
.withTouch(3, () -> new NonMoving(new PulseShimmer(new SimpleParticle(Particle.UNDERWATER, 0, 0, 0, 0, 1), 80, 2)));
|
||||
public final ParticleDesign EVENT_PARTICIPATION_UNDERWATER_MWG = new FixedDesign("event_participation_underwater_mwg", Material.BLUE_CARPET, "PARTICLE_EVENT_RAIN_CLOUD",
|
||||
ParticleRequirement.eventParticipation(35), 15, ALWAYS,
|
||||
() -> new RandomParticle(
|
||||
@@ -136,25 +55,12 @@ public class RewardDesigns {
|
||||
rainCloud(null, Particle.SNOWFLAKE, 5),
|
||||
rainCloud(null, Particle.TOTEM_OF_UNDYING, 2)
|
||||
));
|
||||
public final ParticleDesign EVENT_PARTICIPATION_WARGEAR_SEASON_2022 = wings("event_participation_wargear_season_2022", Material.DIAMOND_SWORD, "PARTICLE_EVENT_WINGS",
|
||||
ParticleRequirement.eventParticipation(37), Particle.DRAGON_BREATH, 0.15, WingDesign.COMPLEX)
|
||||
.withTouch(2, () -> new Delayed(new Wing(new SimpleParticle(Particle.DRAGON_BREATH, 0, 0, 0, 0, 1), 0.15, WingDesign.COMPLEX, false, 100, Wing.Motion.JUMP_BEAT), 2));
|
||||
|
||||
public final ParticleDesign EGG_HUNT_EASY = new FixedDesign("egg_hunt_easy", Material.LIME_CONCRETE_POWDER, "PARTICLE_EGG_HUNT_EASY",
|
||||
ParticleRequirement.EGG_HUNT_EASY, 1, ALWAYS,
|
||||
() -> new LocationMutator(new SimpleParticle(Particle.FALLING_SPORE_BLOSSOM, 0.5F, 0.1f, 0.5F, 1, 1), 0, 2.2, 0))
|
||||
.withTouch(4, () -> new Footprints(new SimpleParticle(Particle.SPORE_BLOSSOM_AIR, 0.05F, 0, 0.05F, 0, 1), 40));
|
||||
public final ParticleDesign EGG_HUNT_MEDIUM = new FixedDesign("egg_hunt_medium", Material.YELLOW_CONCRETE_POWDER, "PARTICLE_EGG_HUNT_MEDIUM",
|
||||
ParticleRequirement.EGG_HUNT_MEDIUM, 5, ALWAYS.andThen(values -> values.set(GROUND, Ground.ON_GROUND).set(SNEAK, Sneak.SNEAKING)),
|
||||
() -> new SimpleParticle(Particle.GLOW_SQUID_INK, 0.4F, 0.9F, 0.4F, 0.01));
|
||||
public final ParticleDesign EGG_HUNT_HARD = new FixedDesign("egg_hunt_hard", Material.RED_CONCRETE_POWDER, "PARTICLE_EGG_HUNT_HARD",
|
||||
ParticleRequirement.EGG_HUNT_HARD, 2, ALWAYS,
|
||||
() -> new LocationMutator(new Circle(new DoubleCircle(new DustParticle(Particle.DUST, 0, 0, 0, 0.01, 1, null), new DustParticle(Particle.DUST, 0, 0, 0, 0.01, 1, null)), 0.8, 0.5), 0, 0.5, 0));
|
||||
public final ParticleDesign EGG_HUNT_EXTREME = new FixedDesign("egg_hunt_extreme", Material.PURPLE_CONCRETE_POWDER, "PARTICLE_EGG_HUNT_EXTREME",
|
||||
ParticleRequirement.EGG_HUNT_EXTREME, 1, ALWAYS,
|
||||
() -> new LocationMutator(new SimpleParticle(Particle.FALLING_OBSIDIAN_TEAR, 0.5F, 0.1F, 0.5F, 1, 1), 0, 2.2, 0))
|
||||
.withTouch(1, () -> new EventBurst(EventBurst.Trigger.LAND, 1, new Group(new Ring(new SimpleParticle(Particle.WITCH, 0, 0.05F, 0, 0, 2), 1, 16),
|
||||
new SimpleParticle(Particle.LANDING_OBSIDIAN_TEAR, 0.4F, 0, 0.4F, 0, 6))));
|
||||
public final ParticleDesign EGG_HUNT_ADVANCED = new FixedDesign("egg_hunt_advanced", Material.BLACK_CONCRETE_POWDER, "PARTICLE_EGG_HUNT_ADVANCED",
|
||||
ParticleRequirement.EGG_HUNT_ADVANCED, 2, ALWAYS.andThen(values -> values.set(SNEAK, Sneak.SNEAKING)),
|
||||
() -> new LocationMutator(new Group(
|
||||
@@ -165,19 +71,6 @@ public class RewardDesigns {
|
||||
player.setVelocity(player.getVelocity().add(new Vector(0, 0.1, 0)));
|
||||
}
|
||||
), 0, -0.2, 0));
|
||||
// Hearts above the head while sneaking on the ground, a heart cloud ring while in the air
|
||||
public final ParticleDesign EGG_HUNT_HALF = new FixedDesign("egg_hunt_half", Material.EGG, "PARTICLE_EGG_HUNT_HALF",
|
||||
ParticleRequirement.EGG_HUNT_FOUND_HALF, 5, ALWAYS,
|
||||
() -> new Group(
|
||||
new Sneaking(new Floor(new LocationMutator(new SimpleParticle(Particle.HEART, 0, 0, 0, 0.01), 0, 1.7, 0))),
|
||||
new NonFloor(new NonFlying(new LocationMutator(new Cloud(new Circle(new SimpleParticle(Particle.HEART, 0, 0, 0, 0.01))), 0, 0.5, 0)))
|
||||
))
|
||||
.withTouch(1, () -> new NonMoving(new HearthBeat(new DustParticle(Particle.DUST, 0, 0, 0, 0, 1, new Gradient(java.awt.Color.RED)), 80)));
|
||||
|
||||
private FixedDesign wings(String id, Material icon, String nameKey, ParticleRequirement requirement, Particle particle, double size, WingDesign wingDesign) {
|
||||
return new FixedDesign(id, icon, nameKey, requirement, wingDesign.getVectors().length, WINGS,
|
||||
() -> new Wing(new SimpleParticle(particle, 0, 0, 0, 0, 1), size, wingDesign));
|
||||
}
|
||||
|
||||
// A cloud above the head that drips the given particle; rain is an optional second particle inside the cloud
|
||||
private ParticleElement rainCloud(Particle rain, Particle drip, int dripCount) {
|
||||
@@ -188,15 +81,6 @@ public class RewardDesigns {
|
||||
}
|
||||
|
||||
public List<ParticleDesign> all() {
|
||||
return List.of(
|
||||
EVENT_PLACEMENT_WARGEAR_SEASON, EVENT_PLACEMENT_AIRSHIP, EVENT_PLACEMENT_HELLS_BELLS, EVENT_PLACEMENT_UNDERWATER,
|
||||
EVENT_PLACEMENT_ADVENT_WAR_SHIP, EVENT_PLACEMENT_MINI_WARGEAR_LIGA, EVENT_PLACEMENT_ABSTURZ, EVENT_PLACEMENT_UNDERWATER_MWG,
|
||||
EVENT_PLACEMENT_WARGEAR_SEASON_2022, EVENT_PLACEMENT_WARGEAR_CLASH,
|
||||
EVENT_PARTICIPATION_WATER, EVENT_PARTICIPATION_LAVA,
|
||||
EVENT_PARTICIPATION_WARGEAR_SEASON, EVENT_PARTICIPATION_AIRSHIP, EVENT_PARTICIPATION_HELLS_BELLS, EVENT_PARTICIPATION_UNDERWATER,
|
||||
EVENT_PARTICIPATION_ADVENT_WAR_SHIP, EVENT_PARTICIPATION_MINI_WARGEAR_LIGA, EVENT_PARTICIPATION_UNDERWATER_MWG,
|
||||
EVENT_PARTICIPATION_WARGEAR_SEASON_2022,
|
||||
EGG_HUNT_EASY, EGG_HUNT_MEDIUM, EGG_HUNT_HARD, EGG_HUNT_EXTREME, EGG_HUNT_ADVANCED, EGG_HUNT_HALF
|
||||
);
|
||||
return List.of(EVENT_PARTICIPATION_UNDERWATER_MWG, EGG_HUNT_MEDIUM, EGG_HUNT_HARD, EGG_HUNT_ADVANCED);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
/*
|
||||
* This file is a part of the SteamWar software.
|
||||
*
|
||||
* Copyright (C) 2026 SteamWar.de-Serverteam
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package de.steamwar.lobby.particle.design;
|
||||
|
||||
import de.steamwar.lobby.particle.ParticleElement;
|
||||
import de.steamwar.lobby.particle.ParticleRequirement;
|
||||
import org.bukkit.Material;
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
||||
// An extra effect an entry can carry next to its design, unlocked by a reward. Touches run every tick, independent
|
||||
// of the entry's conditions and timing, so their points count fully towards the slot budget.
|
||||
public record Touch(String id, Material icon, int points, Supplier<ParticleRequirement> requirement, Supplier<ParticleElement> element) {
|
||||
}
|
||||
@@ -0,0 +1,89 @@
|
||||
/*
|
||||
* This file is a part of the SteamWar software.
|
||||
*
|
||||
* Copyright (C) 2026 SteamWar.de-Serverteam
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package de.steamwar.lobby.particle.design;
|
||||
|
||||
import de.steamwar.lobby.particle.Gradient;
|
||||
import de.steamwar.lobby.particle.ParticleRequirement;
|
||||
import de.steamwar.lobby.particle.WingDesign;
|
||||
import de.steamwar.lobby.particle.elements.*;
|
||||
import de.steamwar.lobby.particle.elements.custom.HearthBeat;
|
||||
import de.steamwar.lobby.particle.elements.custom.NonMoving;
|
||||
import de.steamwar.lobby.particle.elements.custom.PulseShimmer;
|
||||
import de.steamwar.lobby.particle.elements.touch.*;
|
||||
import lombok.experimental.UtilityClass;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.Particle;
|
||||
|
||||
import java.time.Month;
|
||||
import java.util.List;
|
||||
|
||||
// The touches of the entries' touch setting, each unlocked by the event or egg hunt reward that used to carry it
|
||||
@UtilityClass
|
||||
public class Touches {
|
||||
|
||||
public final Touch NONE = new Touch("none", Material.GRAY_DYE, 0, () -> ParticleRequirement.NO_REQUIRMENT, () -> null);
|
||||
|
||||
private final List<Touch> ALL = List.of(
|
||||
NONE,
|
||||
// Bursts on jumping, landing or sneaking
|
||||
new Touch("jump_cloud", Material.SNOWBALL, 1, Unlocks.AIRSHIP_PLACEMENT,
|
||||
() -> new EventBurst(EventBurst.Trigger.JUMP, new SimpleParticle(Particle.CLOUD, 0.3F, 0.05F, 0.3F, 0.02, 12))),
|
||||
new Touch("jump_wings", Material.DRAGON_BREATH, 2, Unlocks.WARGEAR_SEASON_2022,
|
||||
() -> new Delayed(new Wing(new SimpleParticle(Particle.DRAGON_BREATH, 0, 0, 0, 0, 1), 0.15, WingDesign.COMPLEX, false, 100, Wing.Motion.JUMP_BEAT), 2)),
|
||||
new Touch("landing_splash", Material.PRISMARINE_SHARD, 1, Unlocks.UNDERWATER_PLACEMENT,
|
||||
() -> new EventBurst(EventBurst.Trigger.LAND, 1, new Ring(new SimpleParticle(Particle.SPLASH, 0, 0, 0, 0, 3), 1, 16))),
|
||||
new Touch("crash_landing", Material.FEATHER, 1, Unlocks.ABSTURZ_PLACEMENT,
|
||||
() -> new EventBurst(EventBurst.Trigger.LAND, 3, new Group(new SimpleParticle(Particle.EXPLOSION, 0, 0, 0, 0, 1),
|
||||
new Ring(new SimpleParticle(Particle.CRIT, 0, 0.1F, 0, 0.1, 2), 1.2, 16)))),
|
||||
new Touch("lava_landing", Material.LAVA_BUCKET, 1, Unlocks.ANY_EVENT,
|
||||
() -> new EventBurst(EventBurst.Trigger.LAND, 1, new Group(new SimpleParticle(Particle.LAVA, 0.2F, 0, 0.2F, 0, 4),
|
||||
new SimpleParticle(Particle.SMOKE, 0.2F, 0.1F, 0.2F, 0.02, 6)))),
|
||||
new Touch("obsidian_landing", Material.CRYING_OBSIDIAN, 1, Unlocks.EGG_HUNT_EXTREME,
|
||||
() -> new EventBurst(EventBurst.Trigger.LAND, 1, new Group(new Ring(new SimpleParticle(Particle.WITCH, 0, 0.05F, 0, 0, 2), 1, 16),
|
||||
new SimpleParticle(Particle.LANDING_OBSIDIAN_TEAR, 0.4F, 0, 0.4F, 0, 6)))),
|
||||
new Touch("glyph_burst", Material.BOOK, 1, Unlocks.WARGEAR_SEASON,
|
||||
() -> new EventBurst(EventBurst.Trigger.SNEAK, new Glyphs(Glyphs.Path.OUT_OF_PLAYER, 16, 1.5))),
|
||||
// Footprints
|
||||
new Touch("wet_footprints", Material.PRISMARINE_CRYSTALS, 4, Unlocks.ADVENT_WAR_SHIP_PLACEMENT,
|
||||
() -> new Footprints(new SimpleParticle(Particle.FISHING, 0.05F, 0, 0.05F, 0, 1), 40)),
|
||||
new Touch("cloud_footprints", Material.SNOW_BLOCK, 4, Unlocks.AIRSHIP,
|
||||
() -> new Footprints(new SimpleParticle(Particle.CLOUD, 0.05F, 0, 0.05F, 0, 1), 40)),
|
||||
new Touch("blossom_footprints", Material.SPORE_BLOSSOM, 4, Unlocks.EGG_HUNT_EASY,
|
||||
() -> new Footprints(new SimpleParticle(Particle.SPORE_BLOSSOM_AIR, 0.05F, 0, 0.05F, 0, 1), 40)),
|
||||
// Lines to nearby players with the same touch
|
||||
new Touch("water_link", Material.WATER_BUCKET, 5, Unlocks.ANY_EVENT,
|
||||
() -> new TeamLink("water_link", new SimpleParticle(Particle.DRIPPING_WATER, 0, 0, 0, 0, 1))),
|
||||
new Touch("bubble_link", Material.PRISMARINE_BRICKS, 5, Unlocks.UNDERWATER,
|
||||
() -> new TeamLink("bubble_link", new SimpleParticle(Particle.BUBBLE_POP, 0, 0, 0, 0, 1))),
|
||||
// While standing still
|
||||
new Touch("glyph_pull", Material.ENCHANTING_TABLE, 3, Unlocks.WARGEAR_SEASON_PLACEMENT,
|
||||
() -> new NonMoving(new Glyphs(Glyphs.Path.INTO_PLAYER, 3, 1.5))),
|
||||
new Touch("still_shimmer", Material.PRISMARINE_SLAB, 3, Unlocks.MINI_WARGEAR_LIGA,
|
||||
() -> new NonMoving(new PulseShimmer(new SimpleParticle(Particle.UNDERWATER, 0, 0, 0, 0, 1), 80, 2))),
|
||||
new Touch("heartbeat", Material.POPPY, 1, Unlocks.EGG_HUNT_HALF,
|
||||
() -> new NonMoving(new HearthBeat(new DustParticle(Particle.DUST, 0, 0, 0, 0, 1, new Gradient(java.awt.Color.RED)), 80))),
|
||||
// Seasonal
|
||||
new Touch("december_snow", Material.POWDER_SNOW_BUCKET, 2, Unlocks.ADVENT_WAR_SHIP,
|
||||
() -> new Seasonal(Month.DECEMBER, new LocationMutator(new SimpleParticle(Particle.SNOWFLAKE, 1.2F, 0.3F, 1.2F, 0.01, 2), 0, 2.4, 0)))
|
||||
);
|
||||
|
||||
public List<ChoiceParameter.Choice<Touch>> choices() {
|
||||
return ALL.stream().map(touch -> new ChoiceParameter.Choice<>(touch.id(), touch, false, touch.requirement())).toList();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,65 @@
|
||||
/*
|
||||
* This file is a part of the SteamWar software.
|
||||
*
|
||||
* Copyright (C) 2026 SteamWar.de-Serverteam
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
package de.steamwar.lobby.particle.design;
|
||||
|
||||
import de.steamwar.lobby.particle.ParticleRequirement;
|
||||
import lombok.experimental.UtilityClass;
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
||||
// Requirements of the reward ingredients: wing images, particles and touches. Each is created on first use, as event
|
||||
// requirements look up the event's name.
|
||||
@UtilityClass
|
||||
public class Unlocks {
|
||||
|
||||
public final Supplier<ParticleRequirement> WARGEAR_SEASON_PLACEMENT = lazy(() -> ParticleRequirement.eventPlacement(22, 12, 285, 54));
|
||||
public final Supplier<ParticleRequirement> AIRSHIP_PLACEMENT = lazy(() -> ParticleRequirement.eventPlacement(26, 205, 9, 54, 120, 292));
|
||||
public final Supplier<ParticleRequirement> UNDERWATER_PLACEMENT = lazy(() -> ParticleRequirement.eventPlacement(31, 9, 210, 520));
|
||||
public final Supplier<ParticleRequirement> ADVENT_WAR_SHIP_PLACEMENT = lazy(() -> ParticleRequirement.eventPlacement(32, 9, 205, 210));
|
||||
public final Supplier<ParticleRequirement> MINI_WARGEAR_LIGA_PLACEMENT = lazy(() -> ParticleRequirement.eventPlacement(33, 9, 34, 205));
|
||||
public final Supplier<ParticleRequirement> ABSTURZ_PLACEMENT = lazy(() -> ParticleRequirement.eventPlacement(34, 210, 205, 527, 286));
|
||||
public final Supplier<ParticleRequirement> UNDERWATER_MWG_PLACEMENT = lazy(() -> ParticleRequirement.eventPlacement(35, 9, 210));
|
||||
public final Supplier<ParticleRequirement> WARGEAR_SEASON_2022_PLACEMENT = lazy(() -> ParticleRequirement.eventPlacement(37, 285, 210, 122));
|
||||
public final Supplier<ParticleRequirement> WARGEAR_CLASH_PLACEMENT = lazy(() -> ParticleRequirement.eventPlacement(38, 210, 158, 167, 286));
|
||||
|
||||
public final Supplier<ParticleRequirement> ANY_EVENT = () -> ParticleRequirement.EVENT_PARTICIPATION;
|
||||
public final Supplier<ParticleRequirement> WARGEAR_SEASON = lazy(() -> ParticleRequirement.eventParticipation(22));
|
||||
public final Supplier<ParticleRequirement> AIRSHIP = lazy(() -> ParticleRequirement.eventParticipation(26));
|
||||
public final Supplier<ParticleRequirement> HELLS_BELLS = lazy(() -> ParticleRequirement.eventParticipation(28));
|
||||
public final Supplier<ParticleRequirement> UNDERWATER = lazy(() -> ParticleRequirement.eventParticipation(31));
|
||||
public final Supplier<ParticleRequirement> ADVENT_WAR_SHIP = lazy(() -> ParticleRequirement.eventParticipation(32));
|
||||
public final Supplier<ParticleRequirement> MINI_WARGEAR_LIGA = lazy(() -> ParticleRequirement.eventParticipation(33));
|
||||
public final Supplier<ParticleRequirement> WARGEAR_SEASON_2022 = lazy(() -> ParticleRequirement.eventParticipation(37));
|
||||
|
||||
public final Supplier<ParticleRequirement> EGG_HUNT_EASY = () -> ParticleRequirement.EGG_HUNT_EASY;
|
||||
public final Supplier<ParticleRequirement> EGG_HUNT_EXTREME = () -> ParticleRequirement.EGG_HUNT_EXTREME;
|
||||
public final Supplier<ParticleRequirement> EGG_HUNT_HALF = () -> ParticleRequirement.EGG_HUNT_FOUND_HALF;
|
||||
|
||||
private Supplier<ParticleRequirement> lazy(Supplier<ParticleRequirement> create) {
|
||||
return new Supplier<>() {
|
||||
private ParticleRequirement requirement;
|
||||
|
||||
@Override
|
||||
public ParticleRequirement get() {
|
||||
if (requirement == null) requirement = create.get();
|
||||
return requirement;
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -119,21 +119,24 @@ class EntryEditor {
|
||||
|
||||
inventory.setItem(ROW_DESIGN * 9 + FIRST_SETTING, new SWItem(design.getIcon(), designName(design, player), List.of(msg("PARTICLE_VALUE_CLICK", player)), false,
|
||||
clickType -> Pickers.design(player, design, picked -> changeDesign(context, picked), context::reopen)));
|
||||
inventory.setItem(ROW_DESIGN * 9 + FIRST_SETTING + 1, parameterItem(context, TOUCH));
|
||||
if (design.usesEntryParticle()) {
|
||||
inventory.setItem(ROW_DESIGN * 9 + FIRST_SETTING + 1, parameterItem(context, PARTICLE));
|
||||
inventory.setItem(ROW_DESIGN * 9 + FIRST_SETTING + 2, parameterItem(context, PARTICLE));
|
||||
ParticleType type = entry.getValues().get(PARTICLE);
|
||||
if (type.usesColors()) {
|
||||
inventory.setItem(ROW_DESIGN * 9 + FIRST_SETTING + 2, parameterItem(context, COLORS));
|
||||
inventory.setItem(ROW_DESIGN * 9 + FIRST_SETTING + 3, parameterItem(context, COLORS));
|
||||
} else if (type.usesBlock()) {
|
||||
inventory.setItem(ROW_DESIGN * 9 + FIRST_SETTING + 2, parameterItem(context, BLOCK));
|
||||
inventory.setItem(ROW_DESIGN * 9 + FIRST_SETTING + 3, parameterItem(context, BLOCK));
|
||||
}
|
||||
// The trail target follows the particle; its duration goes to the end of the particle row
|
||||
List<Parameter<?>> particleRow = new ArrayList<>(design.replacesAmount(entry.getValues()) ? List.of(SPEED, SPREAD_X, SPREAD_Y, SPREAD_Z) : List.of(COUNT, SPEED, SPREAD_X, SPREAD_Y, SPREAD_Z));
|
||||
if (type.isTrail()) {
|
||||
List<Parameter<?>> trail = List.of(TRAIL_DURATION, TRAIL_TARGET_X, TRAIL_TARGET_Y, TRAIL_TARGET_Z);
|
||||
for (int i = 0; i < trail.size(); i++) {
|
||||
inventory.setItem(ROW_DESIGN * 9 + FIRST_SETTING + 3 + i, parameterItem(context, trail.get(i)));
|
||||
List<Parameter<?>> target = List.of(TRAIL_TARGET_X, TRAIL_TARGET_Y, TRAIL_TARGET_Z);
|
||||
for (int i = 0; i < target.size(); i++) {
|
||||
inventory.setItem(ROW_DESIGN * 9 + FIRST_SETTING + 4 + i, parameterItem(context, target.get(i)));
|
||||
}
|
||||
particleRow.add(TRAIL_DURATION);
|
||||
}
|
||||
List<Parameter<?>> particleRow = design.replacesAmount(entry.getValues()) ? List.of(SPEED, SPREAD_X, SPREAD_Y, SPREAD_Z) : List.of(COUNT, SPEED, SPREAD_X, SPREAD_Y, SPREAD_Z);
|
||||
row(inventory, context, ROW_PARTICLE, particleRow);
|
||||
} else {
|
||||
inventory.setItem(ROW_PARTICLE * 9 + FIRST_SETTING, new SWItem(Material.STRUCTURE_VOID, msg("PARTICLE_FIXED_LOOK", player), clickType -> {
|
||||
@@ -187,6 +190,7 @@ class EntryEditor {
|
||||
if (parameter == COLORS) icon = Material.RED_DYE;
|
||||
if (parameter == BLOCK) icon = (Material) value;
|
||||
if (value instanceof WingShape shape) icon = shape.getIcon();
|
||||
if (value instanceof Touch touch) icon = touch.icon();
|
||||
|
||||
return new SWItem(icon, name(parameter.getNameKey(), player), lore, false, clickType -> {
|
||||
if (parameter instanceof BooleanParameter toggle) {
|
||||
@@ -254,6 +258,7 @@ class EntryEditor {
|
||||
private Material choiceIcon(Object value) {
|
||||
if (value instanceof ParticleType type) return type.getIcon();
|
||||
if (value instanceof WingShape shape) return shape.getIcon();
|
||||
if (value instanceof Touch touch) return touch.icon();
|
||||
if (value instanceof Material material) return material;
|
||||
return Material.LEVER;
|
||||
}
|
||||
|
||||
@@ -120,6 +120,9 @@ class ParticleGuiText {
|
||||
if (entry.getDesign().usesEntryParticle()) {
|
||||
lore.add(msg("PARTICLE_ENTRY_PARTICLE", player, particleName(values.get(PARTICLE), player)));
|
||||
}
|
||||
if (values.get(TOUCH) != Touches.NONE) {
|
||||
lore.add(msg("PARTICLE_ENTRY_TOUCH", player, choiceName(TOUCH, values.get(TOUCH), player)));
|
||||
}
|
||||
lore.add("§8- " + choiceName(TICK_MODE, values.get(TICK_MODE), player));
|
||||
addCondition(lore, MOVEMENT, values.get(MOVEMENT), Movement.ANY, player);
|
||||
addCondition(lore, GLIDING, values.get(GLIDING), Gliding.ANY, player);
|
||||
|
||||
@@ -169,9 +169,9 @@ public class ParticleEntry {
|
||||
return new LocationMutator(element, offsetX, offsetY, offsetZ);
|
||||
}
|
||||
|
||||
// The design's touch with the entry's placement and visibility, or null; touches ignore conditions and timing
|
||||
// The entry's touch with its placement and visibility, or null; touches ignore conditions and timing
|
||||
public ParticleElement buildTouch() {
|
||||
ParticleElement touch = design.touch();
|
||||
ParticleElement touch = values.get(TOUCH).element().get();
|
||||
if (touch == null) {
|
||||
return null;
|
||||
}
|
||||
@@ -181,12 +181,15 @@ public class ParticleEntry {
|
||||
return new Always(values.get(VISIBILITY).wrap(touch));
|
||||
}
|
||||
|
||||
// Shown only when the design, its chosen options and, for designs that use it, the particle type are unlocked
|
||||
// Shown only when the design, its chosen options, the touch and, for designs that use it, the particle type are unlocked
|
||||
@SuppressWarnings("unchecked")
|
||||
public boolean isUnlocked(UnlockContext context) {
|
||||
if (!design.getRequirement().test(context)) {
|
||||
return false;
|
||||
}
|
||||
if (!TOUCH.requirement(values.get(TOUCH)).test(context)) {
|
||||
return false;
|
||||
}
|
||||
for (Parameter<?> parameter : design.getParameters()) {
|
||||
if (parameter instanceof ChoiceParameter<?> choice && !((ChoiceParameter<Object>) choice).requirement(values.get(choice)).test(context)) {
|
||||
return false;
|
||||
@@ -203,7 +206,7 @@ public class ParticleEntry {
|
||||
// Particle positions spawned per tick, used for the slot budget
|
||||
public double cost() {
|
||||
double perTick = design.usesEntryParticle() ? (double) design.points(values) * amount() : design.points(values);
|
||||
return perTick / values.get(INTERVAL);
|
||||
return perTick / values.get(INTERVAL) + values.get(TOUCH).points();
|
||||
}
|
||||
|
||||
public JsonObject toJson() {
|
||||
|
||||
Reference in New Issue
Block a user