Skip to content

Commit 2a3173b

Browse files
authored
Bugfix/scythe right click (TerraFirmaGreg-Team#281)
1 parent f62e5b6 commit 2a3173b

2 files changed

Lines changed: 140 additions & 0 deletions

File tree

Lines changed: 139 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,139 @@
1+
package su.terrafirmagreg.core.mixins.common.gtceu;
2+
3+
import org.spongepowered.asm.mixin.Mixin;
4+
import org.spongepowered.asm.mixin.Overwrite;
5+
import org.spongepowered.asm.mixin.injection.At;
6+
import org.spongepowered.asm.mixin.injection.Inject;
7+
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
8+
9+
import com.gregtechceu.gtceu.api.item.tool.ToolHelper;
10+
import com.gregtechceu.gtceu.common.item.tool.behavior.HarvestCropsBehavior;
11+
12+
import net.dries007.tfc.common.TFCTags;
13+
import net.dries007.tfc.common.blocks.crop.DeadCropBlock;
14+
import net.minecraft.core.BlockPos;
15+
import net.minecraft.core.Direction;
16+
import net.minecraft.server.level.ServerLevel;
17+
import net.minecraft.world.InteractionHand;
18+
import net.minecraft.world.entity.player.Player;
19+
import net.minecraft.world.item.ItemStack;
20+
import net.minecraft.world.item.context.UseOnContext;
21+
import net.minecraft.world.level.Level;
22+
import net.minecraft.world.level.block.Block;
23+
import net.minecraft.world.level.block.CropBlock;
24+
import net.minecraft.world.level.block.LevelEvent;
25+
import net.minecraft.world.level.block.entity.BlockEntity;
26+
import net.minecraft.world.level.block.state.BlockState;
27+
import net.minecraft.world.level.material.FluidState;
28+
import net.minecraft.world.phys.BlockHitResult;
29+
import net.minecraft.world.phys.Vec3;
30+
import net.minecraftforge.common.Tags;
31+
32+
@Mixin(value = HarvestCropsBehavior.class, remap = false)
33+
public abstract class HarvestCropsBehaviorMixin {
34+
35+
/** Harvest routine used for the scythe
36+
* @author Ujhik
37+
* @reason To adapt GregTech harvest routine to TerraFirmaCraft crops so they reset to growth 0 correctly
38+
* And to customize harvest behavior for TerraFirmaGreg
39+
*/
40+
@Overwrite
41+
private static boolean harvestBlockRoutine(BlockPos pos, UseOnContext context) {
42+
Level world = context.getLevel();
43+
ItemStack stack = context.getItemInHand();
44+
Player player = context.getPlayer();
45+
46+
if (world.isClientSide())
47+
return false;
48+
49+
BlockState blockState = world.getBlockState(pos);
50+
boolean isDeadCrop = blockState.getBlock() instanceof DeadCropBlock;
51+
boolean isAliveCrop = blockState.getBlock() instanceof CropBlock;
52+
53+
if (!isDeadCrop && !isAliveCrop)
54+
return false;
55+
56+
if ((blockState.getBlock() instanceof CropBlock cropBlock) && !cropBlock.isMaxAge(blockState))
57+
return false;
58+
59+
// Getting the crop bottom block assuming crops are max 2 block tall
60+
BlockPos belowPos = pos.below();
61+
BlockState belowState = world.getBlockState(belowPos);
62+
BlockPos targetPos;
63+
if (belowState.getBlock() == blockState.getBlock()) {
64+
targetPos = belowPos;
65+
blockState = belowState;
66+
} else {
67+
targetPos = pos;
68+
}
69+
70+
// Not processing top blocks of plants
71+
belowPos = targetPos.below();
72+
belowState = world.getBlockState(belowPos);
73+
boolean isTfcFarmland = belowState.is(TFCTags.Blocks.FARMLAND);
74+
if (!isTfcFarmland)
75+
return false;
76+
77+
BlockEntity be = world.getBlockEntity(targetPos);
78+
var drops = Block.getDrops(blockState, (ServerLevel) world, targetPos, be, player, stack);
79+
80+
ItemStack cropSeed = null;
81+
boolean removedSeed = false;
82+
for (ItemStack drop : drops) {
83+
// Accounting for the replanted seed
84+
if (!removedSeed && drop.is(Tags.Items.SEEDS)) {
85+
cropSeed = drop.copy();
86+
cropSeed.setCount(1);
87+
drop.shrink(1);
88+
removedSeed = true;
89+
}
90+
91+
Block.popResource(world, targetPos, drop);
92+
}
93+
94+
// Replacing block to force multiblock crops to break without spawning drops
95+
FluidState fluidState = world.getFluidState(targetPos);
96+
world.setBlockAndUpdate(targetPos, fluidState.createLegacyBlock());
97+
world.levelEvent(LevelEvent.PARTICLES_DESTROY_BLOCK, targetPos, Block.getId(blockState));
98+
99+
// Replanting in the next tick to ensure multiblock crop tops break
100+
if (cropSeed != null) {
101+
ItemStack finalCropSeed = cropSeed;
102+
UseOnContext plantCtx = new UseOnContext(
103+
world,
104+
player,
105+
InteractionHand.MAIN_HAND,
106+
cropSeed,
107+
new BlockHitResult(
108+
Vec3.atCenterOf(targetPos),
109+
Direction.UP,
110+
targetPos,
111+
false));
112+
113+
world.getServer().execute(() -> finalCropSeed.useOn(plantCtx));
114+
}
115+
116+
ToolHelper.damageItem(stack, player);
117+
118+
return true;
119+
}
120+
121+
/** Filters blocks used in harvest routine
122+
* @author Ujhik
123+
* @reason To add dead crop blocks to the filter
124+
*/
125+
@Inject(method = "isBlockCrops", at = @At("RETURN"), cancellable = true)
126+
private static void tfc$allowDeadCrops(UseOnContext context, CallbackInfoReturnable<Boolean> cir) {
127+
if (!cir.getReturnValue()) {
128+
Level level = context.getLevel();
129+
BlockPos pos = context.getClickedPos();
130+
131+
if (level.getBlockState(pos.above()).isAir()) {
132+
Block block = level.getBlockState(pos).getBlock();
133+
if (block instanceof DeadCropBlock) {
134+
cir.setReturnValue(true);
135+
}
136+
}
137+
}
138+
}
139+
}

src/main/resources/tfg.mixins.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -80,6 +80,7 @@
8080
"common.gtceu.GTRecipeWidgetMixin",
8181
"common.gtceu.GTToolTypeMixin",
8282
"common.gtceu.GTUtilMixin",
83+
"common.gtceu.HarvestCropsBehaviorMixin",
8384
"common.gtceu.LootDataManagerMixin",
8485
"common.gtceu.ModelManagerMixin",
8586
"common.gtceu.MultiblockInfoEmiCategoryMixin",

0 commit comments

Comments
 (0)