Skip to content

Commit

Permalink
Added compatibility with orpheus' orpheus lyre
Browse files Browse the repository at this point in the history
Improved api-stuff to allow modification of drop rules after drop rules has been handled, based on the entire inventory component
  • Loading branch information
B1n-ry committed Feb 22, 2024
1 parent b1f61cc commit eb23ae4
Show file tree
Hide file tree
Showing 12 changed files with 126 additions and 5 deletions.
3 changes: 3 additions & 0 deletions build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,9 @@ dependencies {
modImplementation "com.terraformersmc:modmenu:${project.modmenu_version}"
modCompileOnly "eu.pb4:common-protection-api:${project.protection_api_version}"

// Extra soulbound/droprule modification mods
modCompileOnly "curse.maven:orpheus-${project.orpheus_version}"

// Inventory Mods
modCompileOnly "dev.emi:trinkets:${project.trinkets_version}"
modCompileOnly "curse.maven:inventorio-${project.inventorio_version}"
Expand Down
3 changes: 3 additions & 0 deletions gradle.properties
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,9 @@ org.gradle.parallel=true
modmenu_version=7.2.2
protection_api_version=1.0.0

# Extra soulbound/drop rule modification mods
orpheus_version=936659:5093826

# Inventory compat
trinkets_version=3.7.1
inventorio_version=491073:4619078
Expand Down
3 changes: 3 additions & 0 deletions src/main/java/com/b1n_ry/yigd/DeathHandler.java
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
import com.b1n_ry.yigd.components.RespawnComponent;
import com.b1n_ry.yigd.config.YigdConfig;
import com.b1n_ry.yigd.data.DeathContext;
import com.b1n_ry.yigd.data.DeathInfoManager;
import com.b1n_ry.yigd.data.DirectionalPos;
import com.b1n_ry.yigd.data.TranslatableDeathMessage;
import com.b1n_ry.yigd.events.AllowGraveGenerationEvent;
Expand Down Expand Up @@ -89,6 +90,8 @@ public void onPlayerDeath(ServerPlayerEntity player, ServerWorld world, Vec3d po
.with(Properties.HORIZONTAL_FACING, direction)
.with(Properties.WATERLOGGED, waterlogged);

respawnComponent.setGraveGenerated(true); // Not guaranteed yet, but only errors can stop it from generating after this point
DeathInfoManager.INSTANCE.markDirty(); // Make sure respawn component is updated

// At this point is where the END_OF_TICK would be implemented, unless it wasn't already so
Yigd.END_OF_TICK.add(() -> {
Expand Down
21 changes: 20 additions & 1 deletion src/main/java/com/b1n_ry/yigd/compat/CompatComponent.java
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,25 @@ public boolean containsGraveItems() {
if (!pair.getLeft().isEmpty() && pair.getRight() == DropRule.PUT_IN_GRAVE) return true;
}
return false;
};
}

/**
* Check if the component contains at least one item that matches the predicate. Will stop at first match
* @param predicate Predicate to test items against
* @return Whether the component contains at least one item that matches the predicate
*/
public boolean containsAny(Predicate<ItemStack> predicate) {
for (Pair<ItemStack, DropRule> pair : this.getAsStackDropList()) {
if (predicate.test(pair.getLeft())) return true;
}
return false;
}
public void setDropRules(Predicate<ItemStack> predicate, DropRule dropRule) {
for (Pair<ItemStack, DropRule> pair : this.getAsStackDropList()) {
if (predicate.test(pair.getLeft())) {
pair.setRight(dropRule);
}
}
}
public abstract NbtCompound writeNbt();
}
4 changes: 4 additions & 0 deletions src/main/java/com/b1n_ry/yigd/compat/InvModCompat.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
package com.b1n_ry.yigd.compat;

import com.b1n_ry.yigd.compat.miscCompatMods.CommonProtectionApiCompat;
import com.b1n_ry.yigd.compat.miscCompatMods.OrpheusCompat;
import com.b1n_ry.yigd.config.YigdConfig;
import net.fabricmc.loader.api.FabricLoader;
import net.minecraft.nbt.NbtCompound;
Expand Down Expand Up @@ -29,6 +31,8 @@ static void initModCompat() {

if (loader.isModLoaded("common-protection-api"))
CommonProtectionApiCompat.init();
if (loader.isModLoaded("orpheus"))
OrpheusCompat.init();
}

String getModName();
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package com.b1n_ry.yigd.compat;
package com.b1n_ry.yigd.compat.miscCompatMods;

import com.b1n_ry.yigd.config.YigdConfig;
import com.b1n_ry.yigd.events.AllowBlockUnderGraveGenerationEvent;
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
package com.b1n_ry.yigd.compat.miscCompatMods;

import com.b1n_ry.yigd.events.AdjustDropRuleEvent;
import com.b1n_ry.yigd.util.DropRule;
import com.ecarrascon.orpheus.Orpheus;
import com.ecarrascon.orpheus.registry.ItemsRegistry;

public class OrpheusCompat {
public static void init() {
AdjustDropRuleEvent.EVENT.register((inventory, context) -> {
String orpheusLyrePower = Orpheus.CONFIG_VALUES.getOrpheusLyrePower();

if (!orpheusLyrePower.equals("keep") && !orpheusLyrePower.equals("both")) return;

if (inventory.containsAny(stack -> stack.isOf(ItemsRegistry.ORPHEUS_LYRE.get()), s -> true, i -> true)) {
inventory.setDropRules(stack -> true, s -> true, i -> true, DropRule.KEEP);
}
});
}
}
4 changes: 2 additions & 2 deletions src/main/java/com/b1n_ry/yigd/components/GraveComponent.java
Original file line number Diff line number Diff line change
Expand Up @@ -370,6 +370,8 @@ public ActionResult claim(ServerPlayerEntity player, ServerWorld world, BlockSta
InventoryComponent.dropItemIfToBeDropped(graveItem, this.pos.getX(), this.pos.getY(), this.pos.getZ(), this.world);
}

this.setStatus(GraveStatus.CLAIMED);

if (!config.graveConfig.persistentGraves.enabled) {
if (config.graveConfig.replaceOldWhenClaimed && previousState != null) {
world.setBlockState(pos, previousState);
Expand All @@ -387,8 +389,6 @@ public ActionResult claim(ServerPlayerEntity player, ServerWorld world, BlockSta
}
}

this.setStatus(GraveStatus.CLAIMED);

if (thisIsARobbery && config.graveConfig.graveRobbing.notifyWhenRobbed) {
MinecraftServer server = world.getServer();
String robberName = player.getGameProfile().getName();
Expand Down
44 changes: 44 additions & 0 deletions src/main/java/com/b1n_ry/yigd/components/InventoryComponent.java
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
import com.b1n_ry.yigd.compat.InvModCompat;
import com.b1n_ry.yigd.config.YigdConfig;
import com.b1n_ry.yigd.data.DeathContext;
import com.b1n_ry.yigd.events.AdjustDropRuleEvent;
import com.b1n_ry.yigd.events.DropItemEvent;
import com.b1n_ry.yigd.events.DropRuleEvent;
import com.b1n_ry.yigd.util.DropRule;
Expand Down Expand Up @@ -167,6 +168,8 @@ private void handleDropRules(DeathContext context) {
CompatComponent<?> compatComponent = this.modInventoryItems.get(modName);
compatComponent.handleDropRules(context);
}

AdjustDropRuleEvent.EVENT.invoker().adjustDropRule(this, context);
}

public void applyLoss() {
Expand Down Expand Up @@ -412,6 +415,47 @@ private int findEmptySlot() {
return -1;
}

/**
* Allows for checking for specific items in specific slots and inventories
* @param itemPredicate Predicate to check for items
* @param modPredicate Predicate to check for mod name ("vanilla" for vanilla)
* @param slotPredicate Predicate to check for slot index (only applies to vanilla inventory)
* @return Whether any item in the component matches the predicates
*/
public boolean containsAny(Predicate<ItemStack> itemPredicate, Predicate<String> modPredicate, Predicate<Integer> slotPredicate) {
if (modPredicate.test("vanilla")) {
for (int i = 0; i < this.items.size(); i++) {
Pair<ItemStack, DropRule> pair = this.items.get(i);
if (slotPredicate.test(i) && itemPredicate.test(pair.getLeft())) return true;
}
}
for (Map.Entry<String, CompatComponent<?>> entry : this.modInventoryItems.entrySet()) {
CompatComponent<?> compatComponent = entry.getValue();
if (modPredicate.test(entry.getKey()) && compatComponent.containsAny(itemPredicate)) return true; // Modded inventories don't use slot IDs
}
return false;
}

/**
* Set drop rules for items in the component based on filters/predicates
* @param itemPredicate Items matching this are affected
* @param modPredicate Mods matching this are affected ("vanilla" for vanilla inventory)
* @param slotPredicate Slots matching this are affected (only applies to vanilla inventory)
* @param dropRule Drop rule to set
*/
public void setDropRules(Predicate<ItemStack> itemPredicate, Predicate<String> modPredicate, Predicate<Integer> slotPredicate, DropRule dropRule) {
if (modPredicate.test("vanilla")) {
for (int i = 0; i < this.items.size(); i++) {
Pair<ItemStack, DropRule> pair = this.items.get(i);
if (slotPredicate.test(i) && itemPredicate.test(pair.getLeft())) pair.setRight(dropRule);
}
}
for (Map.Entry<String, CompatComponent<?>> entry : this.modInventoryItems.entrySet()) {
CompatComponent<?> compatComponent = entry.getValue();
if (modPredicate.test(entry.getKey())) compatComponent.setDropRules(itemPredicate, dropRule);
}
}

/**
* Checks if the grave is empty, meaning no items are stored to be retrieved from the grave when it's opened
* @return Whether the grave is empty
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,8 @@ public class RespawnComponent {
private ExpComponent soulboundExp;
private final EffectComponent respawnEffects;

private boolean graveGenerated = false;

public RespawnComponent(ServerPlayerEntity player) {
this.respawnEffects = new EffectComponent(player);
}
Expand All @@ -43,6 +45,13 @@ public void setSoulboundExp(@NotNull ExpComponent component) {
this.soulboundExp = component;
}

public void setGraveGenerated(boolean graveGenerated) {
this.graveGenerated = graveGenerated;
}
public boolean wasGraveGenerated() {
return this.graveGenerated;
}

public void primeForRespawn(GameProfile profile) {
DeathInfoManager.INSTANCE.addRespawnComponent(profile, this);
DeathInfoManager.INSTANCE.markDirty();
Expand Down
16 changes: 16 additions & 0 deletions src/main/java/com/b1n_ry/yigd/events/AdjustDropRuleEvent.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
package com.b1n_ry.yigd.events;

import com.b1n_ry.yigd.components.InventoryComponent;
import com.b1n_ry.yigd.data.DeathContext;
import net.fabricmc.fabric.api.event.Event;
import net.fabricmc.fabric.api.event.EventFactory;

public interface AdjustDropRuleEvent {
Event<AdjustDropRuleEvent> EVENT = EventFactory.createArrayBacked(AdjustDropRuleEvent.class, events -> (inventory, context) -> {
for (AdjustDropRuleEvent event : events) {
event.adjustDropRule(inventory, context);
}
});

void adjustDropRule(InventoryComponent inventoryComponent, DeathContext context);
}
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ public static void registerEvents() {
Optional<RespawnComponent> respawnComponent = DeathInfoManager.INSTANCE.getRespawnComponent(newProfile);
respawnComponent.ifPresent(component -> component.apply(newPlayer));

if (YigdConfig.getConfig().graveConfig.informGraveLocation) {
if (YigdConfig.getConfig().graveConfig.informGraveLocation && respawnComponent.isPresent() && respawnComponent.get().wasGraveGenerated()) {
List<GraveComponent> graves = new ArrayList<>(DeathInfoManager.INSTANCE.getBackupData(newProfile));
graves.removeIf(grave -> grave.getStatus() != GraveStatus.UNCLAIMED);
if (!graves.isEmpty()) {
Expand Down

0 comments on commit eb23ae4

Please sign in to comment.