Jump to content

[1.11.2] [SOLVED!] How do I do Packets


GooberGunter

Recommended Posts

In the Render class

Spoiler

package com.ninja3659.explorationexpansion.client.renders;

import com.ninja3659.explorationexpansion.client.entities.EntityBeelzebook;
import com.ninja3659.explorationexpansion.client.model.ModelBeelzebook;

import net.minecraft.client.model.ModelBase;
import net.minecraft.client.renderer.entity.RenderLiving;
import net.minecraft.client.renderer.entity.RenderManager;
import net.minecraft.util.ResourceLocation;

public class RenderBeelzebook extends RenderLiving<EntityBeelzebook>{

	private static final ResourceLocation TEXTURES = new ResourceLocation("neem:textures/entity/beelzebook/beelzebook.png");
	
	public RenderBeelzebook(RenderManager manager) {
		super(manager, new ModelBeelzebook(), 3);
	}
	
	@Override
	protected ResourceLocation getEntityTexture(EntityBeelzebook entity) {
		return TEXTURES;
	}

}

 

And then in ClientProxy:

Spoiler

@Override
	public void registerRenders() {
		ModItems.registerRenders();
		ModTools.registerRenders();
		ModBlocks.registerRenders();
		RenderingRegistry.registerEntityRenderingHandler(EntityChimera.class, new IRenderFactory<EntityChimera>() {

			@Override
			public Render<? super EntityChimera> createRenderFor(RenderManager manager) {
				return new RenderChimera(manager);
			}
		
		});
		RenderingRegistry.registerEntityRenderingHandler(EntityMindFlayer.class, new IRenderFactory<EntityMindFlayer>() {
			
			@Override
			public Render<? super EntityMindFlayer> createRenderFor(RenderManager manager) {
				return new RenderFlayer(manager);
			}
		});
		RenderingRegistry.registerEntityRenderingHandler(EntityBeelzebook.class, new IRenderFactory<EntityBeelzebook>() {

			@Override
			public Render<? super EntityBeelzebook> createRenderFor(RenderManager manager) {
				// TODO Auto-generated method stub
				return new RenderBeelzebook(manager);
			}
			
		});
		Utils.getLogger().info("Rendered Chimera");
	}

 

 

Edited by GooberGunter
Link to comment
Share on other sites

Your render class returns a new instance of ModelBeelzebook, but your packet updates the model which you have stored in a field in the entity and which does nothing. Instead you should make the model render depending on the entity's awake status, and use the packet to update the entity itself.

Link to comment
Share on other sites

So, like, have a getModel method in the entity class and then in render call said method and have the packet store the entity not the boolean?

 

If so, then how would I go about that writing the entity to bytes? And wouldn't the entity be a lot to write back and forth?

Edited by GooberGunter
Link to comment
Share on other sites

user action -> entity on server gets awake -> send packet -> packet handler sets the same value on the client entity -> renderer reads the data in the entity when rendering the model

  • Like 1

Apparently I'm a complete and utter jerk and come to this forum just like to make fun of people, be confrontational, and make your personal life miserable.  If you think this is the case, JUST REPORT ME.  Otherwise you're just going to get reported when you reply to my posts and point it out, because odds are, I was trying to be nice.

 

Exception: If you do not understand Java, I WILL NOT HELP YOU and your thread will get locked.

 

DO NOT PM ME WITH PROBLEMS. No help will be given.

Link to comment
Share on other sites

And specifically, the LivingHurtEvent only runs server-side.

  • Like 1

Apparently I'm a complete and utter jerk and come to this forum just like to make fun of people, be confrontational, and make your personal life miserable.  If you think this is the case, JUST REPORT ME.  Otherwise you're just going to get reported when you reply to my posts and point it out, because odds are, I was trying to be nice.

 

Exception: If you do not understand Java, I WILL NOT HELP YOU and your thread will get locked.

 

DO NOT PM ME WITH PROBLEMS. No help will be given.

Link to comment
Share on other sites

9 minutes ago, GooberGunter said:

I never thought I'd get it. So...one last question. How do I set up a packet to handle an entity since it's not a basic field

You've already got a packet that handles an entity - it finds the correct one using its id. You just need to set the boolean in the entity itself, rather than setting in the entity's model field (which is unused and pointless anyway).

Link to comment
Share on other sites

Alright it works! Kinda. When I trigger the event, it updates all the entities of the same type

Here is the updated packet 

Spoiler

void proccessMessage(PacketReturnAwaken message, MessageContext ctx) {
			try {
				EntityBeelzebook eb = (EntityBeelzebook) Minecraft.getMinecraft().world.getEntityByID(message.entityid);
				eb.setEntityAwake(message.awake);
				Utils.getLogger().info("packet set: " + eb.getentityAwake());
			}catch(Exception e) {
				Utils.getLogger().catching(e);
			}
		}

 

 

Link to comment
Share on other sites

Yeah here:

Spoiler

public void AwakeAnimation(EntityBeelzebook entity) {
		if(entity.getentityAwake()) {
			this.setRotation(Eye1, 33, 0, 0);
			this.setRotation(Eye2, 33, 0, 0);
			Utils.getLogger().info("animation!");
		}
	}//opens the book's eyes

 

 I should also note that right now, in the render class, it is still marked as new ModelBeelzebook();

Edited by GooberGunter
Link to comment
Share on other sites

7 hours ago, GooberGunter said:

Also. Side-note: how to I isolate every change to the model class per entity?

Could you post your whole Render class. 

VANILLA MINECRAFT CLASSES ARE THE BEST RESOURCES WHEN MODDING

I will be posting 1.15.2 modding tutorials on this channel. If you want to be notified of it do the normal YouTube stuff like subscribing, ect.

Forge and vanilla BlockState generator.

Link to comment
Share on other sites

Render class:

Spoiler

package com.ninja3659.explorationexpansion.client.renders;

import com.ninja3659.explorationexpansion.client.entities.EntityBeelzebook;
import com.ninja3659.explorationexpansion.client.model.ModelBeelzebook;

import net.minecraft.client.Minecraft;
import net.minecraft.client.model.ModelBase;
import net.minecraft.client.renderer.entity.RenderLiving;
import net.minecraft.client.renderer.entity.RenderManager;
import net.minecraft.util.ResourceLocation;

public class RenderBeelzebook extends RenderLiving<EntityBeelzebook>{

	private static final ResourceLocation TEXTURES = new ResourceLocation("neem:textures/entity/beelzebook/beelzebook.png");
	
	public RenderBeelzebook(RenderManager manager) {
		super(manager, new EntityBeelzebook(Minecraft.getMinecraft().world).getModel(), 3);
	}
	
	@Override
	protected ResourceLocation getEntityTexture(EntityBeelzebook entity) {
		return TEXTURES;
	}

}

 

 

Link to comment
Share on other sites

4 minutes ago, GooberGunter said:

Render class:

  Reveal hidden contents


package com.ninja3659.explorationexpansion.client.renders;

import com.ninja3659.explorationexpansion.client.entities.EntityBeelzebook;
import com.ninja3659.explorationexpansion.client.model.ModelBeelzebook;

import net.minecraft.client.Minecraft;
import net.minecraft.client.model.ModelBase;
import net.minecraft.client.renderer.entity.RenderLiving;
import net.minecraft.client.renderer.entity.RenderManager;
import net.minecraft.util.ResourceLocation;

public class RenderBeelzebook extends RenderLiving<EntityBeelzebook>{

	private static final ResourceLocation TEXTURES = new ResourceLocation("neem:textures/entity/beelzebook/beelzebook.png");
	
	public RenderBeelzebook(RenderManager manager) {
		super(manager, new EntityBeelzebook(Minecraft.getMinecraft().world).getModel(), 3);
	}
	
	@Override
	protected ResourceLocation getEntityTexture(EntityBeelzebook entity) {
		return TEXTURES;
	}

}

 

 

In your constructor the second pararmeter of the super needs to be a new Model.

VANILLA MINECRAFT CLASSES ARE THE BEST RESOURCES WHEN MODDING

I will be posting 1.15.2 modding tutorials on this channel. If you want to be notified of it do the normal YouTube stuff like subscribing, ect.

Forge and vanilla BlockState generator.

Link to comment
Share on other sites

Migrate the awake field to your entity class from your model then. Most likely your model is a singleton(and it should be) so a change to this field will change the model of all your entities.

EDIT: haven't noticed all other classes you've posted with those changes. Could you please post your entity class?

Edited by V0idWa1k3r
Link to comment
Share on other sites

Here's the entity class

Spoiler

package com.ninja3659.explorationexpansion.client.entities;

import com.ninja3659.explorationexpansion.client.ai.EntityAIWander3d;
import com.ninja3659.explorationexpansion.client.model.ModelBeelzebook;
import com.ninja3659.explorationexpansion.networking.NeemPacketHandler;
import com.ninja3659.explorationexpansion.networking.PacketReturnAwaken;
import com.ninja3659.explorationexpansion.util.Utils;

import net.minecraft.enchantment.EnumEnchantmentType;
import net.minecraft.entity.EntityCreature;
import net.minecraft.entity.EntityFlying;
import net.minecraft.entity.ai.EntityAIAttackMelee;
import net.minecraft.entity.ai.EntityAIBase;
import net.minecraft.entity.ai.EntityAIFindEntityNearestPlayer;
import net.minecraft.entity.ai.EntityAILookIdle;
import net.minecraft.entity.ai.EntityAINearestAttackableTarget;
import net.minecraft.entity.ai.EntityAIWander;
import net.minecraft.entity.ai.EntityAIWanderAvoidWater;
import net.minecraft.entity.ai.EntityAIWatchClosest;
import net.minecraft.entity.ai.EntityMoveHelper;
import net.minecraft.entity.item.EntityXPOrb;
import net.minecraft.entity.monster.EntityGhast;
import net.minecraft.entity.monster.IMob;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.util.EnumParticleTypes;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.MathHelper;
import net.minecraft.world.World;
import net.minecraftforge.event.entity.living.LivingHurtEvent;
import net.minecraftforge.fml.common.eventhandler.SubscribeEvent;

public class EntityBeelzebook extends EntityFlying implements IMob {

	ModelBeelzebook bookmodel = new ModelBeelzebook();
	public boolean entityAwake;
	public int sync;
	
	public EntityBeelzebook(World worldIn) {
		super(worldIn);
		this.experienceValue = 200;
		this.setSize(2, .5f);
		this.moveHelper = new BeelzebookMoveHelper(this);
		moveHelper.setMoveTo(0, 10, 0, 1D);
		this.entityAwake = false;
		sync = 0;
		
	}
	
	
	@Override
	protected void entityInit() {
		super.entityInit();
	}
	
	
	@Override
	public void onUpdate() {
		super.onUpdate();
		if(entityAwake) {
			//Utils.getLogger().info("AWAKENED");
		}
	}
	
	@Override
	protected void initEntityAI() {
		if(entityAwake) {
			applyAttackAI();
			Utils.getLogger().info("AI updated");
		}
	}
	
	public boolean getentityAwake() {
		return entityAwake;
	}
	
	public void setEntityAwake(boolean truth) {
		this.entityAwake = truth;
	}
	
	public ModelBeelzebook getModel() {
		return this.bookmodel;
	}
	
	
	protected void applyAttackAI() {
		this.tasks.addTask(0, new EntityAIDeath(this, deathTime));
		this.targetTasks.addTask(1, new EntityAIWatchClosest(this, EntityPlayer.class, 32));
		this.targetTasks.addTask(0, new EntityAIFindEntityNearestPlayer(this));
		this.tasks.addTask(0, new EntityAIWander3d(this, 1.0D, 1));
		//Utils.getLogger().info("now we work");
	}
	
	@Override
	protected void onDeathUpdate() {

        ++this.deathTime;
        
        if (this.deathTime != 0) {
        }
        
        if (this.deathTime == 200)
        {
            if (!this.world.isRemote && (this.isPlayer() || this.recentlyHit > 0 && this.canDropLoot() && this.world.getGameRules().getBoolean("doMobLoot")))
            {
                int i = this.getExperiencePoints(this.attackingPlayer);
                i = net.minecraftforge.event.ForgeEventFactory.getExperienceDrop(this, this.attackingPlayer, i);
                while (i > 0)
                {
                    int j = EntityXPOrb.getXPSplit(i);
                    i -= j;
                    this.world.spawnEntity(new EntityXPOrb(this.world, this.posX, this.posY, this.posZ, j));
                }
            }
            
            this.setDead();

            for (int k = 0; k < 20; ++k)
            {
                double d2 = this.rand.nextGaussian() * 0.02D;
                double d0 = this.rand.nextGaussian() * 0.02D;
                double d1 = this.rand.nextGaussian() * 0.02D;
                this.world.spawnParticle(EnumParticleTypes.EXPLOSION_NORMAL, this.posX + (double)(this.rand.nextFloat() * this.width * 2.0F) - (double)this.width, this.posY + (double)(this.rand.nextFloat() * this.height), this.posZ + (double)(this.rand.nextFloat() * this.width * 2.0F) - (double)this.width, d2, d0, d1, new int[0]);
            }
        }		
	}
	
	
	public int getdeathTime() {
		return this.deathTime;
	}
	
	
	
	@Override
	public void onLivingUpdate() {
		super.onLivingUpdate();
		if(entityAwake) {
			applyAttackAI();
		}
		sync++;
		sync %= 20;
		if(sync == 0 && entityAwake) {
			NeemPacketHandler.INSTANCE.sendToAll(new PacketReturnAwaken(this.getentityAwake(), this.getEntityId()));
			Utils.getLogger().info("synched!: " + entityAwake);
		}
	}
	
	public double getPosX() {
		return this.posX;
	}
	
	public double getPosY() {
		return this.posY;
	}
	
	public double getPosZ() {
		return this.posZ;
	}
	
	public EntityBeelzebook getEntity() {
		return this;
	}
	
	static class BeelzebookMoveHelper extends EntityMoveHelper {
		private final EntityBeelzebook parentEntity;
		private int courseCooldown;
		
		public BeelzebookMoveHelper(EntityBeelzebook book) {
			super(book);
			this.parentEntity = book;
		}
		
		public void onUpdateMoveHelper() {
			if (this.action == EntityMoveHelper.Action.MOVE_TO) {
				double dx = this.posX - this.parentEntity.posX;
				double dy = this.posY - this.parentEntity.posY;
				double dz = this.posZ - this.parentEntity.posZ;
				double df = dx * dx + dy * dy + dz * dz;
				
				if(this.courseCooldown-- <=0) {
					this.courseCooldown += this.parentEntity.getRNG().nextInt(5) + 2;
					df = (double)MathHelper.sqrt(df);
					
					if(this.isNotColliding(this.posX, this.posY, this.posZ, df)) {
						this.parentEntity.motionX += dx/df * .1D;
						this.parentEntity.motionY += dy/df * .1D;
						this.parentEntity.motionZ += dz/df * .1D;
					}
					else {
						this.action = EntityMoveHelper.Action.WAIT;
					}
				}
			}
		}
		
		private boolean isNotColliding(double x, double y, double z, double dividend) {
			double d0 = (x - this.parentEntity.posX) / dividend;
			double d1 = (y - this.parentEntity.posY) / dividend;
			double d2 = (z - this.parentEntity.posZ) / dividend;
			AxisAlignedBB ax = this.parentEntity.getEntityBoundingBox();
		
			for (int i =1; (double)i < dividend; ++i) {
				ax = ax.offset(d0, d1, d2);
				
				if(!this.parentEntity.world.getCollisionBoxes(this.parentEntity, ax).isEmpty()) {
					return false;
				}
			}
			
			return true;
		}
	}
}

class EntityAIDeath extends EntityAIBase{

	protected int death;
	protected EntityBeelzebook book;
	
	public EntityAIDeath(EntityBeelzebook entity, int deathT) {
		this.death = deathT;
		this.book = entity;
		setMutexBits(8);
	}
	
	@Override
	public boolean shouldExecute() {
		if (death != 0) {
			return true;
		}
		else {
			return false;
		}
	}
	
	@Override
	public boolean continueExecuting() {
		// TODO Auto-generated method stub
		return false;
	}
	
	@Override
	public void startExecuting() {
		this.book.getMoveHelper().setMoveTo(book.posX, book.posY + 10, book.posZ, 1D);
	}
	
}

 

 

Link to comment
Share on other sites

Don't create a new instance of your model in your entity class, models should be singletons. Models are also client-side only.

If your model class haven't changed since you've last posted it then the problem lies in the fact that you need to handle both cases on your AwakeAnimation method - if the entity is awake, and if they are not. Currently you are changing the rotation angles on the model if the entity is awake... which changes them for all entities as models are singletons. 

  • Like 1
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
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
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.

Announcements



×
×
  • Create New...

Important Information

By using this site, you agree to our Terms of Use.