Skip to content

Commit

Permalink
Add multiplayer support and remove deprecated events (#34)
Browse files Browse the repository at this point in the history
* Fix multiplayer issues for 1.18.2
* Fix place event issues
* Fix issues where place event would incorrectly trigger
* Fix issue with xp change on multiplayer
* Fix multiplayer for 1.19.2
* Add multiplayer support for 1.19.4
* Add multiplayer functionality to 1.20.4
* Add multiplayer for 1.17.1
* Add multiplayer for 1.16.5
* Add multiplayer for 1.15.2
* Add multiplayer for 1.12.2
* Fix on place bug for multiplayer
* Replace deprecated advancement events
  • Loading branch information
Sour-o7 authored Aug 1, 2024
1 parent 0a581c2 commit ef8267d
Show file tree
Hide file tree
Showing 51 changed files with 1,552 additions and 60 deletions.
34 changes: 30 additions & 4 deletions forge/fg-6.0/1.12.2/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,11 @@ plugins {
id 'maven-publish'
id 'net.minecraftforge.gradle' version '[6.0,6.2)'
id 'com.github.johnrengelman.shadow' version '8.1.1'
id 'org.spongepowered.mixin' version '0.7.+'
}

apply plugin: 'org.spongepowered.mixin'

version = mod_version
group = mod_group_id

Expand Down Expand Up @@ -122,11 +125,16 @@ repositories {
// flatDir {
// dir 'libs'
// }

maven {
url = 'https://repo.spongepowered.org/maven'

}
}

configurations {
shade
implementation.extendsFrom shade
implementation.extendsFrom shade
}

dependencies {
Expand All @@ -136,6 +144,8 @@ dependencies {
// If the group id is "net.minecraft" and the artifact id is one of ["client", "server", "joined"],
// then special handling is done to allow a setup of a vanilla dependency without the use of an external repository.
minecraft "net.minecraftforge:forge:${minecraft_version}-${forge_version}"
shade 'org.spongepowered:mixin:0.8.5'
annotationProcessor 'org.spongepowered:mixin:0.8.5:processor'
shade 'io.github.blackspherefollower:buttplug4j.connectors.jetty.websocket.client:3.1.105'

// Example mod dependency with JEI - using fg.deobf() ensures the dependency is remapped to your development mappings
Expand Down Expand Up @@ -175,6 +185,12 @@ tasks.named('processResources', ProcessResources).configure {
}
}

mixin {
// MixinGradle Settings
add sourceSets.main, "mixins.${mod_id}.refmap.json"
config "mixins.${mod_id}.json"
}

// Example for how to get properties into the manifest for reading at runtime.
tasks.named('jar', Jar).configure {
archiveClassifier = 'slim'
Expand All @@ -186,7 +202,11 @@ tasks.named('jar', Jar).configure {
'Implementation-Title' : project.name,
'Implementation-Version' : project.jar.archiveVersion,
'Implementation-Vendor' : mod_authors,
'Implementation-Timestamp': new Date().format("yyyy-MM-dd'T'HH:mm:ssZ")
'Implementation-Timestamp': new Date().format("yyyy-MM-dd'T'HH:mm:ssZ"),
"FMLCorePluginContainsFMLMod": "true",
"ForceLoadAsMod": "true", //Seems to do the opposite of what it claims to do while in dev enviroment, uncomment for build
"TweakClass": "org.spongepowered.asm.launch.MixinTweaker",
'TweakOrder': '0'
])
}

Expand All @@ -195,8 +215,14 @@ tasks.named('jar', Jar).configure {
}

tasks.named('shadowJar', ShadowJar) {
enableRelocation true
relocationPrefix "com.therainbowville.repack"
// enableRelocation true
// relocationPrefix "com.therainbowville.repack"

relocate "com.fasterxml", "com.therainbowville.repack.com.fasterxml"
relocate ("org.eclipse", "com.therainbowville.repack.org.eclipse") {
exclude "org/eclipse/jetty/version/**"
}
relocate "io", "com.therainbowville.repack.io"
archiveClassifier = "${minecraft_version}-Forge-${forge_version}"
configurations = [project.configurations.shade]
exclude '**/META-INF/versions/**'
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -206,6 +206,10 @@ public static void onPlace(BlockEvent.EntityPlaceEvent event){
{
((VibrationStatePlace)vibrationStates.get("place")).onPlace();
}
}

public static void onPlace(){
((VibrationStatePlace)vibrationStates.get("place")).onPlace();
}

@SubscribeEvent
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
package com.therainbowville.minegasm.mixin;
import com.therainbowville.minegasm.client.ClientEventHandler;

import net.minecraft.advancements.Advancement;
import net.minecraft.advancements.AdvancementProgress;
import net.minecraft.client.Minecraft;
import net.minecraft.client.multiplayer.ClientAdvancementManager;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.network.play.server.SPacketAdvancementInfo;
import net.minecraft.util.ResourceLocation;
import net.minecraftforge.common.MinecraftForge;
import net.minecraftforge.event.entity.player.AdvancementEvent;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;

import java.util.Map;

@Mixin(ClientAdvancementManager.class)
public class ClientAdvancementManagerMixin {
private static Logger LOGGER = LogManager.getLogger();

@Inject(method = "read", at = @At("HEAD"), cancellable = true)
public void onUpdate(SPacketAdvancementInfo advancementInfoPacket, CallbackInfo ci) {
if (Minecraft.getMinecraft().isIntegratedServerRunning()) { return; }
LOGGER.info("Advancement updated");

for(Map.Entry<ResourceLocation, AdvancementProgress> entry : advancementInfoPacket.getProgressUpdates().entrySet()) {
Advancement advancement = ((ClientAdvancementManager) (Object) this).getAdvancementList().getAdvancement(entry.getKey());
if (advancement != null) {
EntityPlayer player = Minecraft.getMinecraft().player;
AdvancementEvent event = new AdvancementEvent(player, advancement);
ClientEventHandler.onAdvancementEvent(event);
}
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
package com.therainbowville.minegasm.mixin;
import com.therainbowville.minegasm.client.ClientEventHandler;

import net.minecraft.client.Minecraft;
import net.minecraft.client.entity.EntityPlayerSP;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.entity.EntityLivingBase;
import net.minecraft.entity.item.EntityXPOrb;
import net.minecraft.util.DamageSource;
import net.minecraft.world.World;

import net.minecraftforge.event.entity.living.LivingHealEvent;
import net.minecraftforge.event.entity.living.LivingHurtEvent;
import net.minecraftforge.event.entity.player.PlayerPickupXpEvent;


import net.minecraftforge.common.MinecraftForge;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
import org.spongepowered.asm.mixin.Shadow;

@Mixin(EntityPlayerSP.class)
public class EntityPlayerSPMixin {
private static Logger LOGGER = LogManager.getLogger();

/* @Inject(method = "heal", at = @At("HEAD"), cancellable = true)
public void onHeal(float amount, CallbackInfo ci) {
if (amount > 0) {
LivingHealEvent event = new LivingHealEvent((LocalPlayer) (Object) this, amount);
ClientEventHandler.onHeal(event);
}
}*/

@Inject(method = "attackEntityFrom", at = @At("HEAD"), cancellable = true)
public void onHurt(DamageSource source, float amount, CallbackInfoReturnable<Boolean> cir) {
if (Minecraft.getMinecraft().isIntegratedServerRunning()) { return; }

if (amount > 0) {
LivingHurtEvent event = new LivingHurtEvent((EntityLivingBase) (Object) this, source, amount);
ClientEventHandler.onHurt(event);
}
}

@Inject(method = "setXPStats", at = @At("HEAD"), cancellable = true)
public void onSetXPStats(float currentXp, int totalXp, int level, CallbackInfo ci) {
if (Minecraft.getMinecraft().isIntegratedServerRunning()) { return; }

int amount = totalXp - ((EntityPlayerSP) (Object) this).experienceTotal;

if (amount > 0) {

EntityXPOrb orb = new EntityXPOrb(((EntityPlayer) (Object) this).world);
orb.xpValue = amount;

LOGGER.info("Experience changed");
PlayerPickupXpEvent event = new PlayerPickupXpEvent((EntityPlayer) (Object) this, orb);
ClientEventHandler.onXpChange(event);

}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
package com.therainbowville.minegasm.mixin;
import com.therainbowville.minegasm.client.ClientEventHandler;

import net.minecraft.client.multiplayer.PlayerControllerMP;
import net.minecraftforge.event.world.BlockEvent.BreakEvent;
import net.minecraftforge.event.world.BlockEvent.EntityPlaceEvent;

import net.minecraft.client.Minecraft;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.client.entity.EntityPlayerSP;
import net.minecraft.client.multiplayer.WorldClient;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.math.Vec3d;
import net.minecraft.util.EnumHand;
import net.minecraft.util.EnumActionResult;

import net.minecraft.item.ItemBlock;
import net.minecraft.item.Item;
import net.minecraft.item.ItemStack;

import net.minecraft.util.math.BlockPos;

import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;

@Mixin(PlayerControllerMP.class)
public class PlayerControllerMPMixin {
private static Logger LOGGER = LogManager.getLogger();

boolean placedBlock;

@Inject(method = "onPlayerDestroyBlock", at = @At("HEAD"), cancellable = true)
public void onDestroyBlock(BlockPos blockPos, CallbackInfoReturnable<Boolean> cir) {
if (Minecraft.getMinecraft().isIntegratedServerRunning()) { return; }

EntityPlayer player = Minecraft.getMinecraft().player;
if (player != null) {
BreakEvent event = new BreakEvent(player.world, blockPos, player.world.getBlockState(blockPos), player);
ClientEventHandler.onBreak(event);
}
}

@Inject(method = "processRightClickBlock", at = @At(value = "INVOKE", target = "Lnet/minecraft/item/ItemStack;onItemUse(Lnet/minecraft/entity/player/EntityPlayer;Lnet/minecraft/world/World;Lnet/minecraft/util/math/BlockPos;Lnet/minecraft/util/EnumHand;Lnet/minecraft/util/EnumFacing;FFF)Lnet/minecraft/util/EnumActionResult;",
shift = At.Shift.AFTER), cancellable = true)
public void onUseItemOn(EntityPlayerSP player, WorldClient worldIn, BlockPos pos, EnumFacing direction, Vec3d vec, EnumHand hand, CallbackInfoReturnable<EnumActionResult> cir) {
if (Minecraft.getMinecraft().isIntegratedServerRunning() ) { return; }

if (player.getHeldItem(hand).getItem() instanceof ItemBlock){
this.placedBlock = true;
}

}

@Inject(method = "processRightClickBlock", at = @At("RETURN"), cancellable = true)
public void onUseItemOnReturn(EntityPlayerSP player, WorldClient worldIn, BlockPos pos, EnumFacing direction, Vec3d vec, EnumHand hand, CallbackInfoReturnable<EnumActionResult> cir) {
if (Minecraft.getMinecraft().isIntegratedServerRunning() || !this.placedBlock) { return; }

if (cir.getReturnValue() == EnumActionResult.SUCCESS) {
ClientEventHandler.onPlace();
}
this.placedBlock = false;
}

}
12 changes: 12 additions & 0 deletions forge/fg-6.0/1.12.2/src/main/resources/mixins.minegasm.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
{
"required": true,
"minVersion": "0.8.1",
"package": "com.therainbowville.minegasm.mixin",
"compatibilityLevel": "JAVA_8",
"refmap": "mixins.minegasm.refmap.json",
"mixins": [
"PlayerControllerMPMixin",
"ClientAdvancementManagerMixin",
"EntityPlayerSPMixin"
]
}
8 changes: 8 additions & 0 deletions forge/fg-6.0/1.15.2/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ plugins {
id 'maven-publish'
id 'net.minecraftforge.gradle' version '[6.0,6.2)'
id 'com.github.johnrengelman.shadow' version '8.1.1'
id 'org.spongepowered.mixin' version '0.7.+'
}

version = mod_version
Expand Down Expand Up @@ -136,6 +137,7 @@ dependencies {
// If the group id is "net.minecraft" and the artifact id is one of ["client", "server", "joined"],
// then special handling is done to allow a setup of a vanilla dependency without the use of an external repository.
minecraft "net.minecraftforge:forge:${minecraft_version}-${forge_version}"
annotationProcessor 'org.spongepowered:mixin:0.8.5:processor'
shade 'io.github.blackspherefollower:buttplug4j.connectors.jetty.websocket.client:3.1.105'

// Example mod dependency with JEI - using fg.deobf() ensures the dependency is remapped to your development mappings
Expand Down Expand Up @@ -175,6 +177,12 @@ tasks.named('processResources', ProcessResources).configure {
}
}

mixin {
// MixinGradle Settings
add sourceSets.main, "mixins.${mod_id}.refmap.json"
config "mixins.${mod_id}.json"
}

// Example for how to get properties into the manifest for reading at runtime.
tasks.named('jar', Jar).configure {
archiveClassifier = 'slim'
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -209,6 +209,10 @@ public static void onPlace(BlockEvent.EntityPlaceEvent event){
((VibrationStatePlace)vibrationStates.get("place")).onPlace();
}
}

public static void onPlace(){
((VibrationStatePlace)vibrationStates.get("place")).onPlace();
}

@SubscribeEvent
public static void onItemPickup(EntityItemPickupEvent event)
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
package com.therainbowville.minegasm.mixin;
import com.therainbowville.minegasm.client.ClientEventHandler;

import net.minecraft.advancements.Advancement;
import net.minecraft.advancements.AdvancementProgress;
import net.minecraft.client.Minecraft;
import net.minecraft.client.multiplayer.ClientAdvancementManager;
import net.minecraft.entity.player.PlayerEntity;
import net.minecraft.network.play.server.SAdvancementInfoPacket;
import net.minecraft.util.ResourceLocation;
import net.minecraftforge.common.MinecraftForge;
import net.minecraftforge.event.entity.player.AdvancementEvent;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Inject;
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;

import java.util.Map;

@Mixin(ClientAdvancementManager.class)
public class ClientAdvancementManagerMixin {
private static Logger LOGGER = LogManager.getLogger();
private static final Minecraft minecraft = Minecraft.getInstance();

@Inject(method = "update", at = @At("HEAD"), cancellable = true)
public void onUpdate(SAdvancementInfoPacket advancementInfoPacket, CallbackInfo ci) {
if (Minecraft.getInstance().isLocalServer()) { return; }
LOGGER.info("Advancement updated");

for(Map.Entry<ResourceLocation, AdvancementProgress> entry : advancementInfoPacket.getProgress().entrySet()) {
Advancement advancement = ((ClientAdvancementManager) (Object) this).getAdvancements().get(entry.getKey());
PlayerEntity player = minecraft.player;
AdvancementEvent event = new AdvancementEvent(player, advancement);
ClientEventHandler.onAdvancementEvent(event);
}
}
}
Loading

0 comments on commit ef8267d

Please sign in to comment.