Skip to content

Commit

Permalink
Merge branch '1.20.6' into 1.21.1
Browse files Browse the repository at this point in the history
* 1.20.6:
  Updated traded item
  removed unused methods
  Disable custom illusioner texture when illusioner is disabled
  Fixed trades, moved totem code, fixed mauler inf exp bug
  • Loading branch information
Faboslav committed Jan 19, 2025
2 parents 155b818 + 016c216 commit 8b4b098
Show file tree
Hide file tree
Showing 10 changed files with 276 additions and 230 deletions.
5 changes: 5 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,8 @@
## 3.0.7

- Fixed beekeeper villager trades
- Fixed infinite mauler exp feed (again)

## 3.0.6

- Fixed strong potion of reaching duration
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -276,8 +276,11 @@ public ActionResult interactMob(PlayerEntity player, Hand hand) {
!this.hasAngerTime()
&& (
(
itemStack.hasEnchantments()
|| itemInHand == Items.ENCHANTED_BOOK
!itemStack.isEmpty()
&& (
itemStack.hasEnchantments()
|| itemInHand == Items.ENCHANTED_BOOK
)
)
)
) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
import com.faboslav.friendsandfoes.common.init.registry.RegistryEntry;
import com.faboslav.friendsandfoes.common.init.registry.ResourcefulRegistries;
import com.faboslav.friendsandfoes.common.init.registry.ResourcefulRegistry;
import com.faboslav.friendsandfoes.common.util.TradeOffersUtil;
import com.faboslav.friendsandfoes.common.util.BasicTradeOffer;
import com.google.common.collect.ImmutableSet;
import net.minecraft.item.Items;
import net.minecraft.registry.Registries;
Expand All @@ -24,15 +24,17 @@ public final class FriendsAndFoesVillagerProfessions

public static void registerVillagerTrades(RegisterVillagerTradesEvent event) {
if (event.type() == BEEKEEPER.get()) {
event.register(1, new TradeOffersUtil.BuyForOneEmeraldFactory(FriendsAndFoesItems.BUTTERCUP.get(), 10, 16, 2));
event.register(1, new TradeOffersUtil.BuyForOneEmeraldFactory(Items.DANDELION, 10, 16, 2));
event.register(1, new TradeOffersUtil.BuyForOneEmeraldFactory(Items.SUNFLOWER, 10, 16, 2));
event.register(2, new TradeOffersUtil.BuyForOneEmeraldFactory(Items.GLASS_BOTTLE, 9, 12, 10));
event.register(2, new TradeOffersUtil.SellItemFactory(Items.HONEY_BOTTLE, 3, 1, 12, 5));
event.register(3, new TradeOffersUtil.BuyForOneEmeraldFactory(Items.SHEARS, 1, 12, 20));
event.register(3, new TradeOffersUtil.SellItemFactory(Items.HONEY_BLOCK, 10, 1, 12, 10));
event.register(4, new TradeOffersUtil.SellItemFactory(Items.HONEYCOMB, 4, 1, 12, 15));
event.register(5, new TradeOffersUtil.SellItemFactory(Items.HONEYCOMB_BLOCK, 12, 1, 12, 30));
event.register(1, new BasicTradeOffer(FriendsAndFoesItems.BUTTERCUP.get(), Items.EMERALD, 10, 1, 16, 2, 0.05F));
event.register(1, new BasicTradeOffer(Items.DANDELION, Items.EMERALD, 10, 1, 16, 2, 0.05F));
event.register(1, new BasicTradeOffer(Items.SUNFLOWER, Items.EMERALD, 10, 1, 16, 2, 0.05F));
event.register(2, new BasicTradeOffer(Items.GLASS_BOTTLE, Items.EMERALD, 9, 1, 12, 10, 0.05F));
event.register(2, new BasicTradeOffer(Items.EMERALD, Items.HONEY_BOTTLE, 3, 1, 12, 5, 0.05F));
event.register(3, new BasicTradeOffer(Items.SHEARS, Items.EMERALD, 1, 1, 12, 20, 0.05F));
event.register(3, new BasicTradeOffer(Items.EMERALD, Items.HONEY_BLOCK, 10, 1, 12, 10, 0.05F));
event.register(4, new BasicTradeOffer(Items.EMERALD, Items.HONEYCOMB, 4, 1, 12, 15, 0.05F));
event.register(4, new BasicTradeOffer(Items.EMERALD, Items.HONEYCOMB_BLOCK, 12, 1, 12, 15, 0.05F));
event.register(5, new BasicTradeOffer(Items.EMERALD, Items.BEEHIVE, 10, 1, 3, 30, 0.05F));
event.register(5, new BasicTradeOffer(Items.EMERALD, Items.BEE_NEST, 20, 1, 3, 30, 0.05F));
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -69,10 +69,6 @@ public FeatureSet getRequiredFeatures() {
return getEntityType(ItemStack.EMPTY).getRequiredFeatures();
}

protected EntityType<?> getDefaultType() {
return this.entityType.get();
}

public static void onSetup(SetupEvent event) {
var spawnEggMap = SpawnEggItemAccessor.variantsandventures$getSpawnEggs();
for (var entry : DispenserAddedSpawnEgg.SPAWN_EGGS) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
import net.minecraft.client.render.entity.model.IllagerEntityModel;
import net.minecraft.client.util.math.MatrixStack;
import net.minecraft.entity.mob.IllusionerEntity;
import net.minecraft.util.Identifier;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
Expand All @@ -20,6 +21,8 @@
@Mixin({IllusionerEntityRenderer.class})
public abstract class IllusionerEntityRendererMixin extends IllagerEntityRenderer<IllusionerEntity>
{
private final Identifier FRIENDSANDFOES_TEXTURE = FriendsAndFoes.makeID("textures/entity/illager/illusioner.png");

protected IllusionerEntityRendererMixin(
EntityRendererFactory.Context ctx,
IllagerEntityModel<IllusionerEntity> model,
Expand Down Expand Up @@ -61,4 +64,18 @@ protected void friendsandfoes_isVisible(
callbackInfo.setReturnValue(super.isVisible(illusioner));
}
}

@Inject(
at = @At("HEAD"),
method = "getTexture(Lnet/minecraft/entity/mob/IllusionerEntity;)Lnet/minecraft/util/Identifier;",
cancellable = true
)
protected void friendsandfoes_getTexture(
IllusionerEntity illusionerEntity,
CallbackInfoReturnable<Identifier> cir
) {
if (FriendsAndFoes.getConfig().enableIllusioner) {
cir.setReturnValue(FRIENDSANDFOES_TEXTURE);
}
}
}
Original file line number Diff line number Diff line change
@@ -1,36 +1,27 @@
package com.faboslav.friendsandfoes.common.mixin;

import com.faboslav.friendsandfoes.common.entity.PlayerIllusionEntity;
import com.faboslav.friendsandfoes.common.init.FriendsAndFoesEntityTypes;
import com.faboslav.friendsandfoes.common.init.FriendsAndFoesItems;
import com.faboslav.friendsandfoes.common.init.FriendsAndFoesSoundEvents;
import com.faboslav.friendsandfoes.common.modcompat.ModChecker;
import com.faboslav.friendsandfoes.common.modcompat.ModCompat;
import com.faboslav.friendsandfoes.common.network.packet.TotemEffectPacket;
import com.faboslav.friendsandfoes.common.tag.FriendsAndFoesTags;
import com.faboslav.friendsandfoes.common.util.TotemUtil;
import net.minecraft.advancement.criterion.Criteria;
import net.minecraft.entity.Entity;
import net.minecraft.entity.EntityType;
import net.minecraft.entity.EquipmentSlot;
import net.minecraft.entity.LivingEntity;
import net.minecraft.entity.ai.TargetPredicate;
import net.minecraft.entity.damage.DamageSource;
import net.minecraft.entity.damage.DamageTypes;
import net.minecraft.entity.effect.StatusEffectInstance;
import net.minecraft.entity.effect.StatusEffects;
import net.minecraft.entity.mob.MobEntity;
import net.minecraft.entity.player.PlayerEntity;
import net.minecraft.item.Item;
import net.minecraft.item.ItemStack;
import net.minecraft.particle.ParticleTypes;
import net.minecraft.particle.SimpleParticleType;
import net.minecraft.registry.tag.FluidTags;
import net.minecraft.server.network.ServerPlayerEntity;
import net.minecraft.server.world.ServerWorld;
import net.minecraft.stat.Stats;
import net.minecraft.util.Hand;
import net.minecraft.util.math.MathHelper;
import net.minecraft.util.math.Vec3d;
import net.minecraft.world.World;
import org.jetbrains.annotations.Nullable;
import org.spongepowered.asm.mixin.Mixin;
Expand All @@ -40,25 +31,12 @@
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Objects;
import java.util.function.Predicate;

@Mixin(PlayerEntity.class)
public abstract class PlayerEntityMixin extends LivingEntity
{
private static final int MAX_ILLUSIONS_COUNT = 9;
private static final int ILLUSION_LIFETIME_TICKS = 600;
private static final int NEGATIVE_EFFECT_TICKS = 400;
private static final int POSITIVE_EFFECT_TICKS = 200;
private static final Predicate<LivingEntity> FREEZE_FILTER = (entity) -> {
return !(entity instanceof PlayerEntity) || !((PlayerEntity) entity).isCreative();
};
private static final TargetPredicate FREEZE_TARGET_PREDICATE = TargetPredicate.createNonAttackable().ignoreDistanceScalingFactor().ignoreVisibility().setPredicate(FREEZE_FILTER);
private static final TargetPredicate ATTACK_TARGET_PREDICATE = TargetPredicate.createNonAttackable().ignoreDistanceScalingFactor().ignoreVisibility();

protected PlayerEntityMixin(EntityType<? extends LivingEntity> entityType, World world) {
super(entityType, world);
}
Expand All @@ -69,30 +47,6 @@ protected PlayerEntityMixin(EntityType<? extends LivingEntity> entityType, World
@Shadow
public abstract Iterable<ItemStack> getArmorItems();

@Shadow
public double prevCapeX;

@Shadow
public double prevCapeZ;

@Shadow
public double prevCapeY;

@Shadow
public double capeX;

@Shadow
public double capeY;

@Shadow
public double capeZ;

@Shadow
public float prevStrideDistance;

@Shadow
public float strideDistance;

@Inject(
at = @At("TAIL"),
method = "tick"
Expand Down Expand Up @@ -152,10 +106,10 @@ public void friendsandfoes_tryUseTotems(DamageSource source, float amount, Callb
totemItemStack.decrement(1);

if (totemItem == FriendsAndFoesItems.TOTEM_OF_FREEZING.get()) {
this.friendsandfoes_freezeEntities();
this.addStatusEffect(new StatusEffectInstance(StatusEffects.SPEED, POSITIVE_EFFECT_TICKS, 1));
TotemUtil.freezeEntities(player);
this.addStatusEffect(new StatusEffectInstance(StatusEffects.SPEED, TotemUtil.POSITIVE_EFFECT_TICKS, 1));
} else if (totemItem == FriendsAndFoesItems.TOTEM_OF_ILLUSION.get()) {
this.friendsandfoes_createIllusions();
TotemUtil.createIllusions(player);
}
}
}
Expand Down Expand Up @@ -195,167 +149,4 @@ private static ItemStack friendsandfoes_getTotemFromCustomEquipmentSlots(PlayerE
private static boolean friendsandfoes_isTotem(ItemStack itemStack) {
return itemStack.isIn(FriendsAndFoesTags.TOTEMS);
}

private void friendsandfoes_freezeEntities() {
List<LivingEntity> nearbyEntities = this.getWorld().getEntitiesByClass(LivingEntity.class, this.getBoundingBox().expand(9.0), (livingEntity) -> {
return FREEZE_TARGET_PREDICATE.test(this, livingEntity);
});

nearbyEntities.forEach(nearbyEntity -> {
nearbyEntity.setFrozenTicks(NEGATIVE_EFFECT_TICKS);
nearbyEntity.addStatusEffect(new StatusEffectInstance(StatusEffects.SLOWNESS, NEGATIVE_EFFECT_TICKS, 1));
});
}

private void friendsandfoes_createIllusions() {
this.playSound(
FriendsAndFoesSoundEvents.ENTITY_PLAYER_MIRROR_MOVE.get(),
this.getSoundVolume(),
this.getSoundPitch()
);

Vec3d illusionerPosition = this.getPos();
float slice = 2.0F * (float) Math.PI / MAX_ILLUSIONS_COUNT;
int radius = 9;

ArrayList<PlayerIllusionEntity> createdPlayerIllusions = new ArrayList<>();

for (int point = 0; point < MAX_ILLUSIONS_COUNT; ++point) {
float angle = slice * point;
int x = (int) (illusionerPosition.getX() + radius * MathHelper.cos(angle));
int y = (int) illusionerPosition.getY();
int z = (int) (illusionerPosition.getZ() + radius * MathHelper.sin(angle));

PlayerIllusionEntity createdPlayerIllusion = this.friendsandfoes_createIllusion(x, y, z);

if (createdPlayerIllusion != null) {
createdPlayerIllusions.add(createdPlayerIllusion);
}
}

List<MobEntity> nearbyEntities = this.getWorld().getEntitiesByClass(MobEntity.class, this.getBoundingBox().expand(18.0), (mobEntity) -> {
return ATTACK_TARGET_PREDICATE.test(this, mobEntity);
});

nearbyEntities.forEach(nearbyEntity -> {
if (nearbyEntity.getTarget() == this) {
if (!createdPlayerIllusions.isEmpty()) {
nearbyEntity.setAttacking(true);
nearbyEntity.setAttacker(createdPlayerIllusions.get(this.getRandom().nextInt(createdPlayerIllusions.size())));
nearbyEntity.onAttacking(createdPlayerIllusions.get(this.getRandom().nextInt(createdPlayerIllusions.size())));
}

nearbyEntity.addStatusEffect(new StatusEffectInstance(StatusEffects.BLINDNESS, NEGATIVE_EFFECT_TICKS, 1));
}
});

if (!createdPlayerIllusions.isEmpty()) {
var illusionToReplace = createdPlayerIllusions.get(this.getRandom().nextInt(createdPlayerIllusions.size()));
boolean teleportResult = this.friendsandfoes_tryToTeleport(illusionToReplace.getBlockX(), illusionToReplace.getBlockY(), illusionToReplace.getBlockZ());

if (teleportResult) {
this.friendsandfoes_spawnCloudParticles();
}

var attacker = illusionToReplace.getAttacker();

if (attacker != null) {
illusionToReplace.setAttacking(null);
illusionToReplace.setAttacker(null);
illusionToReplace.onAttacking(null);
}

illusionToReplace.discard();
}

this.addStatusEffect(new StatusEffectInstance(StatusEffects.INVISIBILITY, POSITIVE_EFFECT_TICKS));
}

@Nullable
private PlayerIllusionEntity friendsandfoes_createIllusion(int x, int y, int z) {
PlayerIllusionEntity playerIllusion = FriendsAndFoesEntityTypes.PLAYER_ILLUSION.get().create(this.getWorld());

if (playerIllusion == null) {
return null;
}

playerIllusion.prevCapeX = this.prevCapeX;
playerIllusion.prevCapeY = this.prevCapeY;
playerIllusion.prevCapeZ = this.prevCapeZ;
playerIllusion.capeX = this.capeX;
playerIllusion.capeY = this.capeY;
playerIllusion.capeZ = this.capeZ;
playerIllusion.prevStrideDistance = this.prevStrideDistance;
playerIllusion.strideDistance = this.strideDistance;

playerIllusion.equipStack(EquipmentSlot.MAINHAND, getMainHandStack().copy());
playerIllusion.equipStack(EquipmentSlot.OFFHAND, getOffHandStack().copy());
this.getArmorItems().forEach((item) -> playerIllusion.tryEquip(item.copy()));

playerIllusion.setHealth(this.getMaxHealth());
playerIllusion.copyPositionAndRotation(this);
float randomYaw = 360.F * this.getRandom().nextFloat();
playerIllusion.prevYaw = randomYaw;
playerIllusion.setYaw(randomYaw);
playerIllusion.prevBodyYaw = randomYaw;
playerIllusion.setBodyYaw(randomYaw);
playerIllusion.prevHeadYaw = randomYaw;
playerIllusion.setHeadYaw(randomYaw);
playerIllusion.setPlayerUuid(this.getUuid());
playerIllusion.setPlayer((PlayerEntity) (Object) this);
playerIllusion.setTicksUntilDespawn(ILLUSION_LIFETIME_TICKS);

boolean teleportResult = playerIllusion.tryToTeleport(x, y, z);

if (teleportResult) {
getWorld().spawnEntity(playerIllusion);
playerIllusion.spawnCloudParticles();
}

return playerIllusion;
}

private boolean friendsandfoes_tryToTeleport(int x, int y, int z) {
y -= 8;
double bottomY = Math.max(y, getWorld().getBottomY());
double topY = Math.min(bottomY + 16, ((ServerWorld) this.getWorld()).getLogicalHeight() - 1);

for (int i = 0; i < 16; ++i) {
y = (int) MathHelper.clamp(y + 1, bottomY, topY);
boolean teleportResult = this.teleport(x, y, z, false);

if (teleportResult) {
return true;
}
}

return false;
}

private void friendsandfoes_spawnCloudParticles() {
this.friendsandfoes_spawnParticles(ParticleTypes.CLOUD, 16);
}

private void friendsandfoes_spawnParticles(
SimpleParticleType particleType,
int amount
) {
if (this.getWorld().isClient()) {
return;
}

for (int i = 0; i < amount; i++) {
((ServerWorld) this.getEntityWorld()).spawnParticles(
particleType,
this.getParticleX(0.5D),
this.getRandomBodyY() + 0.5D,
this.getParticleZ(0.5D),
1,
0.0D,
0.0D,
0.0D,
0.0D
);
}
}
}
Loading

0 comments on commit 8b4b098

Please sign in to comment.