mirror of
https://github.com/Sollace/Unicopia.git
synced 2024-11-23 21:38:00 +01:00
Rewrite food effects and add an insect type
This commit is contained in:
parent
c45d6eb86a
commit
536502027d
32 changed files with 376 additions and 246 deletions
|
@ -13,7 +13,6 @@ import com.google.common.base.Strings;
|
|||
import com.minelittlepony.common.client.gui.sprite.TextureSprite;
|
||||
import com.minelittlepony.common.client.gui.style.Style;
|
||||
import com.minelittlepony.unicopia.ability.magic.Affine;
|
||||
import com.minelittlepony.unicopia.item.toxin.FoodType;
|
||||
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.text.Text;
|
||||
|
@ -50,19 +49,6 @@ public enum Race implements Affine {
|
|||
return this == CHANGELING ? Affinity.BAD : Affinity.NEUTRAL;
|
||||
}
|
||||
|
||||
public boolean canConsume(FoodType type) {
|
||||
if (!isUsable()) {
|
||||
return type != FoodType.FORAGE;
|
||||
}
|
||||
if (type.isMeat()) {
|
||||
return this == BAT || this == CHANGELING || this == HUMAN;
|
||||
}
|
||||
if (type.isFish()) {
|
||||
return this == PEGASUS || this == ALICORN;
|
||||
}
|
||||
return hasIronGut();
|
||||
}
|
||||
|
||||
public boolean hasIronGut() {
|
||||
return isUsable() && this != CHANGELING;
|
||||
}
|
||||
|
|
|
@ -24,8 +24,6 @@ import com.minelittlepony.unicopia.entity.Living;
|
|||
import com.minelittlepony.unicopia.entity.Trap;
|
||||
import com.minelittlepony.unicopia.entity.effect.SunBlindnessStatusEffect;
|
||||
import com.minelittlepony.unicopia.item.UItems;
|
||||
import com.minelittlepony.unicopia.item.toxin.FoodType;
|
||||
import com.minelittlepony.unicopia.item.toxin.Toxicity;
|
||||
import com.minelittlepony.unicopia.item.toxin.Toxin;
|
||||
import com.minelittlepony.unicopia.network.Channel;
|
||||
import com.minelittlepony.unicopia.network.MsgOtherPlayerCapabilities;
|
||||
|
@ -420,7 +418,7 @@ public class Pony extends Living<PlayerEntity> implements Transmittable, Copieab
|
|||
|
||||
public void onEat(ItemStack stack) {
|
||||
if (getSpecies() == Race.CHANGELING) {
|
||||
Toxin.POISON.afflict(getMaster(), FoodType.RAW_MEAT, Toxicity.SAFE, stack);
|
||||
Toxin.LOVE_SICKNESS.afflict(getMaster(), stack);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -62,7 +62,7 @@ public interface UItems {
|
|||
Item DAFFODIL_DAISY_SANDWICH = register("daffodil_daisy_sandwich", new Item(new Item.Settings().group(ItemGroup.FOOD).food(UFoodComponents.DAFODIL_DAISY_SANDWICH)));
|
||||
Item HAY_BURGER = register("hay_burger", new Item(new Item.Settings().group(ItemGroup.FOOD).maxCount(1).food(UFoodComponents.HAY_BURGER)));
|
||||
Item HAY_FRIES = register("hay_fries", new Item(new Item.Settings().group(ItemGroup.FOOD).maxCount(16).food(UFoodComponents.HAY_FRIES)));
|
||||
Item WHEAT_WORMS = register("wheat_worms", new Item(new Item.Settings().group(ItemGroup.MISC).maxCount(16).food(UFoodComponents.WORMS)));
|
||||
Item WHEAT_WORMS = register("wheat_worms", new Item(new Item.Settings().group(ItemGroup.MISC).maxCount(16).food(UFoodComponents.INSECTS)));
|
||||
|
||||
Item MUG = register("mug", new Item(new Settings().group(ItemGroup.MATERIALS).maxCount(16)));
|
||||
Item CIDER = register("cider", new DrinkableItem(new Item.Settings().group(ItemGroup.FOOD).food(UFoodComponents.CIDER).maxCount(1).recipeRemainder(MUG)));
|
||||
|
|
|
@ -0,0 +1,12 @@
|
|||
package com.minelittlepony.unicopia.item.toxin;
|
||||
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.item.ItemStack;
|
||||
|
||||
public interface Affliction {
|
||||
void afflict(PlayerEntity player, ItemStack stack);
|
||||
|
||||
interface Predicate {
|
||||
boolean test(PlayerEntity player, ItemStack stack);
|
||||
}
|
||||
}
|
|
@ -1,29 +1,40 @@
|
|||
package com.minelittlepony.unicopia.item.toxin;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import net.minecraft.client.item.TooltipContext;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.text.Text;
|
||||
|
||||
public class Ailment {
|
||||
|
||||
public static final Ailment INNERT = new Ailment(Toxicity.SAFE, Toxin.INNERT);
|
||||
public class Ailment implements Affliction {
|
||||
public static final Ailment INNERT = of(Toxicity.SAFE, Toxin.INNERT);
|
||||
|
||||
private final Toxicity toxicity;
|
||||
private final Toxin toxin;
|
||||
private final Toxin effect;
|
||||
|
||||
public Ailment(Toxicity toxicity, Toxin toxin) {
|
||||
Ailment(Toxicity toxicity, Toxin effect) {
|
||||
this.toxicity = toxicity;
|
||||
this.toxin = toxin;
|
||||
this.effect = effect;
|
||||
}
|
||||
|
||||
public Toxicity getToxicity() {
|
||||
return toxicity;
|
||||
}
|
||||
|
||||
public void afflict(PlayerEntity player, FoodType type, ItemStack stack) {
|
||||
this.toxin.afflict(player, type, toxicity, stack);
|
||||
public void appendTooltip(List<Text> tooltip, TooltipContext context) {
|
||||
tooltip.add(getToxicity().getTooltip());
|
||||
if (context.isAdvanced()) {
|
||||
effect.appendTooltip(tooltip);
|
||||
}
|
||||
}
|
||||
|
||||
public static Ailment of(Toxicity toxicity) {
|
||||
return new Ailment(toxicity, Toxin.FOOD);
|
||||
@Override
|
||||
public void afflict(PlayerEntity player, ItemStack stack) {
|
||||
effect.afflict(player, stack);
|
||||
}
|
||||
|
||||
public static Ailment of(Toxicity toxicity, Toxin effect) {
|
||||
return new Ailment(toxicity, effect);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,19 +0,0 @@
|
|||
package com.minelittlepony.unicopia.item.toxin;
|
||||
|
||||
public enum FoodType {
|
||||
RAW_MEAT, COOKED_MEAT,
|
||||
RAW_FISH, COOKED_FISH,
|
||||
FORAGE;
|
||||
|
||||
public boolean isRaw() {
|
||||
return this == RAW_MEAT || this == RAW_FISH || this == FORAGE;
|
||||
}
|
||||
|
||||
public boolean isMeat() {
|
||||
return this == RAW_MEAT || this == COOKED_MEAT;
|
||||
}
|
||||
|
||||
public boolean isFish() {
|
||||
return this == RAW_FISH || this == COOKED_FISH;
|
||||
}
|
||||
}
|
|
@ -1,7 +1,11 @@
|
|||
package com.minelittlepony.unicopia.item.toxin;
|
||||
|
||||
import java.util.EnumMap;
|
||||
import java.util.Map;
|
||||
import java.util.Optional;
|
||||
|
||||
import com.minelittlepony.unicopia.Race;
|
||||
import com.minelittlepony.unicopia.UTags;
|
||||
import com.minelittlepony.unicopia.entity.player.Pony;
|
||||
|
||||
import net.minecraft.entity.LivingEntity;
|
||||
|
@ -18,22 +22,19 @@ import net.minecraft.world.World;
|
|||
public class Toxic {
|
||||
private final UseAction action;
|
||||
|
||||
private final Ailment lowerBound;
|
||||
private final Ailment upperBound;
|
||||
|
||||
private final FoodType type;
|
||||
|
||||
private final Optional<FoodComponent> component;
|
||||
|
||||
private final Ailment defaultAilment;
|
||||
private final Map<Race, Ailment> ailments;
|
||||
|
||||
private final Tag<Item> tag;
|
||||
|
||||
Toxic(UseAction action, FoodType type, Optional<FoodComponent> component, Tag<Item> tag, Ailment lowerBound, Ailment upperBound) {
|
||||
Toxic(UseAction action, Optional<FoodComponent> component, Tag<Item> tag, Ailment defaultAilment, Map<Race, Ailment> ailments) {
|
||||
this.action = action;
|
||||
this.type = type;
|
||||
this.component = component;
|
||||
this.tag = tag;
|
||||
this.lowerBound = lowerBound;
|
||||
this.upperBound = upperBound;
|
||||
this.defaultAilment = defaultAilment;
|
||||
this.ailments = ailments;
|
||||
}
|
||||
|
||||
public boolean matches(Item item) {
|
||||
|
@ -49,16 +50,15 @@ public class Toxic {
|
|||
}
|
||||
|
||||
public Ailment getAilmentFor(PlayerEntity player) {
|
||||
Pony pony = Pony.of(player);
|
||||
if (pony != null && !pony.getSpecies().canConsume(type)) {
|
||||
return upperBound;
|
||||
if (player == null) {
|
||||
return defaultAilment;
|
||||
}
|
||||
return lowerBound;
|
||||
return ailments.getOrDefault(Pony.of(player).getSpecies(), defaultAilment);
|
||||
}
|
||||
|
||||
public ItemStack finishUsing(ItemStack stack, World world, LivingEntity entity) {
|
||||
if (entity instanceof PlayerEntity) {
|
||||
getAilmentFor((PlayerEntity)entity).afflict((PlayerEntity)entity, type, stack);
|
||||
getAilmentFor((PlayerEntity)entity).afflict((PlayerEntity)entity, stack);
|
||||
}
|
||||
|
||||
return stack;
|
||||
|
@ -70,4 +70,34 @@ public class Toxic {
|
|||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public static class Builder {
|
||||
private final Ailment def;
|
||||
private final Map<Race, Ailment> ailments = new EnumMap<>(Race.class);
|
||||
private UseAction action = UseAction.EAT;
|
||||
private Optional<FoodComponent> component = Optional.empty();
|
||||
|
||||
public Builder(Ailment def) {
|
||||
this.def = def;
|
||||
}
|
||||
|
||||
public Builder action(UseAction action) {
|
||||
this.action = action;
|
||||
return this;
|
||||
}
|
||||
|
||||
public Builder food(FoodComponent food) {
|
||||
component = Optional.ofNullable(food);
|
||||
return this;
|
||||
}
|
||||
|
||||
public Builder with(Race race, Ailment ailment) {
|
||||
ailments.put(race, ailment);
|
||||
return this;
|
||||
}
|
||||
|
||||
public Toxic build(String name) {
|
||||
return new Toxic(action, component, UTags.item(name), def, ailments);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -10,44 +10,18 @@ import net.minecraft.text.TranslatableText;
|
|||
import net.minecraft.util.Formatting;
|
||||
|
||||
public enum Toxicity {
|
||||
SAFE(0, 0),
|
||||
MILD(1, 160),
|
||||
FAIR(1, 30),
|
||||
SEVERE(5, 160),
|
||||
LETHAL(10, 900);
|
||||
|
||||
private final int level;
|
||||
private final int duration;
|
||||
SAFE(Formatting.GRAY),
|
||||
MILD(Formatting.DARK_AQUA),
|
||||
FAIR(Formatting.DARK_BLUE),
|
||||
SEVERE(Formatting.DARK_PURPLE),
|
||||
LETHAL(Formatting.RED);
|
||||
|
||||
private static final Map<String, Toxicity> REGISTRY = Arrays.stream(values()).collect(Collectors.toMap(Toxicity::name, Function.identity()));
|
||||
|
||||
Toxicity(int level, int duration) {
|
||||
this.level = level;
|
||||
this.duration = duration;
|
||||
}
|
||||
private final Formatting color;
|
||||
|
||||
public int getLevel() {
|
||||
return level;
|
||||
}
|
||||
|
||||
public int getDuration() {
|
||||
return duration;
|
||||
}
|
||||
|
||||
public boolean isMild() {
|
||||
return this == MILD;
|
||||
}
|
||||
|
||||
public boolean toxicWhenRaw() {
|
||||
return isLethal() || this != SAFE;
|
||||
}
|
||||
|
||||
public boolean toxicWhenCooked() {
|
||||
return isLethal() || this == SEVERE;
|
||||
}
|
||||
|
||||
public boolean isLethal() {
|
||||
return this == LETHAL;
|
||||
Toxicity(Formatting color) {
|
||||
this.color = color;
|
||||
}
|
||||
|
||||
public String getTranslationKey() {
|
||||
|
@ -55,9 +29,7 @@ public enum Toxicity {
|
|||
}
|
||||
|
||||
public Text getTooltip() {
|
||||
return new TranslatableText(getTranslationKey())
|
||||
.styled(s -> s
|
||||
.withColor(toxicWhenCooked() ? Formatting.RED : toxicWhenRaw() ? Formatting.DARK_PURPLE : Formatting.GRAY));
|
||||
return new TranslatableText(getTranslationKey()).formatted(color);
|
||||
}
|
||||
|
||||
public static Toxicity byName(String name) {
|
||||
|
|
|
@ -1,13 +1,9 @@
|
|||
package com.minelittlepony.unicopia.item.toxin;
|
||||
|
||||
import java.util.Optional;
|
||||
|
||||
import com.minelittlepony.unicopia.UTags;
|
||||
import com.minelittlepony.unicopia.Race;
|
||||
import com.minelittlepony.unicopia.util.Registries;
|
||||
|
||||
import net.minecraft.item.FoodComponent;
|
||||
import net.minecraft.util.Identifier;
|
||||
import net.minecraft.util.UseAction;
|
||||
import net.minecraft.util.registry.Registry;
|
||||
|
||||
import static com.minelittlepony.unicopia.item.toxin.Toxicity.*;
|
||||
|
@ -16,46 +12,87 @@ import static com.minelittlepony.unicopia.item.toxin.Toxin.*;
|
|||
public interface Toxics {
|
||||
Registry<Toxic> REGISTRY = Registries.createSimple(new Identifier("unicopia:toxic"));
|
||||
|
||||
Toxic EDIBLE = forage("edible", SAFE, FOOD);
|
||||
Toxic RISKY = forage("risky", FAIR, FOOD);
|
||||
Toxic MODERATE = forage("moderate", MILD, FOOD);
|
||||
Toxic DANGEROUS = forage("dangerous", SEVERE, FOOD);
|
||||
Toxic NAUSEATING = forage("nauseating", SAFE, NAUSEA);
|
||||
Toxic RADIOACTIVE = forage("radioactive", SAFE, RADIOACTIVITY);
|
||||
Toxic PRICKLY = forage("prickly", SAFE, DAMAGE);
|
||||
Toxic STRENGHTENING = forage("strengthening", SEVERE, STRENGTH);
|
||||
Toxic SEVERELY_NAUSEATING = forage("severely_nauseating", SEVERE, NAUSEA);
|
||||
Toxic BLINDING = forage("blinding", SEVERE, BLINDNESS);
|
||||
Toxic SEVERELY_PRICKLY = forage("severely_prickly", SEVERE, DAMAGE);
|
||||
Toxic EDIBLE = register("forage_edible", new Toxic.Builder(Ailment.of(SAFE, INNERT))
|
||||
.food(UFoodComponents.RANDOM_FOLIAGE)
|
||||
.with(Race.HUMAN, Ailment.of(LETHAL, FOOD_POISONING))
|
||||
);
|
||||
Toxic RISKY = register("forage_risky", new Toxic.Builder(Ailment.of(FAIR, WEAK_NAUSEA.withChance(20)))
|
||||
.food(UFoodComponents.RANDOM_FOLIAGE)
|
||||
.with(Race.HUMAN, Ailment.of(LETHAL, FOOD_POISONING))
|
||||
);
|
||||
Toxic MODERATE = register("forage_moderate", new Toxic.Builder(Ailment.of(MILD, POISON.and(WEAK_NAUSEA)))
|
||||
.food(UFoodComponents.RANDOM_FOLIAGE)
|
||||
.with(Race.HUMAN, Ailment.of(LETHAL, FOOD_POISONING))
|
||||
);
|
||||
Toxic DANGEROUS = register("forage_dangerous", new Toxic.Builder(Ailment.of(SEVERE, FOOD_POISONING))
|
||||
.food(UFoodComponents.RANDOM_FOLIAGE)
|
||||
.with(Race.HUMAN, Ailment.of(LETHAL, FOOD_POISONING.and(NAUSEA)))
|
||||
);
|
||||
Toxic NAUSEATING = register("forage_nauseating", new Toxic.Builder(Ailment.of(SAFE, NAUSEA.and(WEAKNESS.withChance(30))))
|
||||
.food(UFoodComponents.RANDOM_FOLIAGE)
|
||||
.with(Race.HUMAN, Ailment.of(LETHAL, FOOD_POISONING.and(NAUSEA)))
|
||||
);
|
||||
Toxic RADIOACTIVE = register("forage_radioactive", new Toxic.Builder(Ailment.of(SAFE, NAUSEA.and(RADIOACTIVITY.withChance(30))))
|
||||
.food(UFoodComponents.RANDOM_FOLIAGE)
|
||||
.with(Race.HUMAN, Ailment.of(LETHAL, FOOD_POISONING.and(NAUSEA)))
|
||||
);
|
||||
Toxic PRICKLY = register("forage_prickly", new Toxic.Builder(Ailment.of(SAFE, PRICKLING.withChance(30)))
|
||||
.food(UFoodComponents.RANDOM_FOLIAGE)
|
||||
.with(Race.HUMAN, Ailment.of(LETHAL, FOOD_POISONING.and(NAUSEA)))
|
||||
);
|
||||
Toxic STRENGHTENING = register("forage_strengthening", new Toxic.Builder(Ailment.of(SEVERE, STRENGTH.and(WEAK_NAUSEA)))
|
||||
.food(UFoodComponents.RANDOM_FOLIAGE)
|
||||
.with(Race.HUMAN, Ailment.of(LETHAL, FOOD_POISONING.and(WEAKNESS)))
|
||||
);
|
||||
Toxic SEVERELY_NAUSEATING = register("forage_severely_nauseating", new Toxic.Builder(Ailment.of(SEVERE, STRONG_NAUSEA.and(WEAKNESS)))
|
||||
.food(UFoodComponents.RANDOM_FOLIAGE)
|
||||
.with(Race.HUMAN, Ailment.of(LETHAL, FOOD_POISONING.and(WEAKNESS)))
|
||||
);
|
||||
Toxic BLINDING = register("forage_blinding", new Toxic.Builder(Ailment.of(SEVERE, BLINDNESS.and(WEAK_NAUSEA)))
|
||||
.food(UFoodComponents.RANDOM_FOLIAGE)
|
||||
.with(Race.HUMAN, Ailment.of(LETHAL, FOOD_POISONING))
|
||||
);
|
||||
Toxic SEVERELY_PRICKLY = register("forage_severely_prickly", new Toxic.Builder(Ailment.of(SEVERE, PRICKLING.and(NAUSEA)))
|
||||
.food(UFoodComponents.RANDOM_FOLIAGE)
|
||||
.with(Race.HUMAN, Ailment.of(LETHAL, FOOD_POISONING))
|
||||
);
|
||||
Toxic RAW_MEAT = register("raw_meat", new Toxic.Builder(Ailment.of(SEVERE, FOOD_POISONING.withChance(5).and(POISON.withChance(20))))
|
||||
.with(Race.HUMAN, Ailment.INNERT)
|
||||
.with(Race.BAT, Ailment.of(MILD, WEAK_NAUSEA))
|
||||
);
|
||||
Toxic ROTTEN_MEAT = register("rotten_meat", new Toxic.Builder(Ailment.of(SEVERE, FOOD_POISONING.and(POISON)))
|
||||
.with(Race.HUMAN, Ailment.INNERT)
|
||||
.with(Race.BAT, Ailment.of(MILD, STRONG_NAUSEA))
|
||||
);
|
||||
Toxic COOKED_MEAT = register("cooked_meat", new Toxic.Builder(Ailment.of(FAIR, FOOD_POISONING))
|
||||
.with(Race.HUMAN, Ailment.INNERT)
|
||||
.with(Race.BAT, Ailment.INNERT)
|
||||
);
|
||||
|
||||
Toxic RAW_MEAT = meat(FoodType.RAW_MEAT, MILD);
|
||||
Toxic COOKED_MEAT = meat(FoodType.COOKED_MEAT, MILD);
|
||||
Toxic RAW_FISH = register("raw_fish", new Toxic.Builder(Ailment.of(FAIR, FOOD_POISONING.and(POISON)))
|
||||
.with(Race.HUMAN, Ailment.INNERT)
|
||||
.with(Race.PEGASUS, Ailment.of(MILD, POISON.and(WEAK_NAUSEA)))
|
||||
.with(Race.ALICORN, Ailment.INNERT)
|
||||
);
|
||||
Toxic COOKED_FISH = register("cooked_fish", new Toxic.Builder(Ailment.of(MILD, FOOD_POISONING))
|
||||
.with(Race.HUMAN, Ailment.INNERT)
|
||||
.with(Race.PEGASUS, Ailment.INNERT)
|
||||
.with(Race.ALICORN, Ailment.INNERT)
|
||||
);
|
||||
|
||||
Toxic RAW_FISH = meat(FoodType.RAW_FISH, FAIR);
|
||||
Toxic COOKED_FISH = meat(FoodType.COOKED_FISH, FAIR);
|
||||
Toxic RAW_INSECT = register("raw_insect", new Toxic.Builder(Ailment.of(LETHAL, FOOD_POISONING))
|
||||
.with(Race.BAT, Ailment.of(MILD, WEAK_NAUSEA))
|
||||
);
|
||||
|
||||
Toxic COOKED_INSECT = register("cooked_insect", new Toxic.Builder(Ailment.of(LETHAL, FOOD_POISONING))
|
||||
.food(UFoodComponents.INSECTS)
|
||||
.with(Race.BAT, Ailment.INNERT)
|
||||
);
|
||||
|
||||
static void bootstrap() {}
|
||||
|
||||
static Toxic forage(String name, Toxicity toxicity, Toxin toxin) {
|
||||
if (toxin != FOOD) {
|
||||
toxin = FOOD.and(toxin);
|
||||
}
|
||||
return register("forage_" + name, UseAction.EAT, FoodType.FORAGE,
|
||||
Optional.of(UFoodComponents.RANDOM_FOLIAGE),
|
||||
new Ailment(toxicity, toxin),
|
||||
new Ailment(Toxicity.LETHAL, toxin));
|
||||
}
|
||||
|
||||
static Toxic meat(FoodType type, Toxicity toxicity) {
|
||||
return register(type.name().toLowerCase(), UseAction.EAT, type,
|
||||
Optional.empty(),
|
||||
Ailment.INNERT,
|
||||
Ailment.of(toxicity));
|
||||
}
|
||||
|
||||
static Toxic register(String name, UseAction action, FoodType type, Optional<FoodComponent> component,
|
||||
Ailment lower,
|
||||
Ailment upper) {
|
||||
return Registry.register(REGISTRY, name, new Toxic(action, type, component, UTags.item(name), lower, upper));
|
||||
static Toxic register(String name, Toxic.Builder builder) {
|
||||
name = "food_types/" + name;
|
||||
return Registry.register(REGISTRY, name, builder.build(name));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,72 +1,137 @@
|
|||
package com.minelittlepony.unicopia.item.toxin;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import net.minecraft.entity.effect.StatusEffect;
|
||||
import net.minecraft.entity.effect.StatusEffectInstance;
|
||||
import net.minecraft.entity.effect.StatusEffects;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.item.FoodComponent;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.text.MutableText;
|
||||
import net.minecraft.text.Text;
|
||||
import net.minecraft.text.TranslatableText;
|
||||
import net.minecraft.util.ChatUtil;
|
||||
import net.minecraft.world.Difficulty;
|
||||
|
||||
@FunctionalInterface
|
||||
public interface Toxin {
|
||||
Predicate ONE_EVERY_30_TICKS = (player, type, toxicity, stack) -> player.world.random.nextInt(30) == 0;
|
||||
public interface Toxin extends Affliction {
|
||||
Predicate IF_NOT_PEACEFUL = Predicate.of(Text.of("when not in peaceful "), (player, stack) -> player.world.getDifficulty() != Difficulty.PEACEFUL);
|
||||
|
||||
Toxin INNERT = (player, type, toxicity, stack) -> {};
|
||||
Toxin DAMAGE = ONE_EVERY_30_TICKS.then(of(StatusEffects.INSTANT_DAMAGE, 1, 1));
|
||||
Toxin RADIOACTIVITY = ONE_EVERY_30_TICKS.then(of(StatusEffects.GLOWING, 10, 1));
|
||||
Toxin NAUSEA = of(StatusEffects.NAUSEA, 30, 1);
|
||||
Toxin WEAK_NAUSEA = of(StatusEffects.NAUSEA, 3, 1);
|
||||
Toxin STRENGTH = of(StatusEffects.STRENGTH, 30, 1);
|
||||
Toxin BLINDNESS = of(StatusEffects.BLINDNESS, 30, 1);
|
||||
Toxin POISON = (player, type, toxicity, stack) -> {
|
||||
Toxin INNERT = of(Text.of("No Effect"), (player, stack) -> {});
|
||||
|
||||
Toxin PRICKLING = of(StatusEffects.INSTANT_DAMAGE, 1, 0);
|
||||
Toxin RADIOACTIVITY = of(StatusEffects.GLOWING, 15, 0);
|
||||
|
||||
Toxin WEAKNESS = of(StatusEffects.WEAKNESS, 200, 1);
|
||||
|
||||
Toxin WEAK_NAUSEA = of(StatusEffects.NAUSEA, 17, 0);
|
||||
Toxin NAUSEA = of(StatusEffects.NAUSEA, 20, 1);
|
||||
Toxin STRONG_NAUSEA = of(StatusEffects.NAUSEA, 30, 1);
|
||||
|
||||
Toxin STRENGTH = of(StatusEffects.STRENGTH, 30, 0);
|
||||
Toxin BLINDNESS = of(StatusEffects.BLINDNESS, 30, 0);
|
||||
Toxin POISON = of(StatusEffects.POISON, 45, 2);
|
||||
Toxin FOOD_POISONING = of(UEffects.FOOD_POISONING, 300, 2);
|
||||
Toxin WEAK_FOOD_POISONING = of(UEffects.FOOD_POISONING, 150, 1);
|
||||
|
||||
Toxin LOVE_SICKNESS = of(Text.of("Love Sickness "), (player, stack) -> {
|
||||
FoodComponent food = stack.getItem().getFoodComponent();
|
||||
|
||||
player.getHungerManager().add(-food.getHunger()/2, -food.getSaturationModifier()/2);
|
||||
afflict(player, StatusEffects.NAUSEA, 1700, 10);
|
||||
}).and(STRONG_NAUSEA).and(IF_NOT_PEACEFUL.then(WEAK_FOOD_POISONING.withChance(20))).and(WEAKNESS);
|
||||
|
||||
if (player.world.getDifficulty() != Difficulty.PEACEFUL && player.world.random.nextInt(20) == 0) {
|
||||
afflict(player, UEffects.FOOD_POISONING, 150, 2);
|
||||
}
|
||||
default void appendTooltip(List<Text> tooltip) {
|
||||
tooltip.add(getName());
|
||||
}
|
||||
|
||||
afflict(player, StatusEffects.WEAKNESS, 2000, 20);
|
||||
};
|
||||
Toxin FOOD = (player, type, toxicity, stack) -> {
|
||||
if (toxicity.toxicWhenRaw() && type.isRaw()) {
|
||||
player.addStatusEffect(new StatusEffectInstance(toxicity.isMild() ? StatusEffects.NAUSEA : StatusEffects.POISON, toxicity.getDuration(), toxicity.getLevel()));
|
||||
}
|
||||
default Toxin withChance(int max) {
|
||||
return Predicate.of(Text.of("1 in " + max + " chance of "), (player, stack) -> player.world.random.nextInt(max) == 0).then(this);
|
||||
}
|
||||
|
||||
if (toxicity.isLethal()) {
|
||||
player.addStatusEffect(new StatusEffectInstance(UEffects.FOOD_POISONING, 300, 7, false, false));
|
||||
} else if (toxicity.toxicWhenCooked()) {
|
||||
WEAK_NAUSEA.afflict(player, type, toxicity, stack);
|
||||
}
|
||||
};
|
||||
|
||||
void afflict(PlayerEntity player, FoodType type, Toxicity toxicity, ItemStack stack);
|
||||
Text getName();
|
||||
|
||||
default Toxin and(Toxin other) {
|
||||
Toxin self = this;
|
||||
return (player, type, toxicity, stack) -> {
|
||||
self.afflict(player, type, toxicity, stack);
|
||||
other.afflict(player, type, toxicity, stack);
|
||||
return new Toxin() {
|
||||
@Override
|
||||
public void afflict(PlayerEntity player, ItemStack stack) {
|
||||
self.afflict(player, stack);
|
||||
other.afflict(player, stack);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void appendTooltip(List<Text> tooltip) {
|
||||
self.appendTooltip(tooltip);
|
||||
other.appendTooltip(tooltip);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Text getName() {
|
||||
return self.getName().shallowCopy().append(" + ").append(other.getName());
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
static Toxin of(StatusEffect effect, int duration, int amplifier) {
|
||||
return (player, type, toxicity, stack) -> afflict(player, effect, duration, amplifier);
|
||||
static Toxin of(Text name, Affliction affliction) {
|
||||
return new Toxin() {
|
||||
@Override
|
||||
public void afflict(PlayerEntity player, ItemStack stack) {
|
||||
affliction.afflict(player, stack);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Text getName() {
|
||||
return name;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
static void afflict(PlayerEntity player, StatusEffect effect, int duration, int amplifier) {
|
||||
player.addStatusEffect(new StatusEffectInstance(effect, duration, amplifier, false, false));
|
||||
static Toxin of(StatusEffect effect, int seconds, int amplifier) {
|
||||
int ticks = seconds * 20;
|
||||
|
||||
MutableText text = effect.getName().shallowCopy();
|
||||
|
||||
if (amplifier > 0) {
|
||||
text = new TranslatableText("potion.withAmplifier", text, new TranslatableText("potion.potency." + amplifier));
|
||||
}
|
||||
|
||||
text = new TranslatableText("potion.withDuration", text, ChatUtil.ticksToString(ticks));
|
||||
|
||||
return of(text, (player, stack) -> {
|
||||
player.addStatusEffect(new StatusEffectInstance(effect, ticks, amplifier, false, false, false));
|
||||
});
|
||||
}
|
||||
|
||||
interface Predicate {
|
||||
boolean test(PlayerEntity player, FoodType type, Toxicity toxicity, ItemStack stack);
|
||||
static Predicate of(Text name, Affliction.Predicate predicate) {
|
||||
return new Predicate() {
|
||||
@Override
|
||||
public boolean test(PlayerEntity player, ItemStack stack) {
|
||||
return predicate.test(player, stack);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Text getName() {
|
||||
return name;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
boolean test(PlayerEntity player, ItemStack stack);
|
||||
|
||||
Text getName();
|
||||
|
||||
default Toxin then(Toxin toxin) {
|
||||
return (player, type, toxicity, stack) -> {
|
||||
if (test(player, type, toxicity, stack)) {
|
||||
toxin.afflict(player, type, toxicity, stack);
|
||||
return new Toxin() {
|
||||
@Override
|
||||
public void afflict(PlayerEntity player, ItemStack stack) {
|
||||
if (test(player, stack)) {
|
||||
toxin.afflict(player, stack);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public Text getName() {
|
||||
return Predicate.this.getName().shallowCopy().append(toxin.getName());
|
||||
}
|
||||
};
|
||||
}
|
||||
|
|
|
@ -11,17 +11,20 @@ import net.minecraft.util.Identifier;
|
|||
|
||||
public interface UEffects {
|
||||
|
||||
StatusEffect FOOD_POISONING = new CustomStatusEffect(new Identifier("unicopia", "food_poisoning"), StatusEffectType.BENEFICIAL, 3484199)
|
||||
.setSilent()
|
||||
.direct((p, e, i) -> {
|
||||
StatusEffectInstance nausea = e.getStatusEffect(StatusEffects.NAUSEA);
|
||||
if (nausea == null) {
|
||||
StatusEffectInstance foodEffect = e.getStatusEffect(p);
|
||||
nausea = new StatusEffectInstance(StatusEffects.NAUSEA, foodEffect.getDuration(), foodEffect.getAmplifier(), foodEffect.isAmbient(), foodEffect.shouldShowParticles());
|
||||
StatusEffect FOOD_POISONING = new CustomStatusEffect.Builder(new Identifier("unicopia", "food_poisoning"), StatusEffectType.HARMFUL, 3484199).direct((p, e, i) -> {
|
||||
StatusEffectInstance nausea = e.getStatusEffect(StatusEffects.NAUSEA);
|
||||
if (nausea == null) {
|
||||
StatusEffectInstance foodEffect = e.getStatusEffect(p);
|
||||
nausea = new StatusEffectInstance(StatusEffects.NAUSEA, foodEffect.getDuration(),
|
||||
foodEffect.getAmplifier(),
|
||||
true,
|
||||
foodEffect.shouldShowParticles(),
|
||||
false
|
||||
);
|
||||
|
||||
e.addStatusEffect(nausea);
|
||||
}
|
||||
e.addStatusEffect(nausea);
|
||||
}
|
||||
|
||||
e.damage(MagicalDamageSource.FOOD_POISONING, i);
|
||||
});
|
||||
e.damage(MagicalDamageSource.FOOD_POISONING, i);
|
||||
}).build();
|
||||
}
|
||||
|
|
|
@ -15,10 +15,12 @@ public interface UFoodComponents {
|
|||
FoodComponent HAY_FRIES = builder(1, 5).build();
|
||||
FoodComponent SALAD = builder(4, 2).build();
|
||||
FoodComponent CIDER = builder(4, 2).alwaysEdible().build();
|
||||
FoodComponent RANDOM_FOLIAGE = builder(2, 1).build();
|
||||
|
||||
FoodComponent JUICE = builder(2, 2).alwaysEdible().build();
|
||||
FoodComponent BURNED_JUICE = builder(3, 1).build();
|
||||
FoodComponent WORMS = builder(1, 0).alwaysEdible().build();
|
||||
|
||||
FoodComponent RANDOM_FOLIAGE = builder(2, 1).build();
|
||||
FoodComponent INSECTS = builder(1, 0).alwaysEdible().build();
|
||||
|
||||
FoodComponent CEREAL = builder(9, 0.8F).build();
|
||||
FoodComponent SUGAR = builder(20, -2).build();
|
||||
|
|
|
@ -20,6 +20,6 @@ import net.minecraft.world.World;
|
|||
abstract class MixinItem implements ToxicHolder {
|
||||
@Inject(method = "appendTooltip", at = @At("RETURN"))
|
||||
private void onAppendTooltip(ItemStack stack, @Nullable World world, List<Text> tooltip, TooltipContext context, CallbackInfo into) {
|
||||
getToxic().ifPresent(t -> tooltip.add(t.getAilmentFor(MinecraftClient.getInstance().player).getToxicity().getTooltip()));
|
||||
getToxic().ifPresent(t -> t.getAilmentFor(MinecraftClient.getInstance().player).appendTooltip(tooltip, context));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -11,47 +11,17 @@ import net.minecraft.util.Identifier;
|
|||
import net.minecraft.util.registry.Registry;
|
||||
|
||||
public class CustomStatusEffect extends StatusEffect {
|
||||
private final boolean instant;
|
||||
private final int rate;
|
||||
private final Direct direct;
|
||||
private final Indirect indirect;
|
||||
|
||||
private int tickDelay = 40;
|
||||
|
||||
@NotNull
|
||||
private DirectEffect direct = DirectEffect.NONE;
|
||||
|
||||
@NotNull
|
||||
private IndirectEffect indirect = IndirectEffect.NONE;
|
||||
|
||||
public CustomStatusEffect(Identifier id, StatusEffectType type, int color) {
|
||||
public CustomStatusEffect(StatusEffectType type, int color, int rate, boolean instant, Direct direct, Indirect indirect) {
|
||||
super(type, color);
|
||||
|
||||
Registry.register(Registry.STATUS_EFFECT, id, this);
|
||||
}
|
||||
|
||||
public CustomStatusEffect setSilent() {
|
||||
return this;
|
||||
}
|
||||
|
||||
public CustomStatusEffect direct(@NotNull DirectEffect applicator) {
|
||||
this.direct = applicator;
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
public CustomStatusEffect indirect(@NotNull IndirectEffect applicator) {
|
||||
this.indirect = applicator;
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
|
||||
public CustomStatusEffect setTickDelay(int delay) {
|
||||
tickDelay = delay;
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
public CustomStatusEffect setEffectiveness(double effectiveness) {
|
||||
|
||||
return this;
|
||||
this.direct = direct;
|
||||
this.rate = rate;
|
||||
this.indirect = indirect;
|
||||
this.instant = instant;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -66,32 +36,74 @@ public class CustomStatusEffect extends StatusEffect {
|
|||
|
||||
@Override
|
||||
public boolean isInstant() {
|
||||
return tickDelay > 0;
|
||||
return instant;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean canApplyUpdateEffect(int duration, int amplifier) {
|
||||
if (!isInstant()) {
|
||||
int i = tickDelay >> amplifier;
|
||||
|
||||
if (i > 0) {
|
||||
return duration % i == 0;
|
||||
}
|
||||
if (isInstant()) {
|
||||
return duration > 0;
|
||||
}
|
||||
|
||||
return duration > 0;
|
||||
int i = rate >> amplifier;
|
||||
return i <= 0 || duration % i == 0;
|
||||
}
|
||||
|
||||
public static class Builder {
|
||||
private final Identifier id;
|
||||
private final StatusEffectType type;
|
||||
private final int color;
|
||||
|
||||
private boolean instant;
|
||||
private int rate = 40;
|
||||
|
||||
@NotNull
|
||||
private Direct direct = Direct.NONE;
|
||||
|
||||
@NotNull
|
||||
private Indirect indirect = Indirect.NONE;
|
||||
|
||||
public Builder(Identifier id, StatusEffectType type, int color) {
|
||||
this.id = id;
|
||||
this.type = type;
|
||||
this.color = color;
|
||||
}
|
||||
|
||||
public Builder instant() {
|
||||
instant = true;
|
||||
return this;
|
||||
}
|
||||
|
||||
public Builder rate(int rate) {
|
||||
this.rate = rate;
|
||||
return this;
|
||||
}
|
||||
|
||||
public Builder direct(@NotNull Direct applicator) {
|
||||
this.direct = applicator;
|
||||
return this;
|
||||
}
|
||||
|
||||
public Builder indirect(@NotNull Indirect applicator) {
|
||||
this.indirect = applicator;
|
||||
return this;
|
||||
}
|
||||
|
||||
public StatusEffect build() {
|
||||
return Registry.register(Registry.STATUS_EFFECT, id, new CustomStatusEffect(type, color, rate, instant, direct, indirect));
|
||||
}
|
||||
}
|
||||
|
||||
@FunctionalInterface
|
||||
public interface DirectEffect {
|
||||
DirectEffect NONE = (p, e, i) -> {};
|
||||
public interface Direct {
|
||||
Direct NONE = (p, e, i) -> {};
|
||||
|
||||
void perform(StatusEffect effect, LivingEntity target, int amplifier);
|
||||
}
|
||||
|
||||
@FunctionalInterface
|
||||
public interface IndirectEffect {
|
||||
IndirectEffect NONE = (p, s, a, t, A, d) -> {};
|
||||
public interface Indirect {
|
||||
Indirect NONE = (p, s, a, t, A, d) -> {};
|
||||
|
||||
void perform(StatusEffect effect, @Nullable Entity source, @Nullable Entity attacker, LivingEntity target, int amplifier, double distance);
|
||||
}
|
||||
|
|
|
@ -74,7 +74,7 @@
|
|||
"unicopia.effect.tribe.stage.determination": "As your bones realign you are filled by determination.",
|
||||
"unicopia.effect.tribe.stage.resurection": "Knowing you will return to this world as a %s",
|
||||
|
||||
"effect.food_poisoning": "Food Poisoning",
|
||||
"effect.unicopia.food_poisoning": "Food Poisoning",
|
||||
|
||||
"player.reachDistance": "Reach Distance",
|
||||
"player.miningSpeed": "Mining Speed",
|
||||
|
@ -112,6 +112,8 @@
|
|||
"item.minecraft.lingering_potion.effect.unicopia.tribe_swap_bat": "Lingering Potion of Bat Pony Metamorphosis",
|
||||
"item.minecraft.tipped_arrow.effect.unicopia.tribe_swap_bat": "Arrow of Bat Pony Metamorphosis",
|
||||
|
||||
"potion.potency.6": "VII",
|
||||
|
||||
"spell.unicopia.frost": "Frost",
|
||||
"spell.unicopia.frost.lore": "Ice I",
|
||||
|
||||
|
|
|
@ -0,0 +1,6 @@
|
|||
{
|
||||
"replace": false,
|
||||
"values": [
|
||||
"minecraft:fermented_spider_eye"
|
||||
]
|
||||
}
|
|
@ -0,0 +1,7 @@
|
|||
{
|
||||
"replace": false,
|
||||
"values": [
|
||||
"minecraft:spider_eye",
|
||||
"unicopia:wheat_worms"
|
||||
]
|
||||
}
|
|
@ -0,0 +1,6 @@
|
|||
{
|
||||
"replace": false,
|
||||
"values": [
|
||||
"minecraft:rotten_flesh"
|
||||
]
|
||||
}
|
Loading…
Reference in a new issue