jabelar Posted May 13, 2014 Posted May 13, 2014 [Edited] In the course of trying to better understand which side different code runs on, I've been putting in prints to console to try to trace it. I got a weird result I'm trying to understand. Probably simple, but in the constructor of my entity I print out what side it is on and what side the world parameter passed to it is. In the game when the entity is created as expected I see the constructors on both sides, but the weird thing is the entity is on different side than the world passed to it. I'm probably just doing something dumb, but can you see what it is? The console output: EntityHerdAnimal constructor(), entity.isClientWorld() = false, par1World.isRemote = true The entity's constructor is: public EntityHerdAnimal(World par1World) { super(par1World); // DEBUG System.out.println("EntityHerdAnimal constructor(), entity.isClientWorld() = "+this.isClientWorld()+", par1World.isRemote = "+par1World.isRemote); setSize(0.9F, 1.3F); getNavigator().setAvoidsWater(true); tasks.addTask(0, new EntityAISwimming(this)); tasks.addTask(1, new EntityAIPanicHerdAnimal(this)); // the leap and the collide together form an actual attack tasks.addTask(2, new EntityAILeapAtTarget(this, 0.4F)); tasks.addTask(3, new EntityAIAttackOnCollide(this, 1.0D, true)); tasks.addTask(5, new EntityAIMate(this, 1.0D)); tasks.addTask(6, new EntityAITempt(this, 1.25D, Items.wheat, false)); tasks.addTask(7, new EntityAIFollowParent(this, 1.25D)); tasks.addTask(8, new EntityAIWander(this, 1.0D)); tasks.addTask(9, new EntityAIWatchClosest(this, EntityPlayer.class, 6.0F)); tasks.addTask(10, new EntityAILookIdle(this)); targetTasks.addTask(4, new EntityAIHurtByTargetHerdAnimal(this, true)); // needs to have lower priority than panic (which does rearing) } Is this expected? I thought the world parameter gets passed to the worldObj which is then queried for the isClientWorld() which should be equivalent to worldObj.isRemote ... Quote Check out my tutorials here: http://jabelarminecraft.blogspot.com/
SanAndreaP Posted May 13, 2014 Posted May 13, 2014 If you spawn an entity with an constructor like Entity(worldObj, x, y, z) on the server, the server sends a packet to the client and the client will also spawn it with the (entitys standard) constructor Entity(worldObj) in the client world. That's why you should always spawn an entity on the server, or you'll get duplicates on the client. How would the client know about the entity otherwise except excessive network transfer? This setup is there to prevent exactly that. So yes, it's intended. Quote Don't ask for support per PM! They'll get ignored! | If a post helped you, click the "Thank You" button at the top right corner of said post! | mah twitter This thread makes me sad because people just post copy-paste-ready code when it's obvious that the OP has little to no programming experience. This is not how learning works.
jabelar Posted May 13, 2014 Author Posted May 13, 2014 If you spawn an entity with an constructor like Entity(worldObj, x, y, z) on the server, the server sends a packet to the client and the client will also spawn it with the (entitys standard) constructor Entity(worldObj) in the client world. That's why you should always spawn an entity on the server, or you'll get duplicates on the client. How would the client know about the entity otherwise except excessive network transfer? This setup is there to prevent exactly that. So yes, it's intended. I understand that the entity is spawned on both sides, on server and then that causes spawn on client. But it seems weird to me that the entity spawned is on the opposite side as the worldObj passed to it. I mean right in the same constructor if you query whether the world object parameter is remote and compare that with whether the entity. Actually, I also tried comparing this.worldObj.isRemote and this.isClientWorld() and they return opposite values! These methods come from vanilla EntityLivingBase: /** * Returns whether the entity is in a local (client) world */ public boolean isClientWorld() { return !this.worldObj.isRemote; } Is my mind just fried, but isn't that backwards? I thought isRemote meant a client world, but the vanilla method says the opposite. Anyway, that is where my code has gone wrong -- I was using both interchangeably. Solution: The isClientWorld() method seems to have logic backwards -- don't use it. Only use worldObj.isRemote to test entity side. Quote Check out my tutorials here: http://jabelarminecraft.blogspot.com/
Recommended Posts
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.