Skip to content

Commit

Permalink
Hammer Cod, Whacker Salmon, Mixin Extra usage, and FlounderFest spawn…
Browse files Browse the repository at this point in the history
… rate changes!

FEAT: Added Hammer Cod, a cod holding a giant toy hammer which does a lot damage!
FEAT: Added Whacker Salmon, a salmon holding a punching glove which does a lot of knockback!
REFACTOR: Updated ClientWorldMixin to ModifyReturnValue from MixinExtras
REFACTOR: Updated FlounderFest spawn rates to be slightly more chaotic, but also more balanced.
  • Loading branch information
Superkat32 committed Dec 24, 2023
1 parent b21b161 commit 20302c4
Show file tree
Hide file tree
Showing 22 changed files with 939 additions and 34 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,10 @@
import net.superkat.flutterandflounder.entity.FlutterAndFlounderEntities;
import net.superkat.flutterandflounder.entity.client.cod.CodAutomobileRenderer;
import net.superkat.flutterandflounder.entity.client.cod.FlyingCodRenderer;
import net.superkat.flutterandflounder.entity.client.cod.HammerCodRenderer;
import net.superkat.flutterandflounder.entity.client.salmon.FlyingSalmonRenderer;
import net.superkat.flutterandflounder.entity.client.salmon.SalmonShipRenderer;
import net.superkat.flutterandflounder.entity.client.salmon.WhackerSalmonRenderer;
import net.superkat.flutterandflounder.network.FlutterAndFlounderPackets;
import net.superkat.flutterandflounder.rendering.FlutterAndFlounderRendering;

Expand All @@ -19,6 +21,8 @@ public void onInitializeClient() {
//bosses
EntityRendererRegistry.register(FlutterAndFlounderEntities.COD_AUTOMOBILE, CodAutomobileRenderer::new);
EntityRendererRegistry.register(FlutterAndFlounderEntities.SALMON_SHIP, SalmonShipRenderer::new);
EntityRendererRegistry.register(FlutterAndFlounderEntities.HAMMER_COD, HammerCodRenderer::new);
EntityRendererRegistry.register(FlutterAndFlounderEntities.WHACKER_SALMON, WhackerSalmonRenderer::new);

FlutterAndFlounderPackets.registerPackets();

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,10 @@
import net.superkat.flutterandflounder.entity.FlutterAndFlounderEntities;
import net.superkat.flutterandflounder.entity.custom.cod.CodAutomobileEntity;
import net.superkat.flutterandflounder.entity.custom.cod.FlyingCodEntity;
import net.superkat.flutterandflounder.entity.custom.cod.HammerCodEntity;
import net.superkat.flutterandflounder.entity.custom.salmon.FlyingSalmonEntity;
import net.superkat.flutterandflounder.entity.custom.salmon.SalmonShipEntity;
import net.superkat.flutterandflounder.entity.custom.salmon.WhackerSalmonEntity;
import net.superkat.flutterandflounder.flounderfest.command.FlounderFestCommand;
import net.superkat.flutterandflounder.item.FlutterAndFlounderItems;
import org.slf4j.Logger;
Expand All @@ -31,6 +33,8 @@ public void onInitialize() {
//bosses
FabricDefaultAttributeRegistry.register(FlutterAndFlounderEntities.COD_AUTOMOBILE, CodAutomobileEntity.createAttributes());
FabricDefaultAttributeRegistry.register(FlutterAndFlounderEntities.SALMON_SHIP, SalmonShipEntity.createAttributes());
FabricDefaultAttributeRegistry.register(FlutterAndFlounderEntities.HAMMER_COD, HammerCodEntity.createAttributes());
FabricDefaultAttributeRegistry.register(FlutterAndFlounderEntities.WHACKER_SALMON, WhackerSalmonEntity.createAttributes());

CommandRegistrationCallback.EVENT.register(((dispatcher, registryAccess, environment) -> FlounderFestCommand.register(dispatcher)));

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,10 @@
import net.minecraft.util.Identifier;
import net.superkat.flutterandflounder.entity.custom.cod.CodAutomobileEntity;
import net.superkat.flutterandflounder.entity.custom.cod.FlyingCodEntity;
import net.superkat.flutterandflounder.entity.custom.cod.HammerCodEntity;
import net.superkat.flutterandflounder.entity.custom.salmon.FlyingSalmonEntity;
import net.superkat.flutterandflounder.entity.custom.salmon.SalmonShipEntity;
import net.superkat.flutterandflounder.entity.custom.salmon.WhackerSalmonEntity;

import static net.superkat.flutterandflounder.FlutterAndFlounderMain.MOD_ID;

Expand Down Expand Up @@ -45,4 +47,18 @@ public class FlutterAndFlounderEntities {
.dimensions(EntityDimensions.fixed(1.5f, 1f)).build()
);

public static final EntityType<HammerCodEntity> HAMMER_COD = Registry.register(
Registries.ENTITY_TYPE,
new Identifier(MOD_ID, "hammercod"),
FabricEntityTypeBuilder.create(SpawnGroup.MONSTER, HammerCodEntity::new)
.dimensions(EntityDimensions.fixed(2f, 3.2f)).build()
);

public static final EntityType<WhackerSalmonEntity> WHACKER_SALMON = Registry.register(
Registries.ENTITY_TYPE,
new Identifier(MOD_ID, "whacker"),
FabricEntityTypeBuilder.create(SpawnGroup.MONSTER, WhackerSalmonEntity::new)
.dimensions(EntityDimensions.fixed(1.5f, 0.7f)).build()
);

}
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
import net.superkat.flutterandflounder.entity.custom.cod.CodAutomobileEntity;
import software.bernie.geckolib.renderer.GeoEntityRenderer;

public class CodAutomobileRenderer extends GeoEntityRenderer<CodAutomobileEntity> {
public class CodAutomobileRenderer extends GeoEntityRenderer<CodAutomobileEntity> {
public CodAutomobileRenderer(EntityRendererFactory.Context renderManager) {
super(renderManager, new CodAutomobileModel());
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
package net.superkat.flutterandflounder.entity.client.cod;

import net.minecraft.util.Identifier;
import net.superkat.flutterandflounder.FlutterAndFlounderMain;
import net.superkat.flutterandflounder.entity.custom.cod.HammerCodEntity;
import software.bernie.geckolib.model.DefaultedEntityGeoModel;

public class HammerCodModel extends DefaultedEntityGeoModel<HammerCodEntity> {
public HammerCodModel() {
super(new Identifier(FlutterAndFlounderMain.MOD_ID, "hammercod"), false);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
package net.superkat.flutterandflounder.entity.client.cod;

import net.minecraft.client.render.entity.EntityRendererFactory;
import net.superkat.flutterandflounder.entity.custom.cod.HammerCodEntity;
import software.bernie.geckolib.renderer.GeoEntityRenderer;

public class HammerCodRenderer extends GeoEntityRenderer<HammerCodEntity> {
public HammerCodRenderer(EntityRendererFactory.Context renderManager) {
super(renderManager, new HammerCodModel());
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
package net.superkat.flutterandflounder.entity.client.salmon;

import net.minecraft.util.Identifier;
import net.superkat.flutterandflounder.FlutterAndFlounderMain;
import net.superkat.flutterandflounder.entity.custom.salmon.WhackerSalmonEntity;
import software.bernie.geckolib.model.DefaultedEntityGeoModel;

public class WhackerSalmonModel extends DefaultedEntityGeoModel<WhackerSalmonEntity> {
public WhackerSalmonModel() {
super(new Identifier(FlutterAndFlounderMain.MOD_ID, "whacker"), true);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
package net.superkat.flutterandflounder.entity.client.salmon;

import net.minecraft.client.render.entity.EntityRendererFactory;
import net.superkat.flutterandflounder.entity.custom.salmon.WhackerSalmonEntity;
import software.bernie.geckolib.renderer.GeoEntityRenderer;

public class WhackerSalmonRenderer extends GeoEntityRenderer<WhackerSalmonEntity> {
public WhackerSalmonRenderer(EntityRendererFactory.Context renderManager) {
super(renderManager, new WhackerSalmonModel());
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package net.superkat.flutterandflounder.entity.custom;

import net.minecraft.entity.EntityType;
import net.minecraft.entity.damage.DamageSource;
import net.minecraft.entity.mob.HostileEntity;
import net.minecraft.server.world.ServerWorld;
import net.minecraft.util.math.BlockPos;
Expand All @@ -15,9 +16,17 @@ protected CommonBossFish(EntityType<? extends HostileEntity> entityType, World w
}

public void updateFlounderFestQuota(ServerWorld world, BlockPos pos) {
FlounderFest flounderFest = FlounderFestApi.getFlounderFestAt(world, pos, 100);
FlounderFest flounderFest = FlounderFestApi.getFlounderFestAt(world, pos, 2000);
if(flounderFest != null) {
flounderFest.updateQuota(1);
}
}

@Override
public void onDeath(DamageSource damageSource) {
if(!this.getWorld().isClient) {
updateFlounderFestQuota((ServerWorld) this.getWorld(), this.getBlockPos());
}
super.onDeath(damageSource);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -7,11 +7,9 @@
import net.minecraft.entity.ai.goal.WanderAroundFarGoal;
import net.minecraft.entity.attribute.DefaultAttributeContainer;
import net.minecraft.entity.attribute.EntityAttributes;
import net.minecraft.entity.damage.DamageSource;
import net.minecraft.entity.mob.HostileEntity;
import net.minecraft.entity.mob.MobEntity;
import net.minecraft.entity.player.PlayerEntity;
import net.minecraft.server.world.ServerWorld;
import net.minecraft.world.World;
import net.superkat.flutterandflounder.entity.custom.CommonBossFish;
import software.bernie.geckolib.core.animatable.instance.AnimatableInstanceCache;
Expand Down Expand Up @@ -67,11 +65,4 @@ protected void initGoals() {
this.targetSelector.add(1, new ActiveTargetGoal<>(this, PlayerEntity.class, true));
}

@Override
public void onDeath(DamageSource damageSource) {
if(!this.getWorld().isClient) {
updateFlounderFestQuota((ServerWorld) this.getWorld(), this.getBlockPos());
}
super.onDeath(damageSource);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,98 @@
package net.superkat.flutterandflounder.entity.custom.cod;

import net.minecraft.entity.EntityType;
import net.minecraft.entity.ai.TargetPredicate;
import net.minecraft.entity.ai.goal.ActiveTargetGoal;
import net.minecraft.entity.ai.goal.LookAtEntityGoal;
import net.minecraft.entity.ai.goal.MeleeAttackGoal;
import net.minecraft.entity.attribute.DefaultAttributeContainer;
import net.minecraft.entity.attribute.EntityAttributes;
import net.minecraft.entity.mob.HostileEntity;
import net.minecraft.entity.mob.MobEntity;
import net.minecraft.entity.player.PlayerEntity;
import net.minecraft.sound.SoundCategory;
import net.minecraft.sound.SoundEvents;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.Box;
import net.minecraft.world.World;
import net.superkat.flutterandflounder.entity.custom.CommonBossFish;
import software.bernie.geckolib.core.animatable.instance.AnimatableInstanceCache;
import software.bernie.geckolib.core.animation.AnimatableManager;
import software.bernie.geckolib.core.animation.AnimationController;
import software.bernie.geckolib.core.animation.AnimationState;
import software.bernie.geckolib.core.animation.RawAnimation;
import software.bernie.geckolib.core.object.PlayState;
import software.bernie.geckolib.util.GeckoLibUtil;

import java.util.List;

public class HammerCodEntity extends CommonBossFish {
protected static final RawAnimation IDLE_ANIM = RawAnimation.begin().thenLoop("animation.hammercod.idle");
protected static final RawAnimation ATTACK_ANIM = RawAnimation.begin().thenLoop("animation.hammercod.attack");
private final AnimatableInstanceCache geoCache = GeckoLibUtil.createInstanceCache(this);
public HammerCodEntity(EntityType<? extends HostileEntity> entityType, World world) {
super(entityType, world);
}

@Override
public void registerControllers(AnimatableManager.ControllerRegistrar controllers) {
controllers.add(new AnimationController<>(this, "controller", 5, this::animController)
.setParticleKeyframeHandler(state -> {
BlockPos pos = state.getAnimatable().getBlockPos();
BlockPos particlePos = pos.offset(state.getAnimatable().getHorizontalFacing(), 2);
this.getWorld().addBlockBreakParticles(particlePos, state.getAnimatable().getSteppingBlockState());
}).setSoundKeyframeHandler(state -> {
Box box = state.getAnimatable().getBoundingBox().expand(15.0, 8.0, 15.0);
List<PlayerEntity> players = this.getWorld().getPlayers(TargetPredicate.createNonAttackable().setBaseMaxDistance(15), state.getAnimatable(), box);

for(PlayerEntity player : players) {
player.playSound(SoundEvents.ENTITY_PLAYER_ATTACK_CRIT, SoundCategory.HOSTILE, 1, 0.7f);
}
})
);
}

// private TargetPredicate isInHammerHearingRange() {
// return player -> {
// double distance = squaredDistanceTo(player);
// return distance <= 15;
// };
// }

protected<E extends HammerCodEntity> PlayState animController(final AnimationState<E> event) {
if(this.isAttacking()) {
return event.setAndContinue(ATTACK_ANIM);
} else if (!event.isMoving()) {
return event.setAndContinue(IDLE_ANIM);
} else {
return PlayState.STOP;
}
}

@Override
public AnimatableInstanceCache getAnimatableInstanceCache() {
return geoCache;
}

private boolean shouldHearHammerSound(PlayerEntity player) {
double distance = squaredDistanceTo(player);
return distance <= 15;
}

public static DefaultAttributeContainer.Builder createAttributes() {
return MobEntity.createMobAttributes()
.add(EntityAttributes.GENERIC_MAX_HEALTH, 15)
.add(EntityAttributes.GENERIC_MOVEMENT_SPEED, 0.30)
.add(EntityAttributes.GENERIC_ATTACK_DAMAGE, 10)
.add(EntityAttributes.GENERIC_ATTACK_KNOCKBACK, 5)
.add(EntityAttributes.GENERIC_KNOCKBACK_RESISTANCE, 2)
.add(EntityAttributes.GENERIC_FOLLOW_RANGE, 48);
}

@Override
protected void initGoals() {
this.goalSelector.add(1, new MeleeAttackGoal(this, 1, false));
this.goalSelector.add(2, new LookAtEntityGoal(this, PlayerEntity.class, 15f, 0.5f));
this.targetSelector.add(1, new ActiveTargetGoal<>(this, PlayerEntity.class, true));
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,9 @@
import net.minecraft.entity.ai.goal.LookAtEntityGoal;
import net.minecraft.entity.attribute.DefaultAttributeContainer;
import net.minecraft.entity.attribute.EntityAttributes;
import net.minecraft.entity.damage.DamageSource;
import net.minecraft.entity.mob.HostileEntity;
import net.minecraft.entity.mob.MobEntity;
import net.minecraft.entity.player.PlayerEntity;
import net.minecraft.server.world.ServerWorld;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World;
import net.superkat.flutterandflounder.entity.custom.CommonBossFish;
Expand Down Expand Up @@ -102,14 +100,6 @@ public void tick() {
}
}

@Override
public void onDeath(DamageSource damageSource) {
if(!this.getWorld().isClient) {
updateFlounderFestQuota((ServerWorld) this.getWorld(), this.getBlockPos());
}
super.onDeath(damageSource);
}

public void setWarningTicks(int warningTicks) {
this.warningTicks = warningTicks;
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
package net.superkat.flutterandflounder.entity.custom.salmon;

import net.minecraft.entity.EntityType;
import net.minecraft.entity.ai.goal.ActiveTargetGoal;
import net.minecraft.entity.ai.goal.LookAtEntityGoal;
import net.minecraft.entity.ai.goal.MeleeAttackGoal;
import net.minecraft.entity.ai.goal.WanderAroundFarGoal;
import net.minecraft.entity.attribute.DefaultAttributeContainer;
import net.minecraft.entity.attribute.EntityAttributes;
import net.minecraft.entity.mob.HostileEntity;
import net.minecraft.entity.mob.MobEntity;
import net.minecraft.entity.player.PlayerEntity;
import net.minecraft.world.World;
import net.superkat.flutterandflounder.entity.custom.CommonBossFish;
import software.bernie.geckolib.core.animatable.instance.AnimatableInstanceCache;
import software.bernie.geckolib.core.animation.AnimatableManager;
import software.bernie.geckolib.core.animation.AnimationController;
import software.bernie.geckolib.core.animation.AnimationState;
import software.bernie.geckolib.core.animation.RawAnimation;
import software.bernie.geckolib.core.object.PlayState;
import software.bernie.geckolib.util.GeckoLibUtil;

public class WhackerSalmonEntity extends CommonBossFish {
protected static final RawAnimation IDLE_ANIM = RawAnimation.begin().thenLoop("animation.whacker.idle");
protected static final RawAnimation WALK_ANIM = RawAnimation.begin().thenLoop("animation.whacker.walk");
protected static final RawAnimation ATTACK_ANIM = RawAnimation.begin().thenLoop("animation.whacker.attack");
private final AnimatableInstanceCache geoCache = GeckoLibUtil.createInstanceCache(this);
public WhackerSalmonEntity(EntityType<? extends HostileEntity> entityType, World world) {
super(entityType, world);
}

@Override
public void registerControllers(AnimatableManager.ControllerRegistrar controllers) {
controllers.add(new AnimationController<>(this, "controller", 5, this::animController));
}

protected <E extends WhackerSalmonEntity> PlayState animController(final AnimationState<E> event) {
if(this.isAttacking()) {
return event.setAndContinue(ATTACK_ANIM);
} else if (event.isMoving()) {
return event.setAndContinue(WALK_ANIM);
} else {
return event.setAndContinue(IDLE_ANIM);
}
}

@Override
public AnimatableInstanceCache getAnimatableInstanceCache() {
return geoCache;
}

public static DefaultAttributeContainer.Builder createAttributes() {
return MobEntity.createMobAttributes()
.add(EntityAttributes.GENERIC_MAX_HEALTH, 15)
.add(EntityAttributes.GENERIC_MOVEMENT_SPEED, 0.4)
.add(EntityAttributes.GENERIC_ATTACK_DAMAGE, 7)
.add(EntityAttributes.GENERIC_ATTACK_SPEED, 0.3)
.add(EntityAttributes.GENERIC_ATTACK_KNOCKBACK, 5)
.add(EntityAttributes.GENERIC_FOLLOW_RANGE, 48);
}

@Override
protected void initGoals() {
this.goalSelector.add(1, new MeleeAttackGoal(this, 1, false));
this.goalSelector.add(2, new LookAtEntityGoal(this, PlayerEntity.class, 15f, 1f));
this.goalSelector.add(3, new WanderAroundFarGoal(this, 1));
this.targetSelector.add(1, new ActiveTargetGoal<>(this, PlayerEntity.class, true));
}
}
Loading

0 comments on commit 20302c4

Please sign in to comment.