Jump to content
Search In
  • More options...
Find results that contain...
Find results in...

[SOLVED] Adding tasks for different side than original(CLIENT-SERVER) by using NetworkEvent.Context


Mr Bonobo
 Share

Recommended Posts

What is the new way of adding task to work queue?

What i want to do in old way:

public static void handle(Packet message, Supplier<NetworkEvent.Context> contextSupplier) {
FMLCommonHandler.instance().getWorldThread(contextSupplier.netHandler).addScheduledTask(() ->

New way:

public static void handle(Packetmessage, Supplier<NetworkEvent.Context> contextSupplier) {
      contextSupplier.get().enqueueWork(() -> {

If contexSupplier is CLIENT, it will add task on CLIENT. So what should i do to add task on DEDICATED_SERVER, even though contextSupplier is CLIENT?

Edited by Mr Bonobo
Link to comment
Share on other sites

Ok, I somewhat managed to make it work in different way by accessing capability values with:

 

public static void handle(PacketTriggerElectricGen message, Supplier<NetworkEvent.Context> contextSupplier) {
contextSupplier.get().enqueueWork(() -> {
    contextSupplier.get().getSender().getServerWorld().getTileEntity(message.blockPos).
            getCapability(new UtilCapabilities().UTIL_CAP).ifPresent(st -> {

And context shouldnt be in CLIENT-side, because this packet is triggered by sendToServer(new etc...) from CLIENTside, only sender should be a CLIENT. Even though i tested with DistExecutor which side it is, and it shows its always a CLIENT, but maybe its SERVER after all if I managed to access SERVER side capability values.

Link to comment
Share on other sites

You are the confusing the concepts of distribution (dedicated server vs the client launched from the launcher, this is what DistExecutor checks) vs logical side (server, including integrated server used in singleplayer, vs client, the thing that renders the game and accepts inputs).

What matters here is the logical side, which is usually accessible using World#isRemote (true on the client). The context also tells you the direction (it is on the network thread, this is why you need to "enqueueWork" and also why you don't have a world here) using NetworkEvent.Context#getDirection.

  • Thanks 1
Link to comment
Share on other sites

3 minutes ago, diesieben07 said:

You are the confusing the concepts of distribution (dedicated server vs the client launched from the launcher, this is what DistExecutor checks) vs logical side (server, including integrated server used in singleplayer, vs client, the thing that renders the game and accepts inputs).

What matters here is the logical side, which is usually accessible using World#isRemote (true on the client). The context also tells you the direction (it is on the network thread, this is why you need to "enqueueWork" and also why you don't have a world here) using NetworkEvent.Context#getDirection.

Wow! Very good and full-explanitory post. It solved probably all my questions. Only one question came from it: if i create packet, which is sent from a SERVER and handled by a CLIENT, I dont need to use enqueueWork then, or I should add this scheduled task always to prevent bugs/overlapping even on CLIENT side??

Link to comment
Share on other sites

Just now, Mr Bonobo said:

if i create packet, which is sent from a SERVER and handled by a CLIENT, I dont need to use enqueueWork

Yes, you do. Packets are received on the network thread always, that's why you need enqueueWork (you can read the name as "doThisOnMainThread"). Most of Minecraft is not thread-safe, which is why you need to schedule your code to run on the main thread if you want to do anything meaningful from your packet.

  • Thanks 1
Link to comment
Share on other sites

1 minute ago, diesieben07 said:

Yes, you do. Packets are received on the network thread always, that's why you need enqueueWork (you can read the name as "doThisOnMainThread"). Most of Minecraft is not thread-safe, which is why you need to schedule your code to run on the main thread if you want to do anything meaningful from your packet.

A many thanks to you! :)

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

 Share



  • Recently Browsing

    No registered users viewing this page.

  • Posts

    • [04Dec2021 13:01:52.507] [main/INFO] [cpw.mods.modlauncher.Launcher/MODLAUNCHER]: ModLauncher running: args [--gameDir, ., --launchTarget, fmlserver, --fml.forgeVersion, 36.2.19, --fml.mcpVersion, 20210115.111550, --fml.mcVersion, 1.16.5, --fml.forgeGroup, net.minecraftforge, nogui] [04Dec2021 13:01:52.510] [main/INFO] [cpw.mods.modlauncher.Launcher/MODLAUNCHER]: ModLauncher 8.0.9+86+master.3cf110c starting: java version 17.0.1 by Oracle Corporation [04Dec2021 13:01:52.522] [main/DEBUG] [cpw.mods.modlauncher.LaunchServiceHandler/MODLAUNCHER]: Found launch services [minecraft,testharness,fmlclient,fmlserver]   This also might be it?
    • [17:28:20] [main/INFO]: Environment: authHost='https://authserver.mojang.com', accountsHost='https://api.mojang.com', sessionHost='https://sessionserver.mojang.com', servicesHost='https://api.minecraftservices.com', name='PROD' [17:28:20] [main/WARN]: Ambiguity between arguments [teleport, destination] and [teleport, targets] with inputs: [Player, 0123, @e, dd12be42-52a9-4a91-a8a1-11c01849e498] [17:28:20] [main/WARN]: Ambiguity between arguments [teleport, location] and [teleport, destination] with inputs: [0.1 -0.5 .9, 0 0 0] [17:28:20] [main/WARN]: Ambiguity between arguments [teleport, location] and [teleport, targets] with inputs: [0.1 -0.5 .9, 0 0 0] [17:28:20] [main/WARN]: Ambiguity between arguments [teleport, targets] and [teleport, destination] with inputs: [Player, 0123, dd12be42-52a9-4a91-a8a1-11c01849e498] [17:28:20] [main/WARN]: Ambiguity between arguments [teleport, targets, location] and [teleport, targets, destination] with inputs: [0.1 -0.5 .9, 0 0 0] [17:28:20] [main/INFO]: Reloading ResourceManager: Default [17:28:21] [Worker-Main-10/INFO]: Loaded 7 recipes [17:28:22] [Worker-Main-10/INFO]: Loaded 927 advancements [17:28:24] [Server thread/INFO]: Starting minecraft server version 1.16.5 [17:28:24] [Server thread/INFO]: Loading properties [17:28:24] [Server thread/INFO]: Default game type: SURVIVAL [17:28:24] [Server thread/INFO]: Generating keypair [17:28:24] [Server console handler/ERROR]: Exception handling console input java.io.IOException: The handle is invalid     at java.io.FileInputStream.readBytes(Native Method) ~[?:?]     at java.io.FileInputStream.read(FileInputStream.java:276) ~[?:?]     at java.io.BufferedInputStream.read1(BufferedInputStream.java:282) ~[?:?]     at java.io.BufferedInputStream.read(BufferedInputStream.java:343) ~[?:?]     at sun.nio.cs.StreamDecoder.readBytes(StreamDecoder.java:270) ~[?:?]     at sun.nio.cs.StreamDecoder.implRead(StreamDecoder.java:313) ~[?:?]     at sun.nio.cs.StreamDecoder.read(StreamDecoder.java:188) ~[?:?]     at java.io.InputStreamReader.read(InputStreamReader.java:177) ~[?:?]     at java.io.BufferedReader.fill(BufferedReader.java:162) ~[?:?]     at java.io.BufferedReader.readLine(BufferedReader.java:329) ~[?:?]     at java.io.BufferedReader.readLine(BufferedReader.java:396) ~[?:?]     at zg$1.run(SourceFile:95) [server.jar.jar:?] [17:28:24] [Server thread/INFO]: Starting Minecraft server on *:25565 [17:28:24] [Server thread/INFO]: Using default channel type [17:28:25] [Server thread/WARN]: Failed to load white-list:  com.google.gson.JsonSyntaxException: Expected entry to be a JsonObject, was "Sta...ne"     at afd.m(SourceFile:393) ~[server.jar.jar:?]     at acy.f(SourceFile:122) ~[server.jar.jar:?]     at zf.B(SourceFile:119) ~[server.jar.jar:?]     at zf.<init>(SourceFile:27) ~[server.jar.jar:?]     at zg.d(SourceFile:169) ~[server.jar.jar:?]     at net.minecraft.server.MinecraftServer.w(SourceFile:645) ~[server.jar.jar:?]     at net.minecraft.server.MinecraftServer.a(SourceFile:257) ~[server.jar.jar:?]     at java.lang.Thread.run(Thread.java:833) [?:?] [17:28:25] [Server thread/INFO]: Preparing level "Better Minecraft" [17:28:25] [Server thread/INFO]: Preparing start region for dimension minecraft:overworld [17:28:27] [Server thread/INFO]: Preparing spawn area: 0% [17:28:27] [Server thread/INFO]: Preparing spawn area: 0% [17:28:27] [Server thread/INFO]: Preparing spawn area: 0% [17:28:27] [Server thread/INFO]: Preparing spawn area: 0% [17:28:28] [Server thread/INFO]: Preparing spawn area: 0% [17:28:28] [Server thread/INFO]: Preparing spawn area: 47% [17:28:32] [Worker-Main-9/INFO]: Preparing spawn area: 83% [17:28:32] [Worker-Main-9/INFO]: Preparing spawn area: 83% [17:28:32] [Worker-Main-8/INFO]: Preparing spawn area: 83% [17:28:32] [Worker-Main-9/INFO]: Preparing spawn area: 83% [17:28:32] [Worker-Main-9/INFO]: Preparing spawn area: 83% [17:28:32] [Worker-Main-9/INFO]: Preparing spawn area: 83% [17:28:32] [Worker-Main-9/INFO]: Preparing spawn area: 83% [17:28:32] [Worker-Main-7/INFO]: Preparing spawn area: 83% [17:28:32] [Worker-Main-9/INFO]: Preparing spawn area: 83% [17:28:33] [Worker-Main-9/INFO]: Preparing spawn area: 83% [17:28:33] [Worker-Main-8/INFO]: Preparing spawn area: 83% [17:28:34] [Worker-Main-7/INFO]: Preparing spawn area: 83% [17:28:34] [Worker-Main-9/INFO]: Preparing spawn area: 83% [17:28:35] [Worker-Main-9/INFO]: Preparing spawn area: 84% [17:28:35] [Worker-Main-6/INFO]: Preparing spawn area: 84% [17:28:36] [Server thread/INFO]: Preparing spawn area: 89% [17:28:36] [Server thread/INFO]: Time elapsed: 10908 ms [17:28:36] [Server thread/INFO]: Done (11.035s)! For help, type "help" [17:30:38] [User Authenticator #1/INFO]: UUID of player Stark3rmine is c3b23361-12df-4ef7-81f5-a0c864d1bf3c [17:30:38] [Server thread/INFO]: Stark3rmine[/127.0.0.1:65426] logged in with entity id 170 at (178.5, 74.0, 249.5) [17:30:38] [Server thread/INFO]: Stark3rmine joined the game [17:30:41] [Server thread/INFO]: Stark3rmine lost connection: Disconnected [17:30:41] [Server thread/INFO]: Stark3rmine left the game [17:30:45] [User Authenticator #2/INFO]: UUID of player Stark3rmine is c3b23361-12df-4ef7-81f5-a0c864d1bf3c [17:30:45] [Server thread/INFO]: Stark3rmine[/127.0.0.1:65431] logged in with entity id 172 at (178.5, 74.0, 249.5) [17:30:45] [Server thread/INFO]: Stark3rmine joined the game [17:30:47] [Server thread/INFO]: Stark3rmine lost connection: Disconnected [17:30:47] [Server thread/INFO]: Stark3rmine left the game   This?
    • It worked thanks a lot ❤️ I'm gonna paste all of my code for anyone in the future looking to do capabilities package com.chickenwand3.rpgmod.core.capabilities.entity; import javax.annotation.Nullable; import net.minecraftforge.common.capabilities.Capability; import net.minecraftforge.common.capabilities.CapabilityManager; import net.minecraftforge.common.capabilities.CapabilityToken; import net.minecraftforge.common.capabilities.ICapabilityProvider; public class CapabilityMobLevel{ public static Capability<MobLevel> MOB_LEVEL_CAPABILITY = CapabilityManager.get(new CapabilityToken<>() {}); public static void register() { CapabilityManager.INSTANCE.register(MobLevel.class); } } package com.chickenwand3.rpgmod.core.capabilities.entity; public class DefaultMobLevel implements MobLevel { public int mobLevel; public float mobMaxHealth; public float mobCurrentHealth; public boolean crazy; public boolean isCrazy() { return crazy; } public float getMaxHealth() { return mobMaxHealth; } public float getCurrentHealth() { return mobCurrentHealth; } } package com.chickenwand3.rpgmod.core.capabilities.entity; public interface MobLevel { } package com.chickenwand3.rpgmod.core.capabilities.entity; import com.chickenwand3.rpgmod.RPGMod; import net.minecraft.resources.ResourceLocation; import net.minecraft.world.entity.Entity; import net.minecraft.world.entity.Mob; import net.minecraft.world.entity.ai.attributes.Attributes; import net.minecraft.world.entity.animal.Animal; import net.minecraft.world.entity.monster.Zombie; import net.minecraft.world.item.enchantment.Enchantments; import net.minecraftforge.common.capabilities.RegisterCapabilitiesEvent; import net.minecraftforge.event.AttachCapabilitiesEvent; import net.minecraftforge.event.entity.EntityJoinWorldEvent; import net.minecraftforge.event.entity.living.LivingDeathEvent; import net.minecraftforge.eventbus.api.SubscribeEvent; import net.minecraftforge.fml.common.Mod; @Mod.EventBusSubscriber(modid = RPGMod.MODID, bus = Mod.EventBusSubscriber.Bus.FORGE) public class MobLevelEventHandler { @SubscribeEvent public static void onAttachCapabilitiesEvent(AttachCapabilitiesEvent<Entity> event) { if (event.getObject() instanceof Mob && !event.getObject().getCommandSenderWorld().isClientSide) { MobLevelProvider providerMobLevel = new MobLevelProvider(); event.addCapability(new ResourceLocation(RPGMod.MODID, "moblevel"), providerMobLevel); event.addListener(providerMobLevel::invalidate); } } @SubscribeEvent public void registerCaps(RegisterCapabilitiesEvent event) { event.register(MobLevel.class); } @SubscribeEvent public static void OnSpawn(final EntityJoinWorldEvent event) { if (event.getEntity()instanceof Mob target && !event.getWorld().isClientSide) { target.getCapability(CapabilityMobLevel.MOB_LEVEL_CAPABILITY).ifPresent(mobLevel -> { DefaultMobLevel actualMobLevel = (DefaultMobLevel) mobLevel; if (actualMobLevel.mobLevel < 1) { actualMobLevel.mobLevel = (randomizeMobLevel()); } if (superCrazy(actualMobLevel.mobLevel)) { actualMobLevel.crazy = true; } if (actualMobLevel.crazy) { if (!target.getMainHandItem().isEmpty()) { target.getMainHandItem().enchant(Enchantments.FIRE_ASPECT, 1); } if (event.getEntity()instanceof Zombie zombie) { zombie.getAttribute(Attributes.SPAWN_REINFORCEMENTS_CHANCE).setBaseValue(0.99D); } System.out.println("Super Crazy " + target.getName() + " has spawned!"); } actualMobLevel.mobMaxHealth = (target.getMaxHealth() * actualMobLevel.mobLevel * 2); actualMobLevel.mobCurrentHealth = actualMobLevel.mobMaxHealth; target.getAttribute(Attributes.MOVEMENT_SPEED) .setBaseValue(target.getAttributeValue(Attributes.MOVEMENT_SPEED) * (1 + (actualMobLevel.mobLevel - 1.0) / 10.0)); if (target.getAttribute(Attributes.ATTACK_DAMAGE) != null) { target.getAttribute(Attributes.ATTACK_DAMAGE) .setBaseValue(target.getAttributeValue(Attributes.ATTACK_DAMAGE) * (1 + (actualMobLevel.mobLevel - 1.0) / 2.0)); } }); } } private static int randomizeMobLevel() { boolean roll = true; int level = 1; while (roll) { if (Math.random() > .5) { level += 1; roll = true; } else { roll = false; } } return level; } private static boolean superCrazy(int level) { boolean result = false; if (level >= 5) { if (Math.random() < .25) { result = true; } else result = false; } return result; } } package com.chickenwand3.rpgmod.core.capabilities.entity; import net.minecraft.core.Direction; import net.minecraft.nbt.CompoundTag; import net.minecraftforge.common.capabilities.Capability; import net.minecraftforge.common.capabilities.ICapabilitySerializable; import net.minecraftforge.common.util.LazyOptional; import javax.annotation.Nonnull; import javax.annotation.Nullable; public class MobLevelProvider implements ICapabilitySerializable<CompoundTag> { private final DefaultMobLevel mobLevel = new DefaultMobLevel(); private final LazyOptional<MobLevel> mobLevelOptional = LazyOptional.of(() -> mobLevel); public void invalidate() { mobLevelOptional.invalidate(); } @Nonnull @Override public <T> LazyOptional<T> getCapability(@Nonnull Capability<T> cap, @Nullable Direction side) { return mobLevelOptional.cast(); } @Override public CompoundTag serializeNBT() { System.out.println("It serialized"); if (CapabilityMobLevel.MOB_LEVEL_CAPABILITY == null) { System.out.println("It made a new compound"); return new CompoundTag(); } else { System.out.println("It serialized the values"); CompoundTag compoundNBT = new CompoundTag(); compoundNBT.putInt("mobLevel", mobLevel.mobLevel); compoundNBT.putFloat("mobCurrentHealth", mobLevel.mobCurrentHealth); compoundNBT.putFloat("mobMaxHealth", mobLevel.mobMaxHealth); compoundNBT.putBoolean("crazy", mobLevel.crazy); return compoundNBT; } } @Override public void deserializeNBT(CompoundTag nbt) { System.out.println("It deserialized"); if (CapabilityMobLevel.MOB_LEVEL_CAPABILITY != null) { System.out.println("It deserialized the values"); mobLevel.mobLevel = (nbt.getInt("mobLevel")); float mobCurrentHealth = nbt.getFloat("mobCurrentHealth"); mobLevel.mobCurrentHealth = (mobCurrentHealth); float mobMaxHealth = nbt.getFloat("mobMaxHealth"); mobLevel.mobMaxHealth = (mobMaxHealth); boolean crazy = nbt.getBoolean("crazy"); mobLevel.crazy = (crazy); } } }  
    • Just uploaded the correct installer from win machine to ubuntu via winscp. Sorry, didn't check the checksum. Very strange behavior :( Thank you!
    • I just tried it with both 36.2.0 and 36.2.19 using wget and the direct downloads. Both worked fine for me, giving me the correct MD5 sum. This is something on your machine.
  • Topics

  • Who's Online (See full list)

×
×
  • Create New...

Important Information

By using this site, you agree to our Privacy Policy.