Jump to content

Recommended Posts

Posted

So i have created a custom entity which can be ridden but when i ride the entity it stops moving and it won't move in any way.

That's my entity class:

	public boolean inputForward = false;
	public boolean inputRight = false;
	public boolean inputBack = false;
	public boolean inputLeft = false;
	public boolean inputUp = false;
	public boolean inputDown = false;
	
	private int debug = 0;
	
	public EntitySeamoth(World worldIn) {
		super(worldIn);
		setSize(1.0f, 1.0f);
		isImmuneToFire = true;
	}
	
	@Override
	public boolean canBeCollidedWith() {
		return !this.isDead;
	}
	
	@Override
	public boolean canBePushed() {
		return true;
	}
	
	@Override
	protected boolean canBeRidden(Entity entityIn) {
		return true;
	}
	
	@Override
	public boolean canRiderInteract() {
		return true;
	}
	
	@Override
	public boolean shouldDismountInWater(Entity rider) {
		return false;
	}
	
	@Override
	public double getMountedYOffset() {
		return 0.0d;
	}
	
	@Override
	public boolean canPassengerSteer() {
		return getControllingPassenger() instanceof EntityPlayer;
	}
	
	@Override
	public boolean processInitialInteract(EntityPlayer player, EnumHand hand) {
		if (player.isSneaking()) {
			return false;
		} else {
			if (!this.world.isRemote) {
				player.startRiding(this);
			}
			return true;
		}
	}
	
	@Override
	public AxisAlignedBB getCollisionBox(Entity entityIn) {
		return getEntityBoundingBox();
	}
	
	@Override
	public boolean attackEntityFrom(DamageSource source, float amount) {
		if (source.getTrueSource() instanceof EntityPlayer) {
			this.setDead();
			return true;
		}
		return false;
	}
	
	@Override
	public Entity getControllingPassenger() {
		List<Entity> list = this.getPassengers();
		return list.isEmpty() ? null : (Entity) list.get(0);
	}
	
	@Override
	public AxisAlignedBB getCollisionBoundingBox() {
		return null;
	}
	
	@Override
	public void onUpdate() {
		super.onUpdate();
		
		if (this.world.isRemote) {
			BetterDiving.CONNECTION.sendToServer(new PacketVehicleKeyPress());
		}
		
		this.updateRotation();
		
		this.updateMotion();
		
		this.move(MoverType.SELF, this.motionX, this.motionY, this.motionZ);
		
	}
	
	public void updateRotation() {
		if (this.getControllingPassenger() instanceof EntityPlayer) {
			this.rotationYaw = MathHelper.wrapDegrees(this.getControllingPassenger().rotationYaw);
			this.rotationPitch = this.getControllingPassenger().rotationPitch;
		}
	}
	
	public void updateMotion() {
		double rotX  = -MathHelper.sin(this.rotationYaw * 0.017453292F);
		double rotZ  =  MathHelper.cos(this.rotationYaw * 0.017453292F);
		float fakeRotationPitch = this.rotationPitch;
		
		double speed = 0.02d;
		
		if (inputDown && !inputUp) {
			if (inputForward) {
				fakeRotationPitch = (fakeRotationPitch + 90f) / 2f;
			} else if (inputBack) {
				fakeRotationPitch = (fakeRotationPitch - 90f) / 2f;
			} else {
				this.motionY -= speed;
			}
		}
		
		if (inputUp && !inputDown) {
			if (inputForward) {
				fakeRotationPitch = (fakeRotationPitch - 90f) / 2f;
			} else if (inputBack) {
				fakeRotationPitch = (fakeRotationPitch + 90f) / 2f;
			} else {
				this.motionY += speed;
			}
		}
		
		double lookVecX = rotX * MathHelper.cos(fakeRotationPitch * 0.017453292F);
		double lookVecY = -MathHelper.sin(fakeRotationPitch * 0.017453292F);
		double lookVecZ = rotZ * MathHelper.cos(fakeRotationPitch * 0.017453292F);
		
		if (inputForward) {
			this.motionX += speed * lookVecX;
			this.motionY += speed * lookVecY;
			this.motionZ += speed * lookVecZ;
		}
		if (inputBack) {
			this.motionX -= speed * lookVecX;
			this.motionY -= speed * lookVecY;
			this.motionZ -= speed * lookVecZ;
		}
		if (inputLeft) {
			this.motionX += speed * rotZ;
			this.motionZ += speed * -rotX;
		}
		if (inputRight) {
			this.motionX += speed * -rotZ;
			this.motionZ += speed * rotZ;
		}
		
		this.motionX *= 0.90d;
		if (this.motionX < 0.0001d) this.motionX = 0;
		this.motionY *= 0.90d;
		if (this.motionY < 0.0001d) this.motionY = 0;
		this.motionZ *= 0.90d;
		if (this.motionZ < 0.0001d) this.motionZ = 0;
	}
	
	@Override
	protected void entityInit() {
		
	}
	
	@Override
	protected void readEntityFromNBT(NBTTagCompound compound) {
		
	}
	
	@Override
	protected void writeEntityToNBT(NBTTagCompound compound) {
		
	}

 

The update methods are fine because i tried this without success:

@Override
	public void onUpdate() {
		super.onUpdate();
		this.motionY += 0.001d;
		this.move(MoverType.SELF, this.motionX, this.motionY, this.motionZ);
		
	}

 

I seem to miss something...

Posted (edited)

You do not need to invoke Entity#move manually since it already does that for you in it's update method.

Could you try a higher value in your second example? 0.001 is very low and minecraft already subtracts the motionY each tick to simulate gravity.

As for the likely cause of your issue:

6 hours ago, Meldexun said:

if (inputDown && !inputUp

All inputX fields are false and I don't see you changing them anywhere.

Edited by V0idWa1k3r
Posted (edited)
1 hour ago, V0idWa1k3r said:

You do not need to invoke Entity#move manually since it already does that for you in it's update method.

I'm extending my class the Entity class directly so i have to call it myself since it's not called in the Entity class.

But that's no my issue anymore.

 

Now i have this code to update the movement:

	@Override
	public void onUpdate() {
		super.onUpdate();
		
		if (this.world.isRemote) {
			if (this.getControllingPassenger() instanceof EntityPlayer) {
				GameSettings settings = Minecraft.getMinecraft().gameSettings;
				
				this.inputForward = settings.keyBindForward.isKeyDown();
				this.inputRight = settings.keyBindRight.isKeyDown();
				this.inputBack = settings.keyBindBack.isKeyDown();
				this.inputLeft = settings.keyBindLeft.isKeyDown();
				this.inputUp = settings.keyBindJump.isKeyDown();
				this.inputDown = settings.keyBindSneak.isKeyDown();
			} else {
				this.inputForward = false;
				this.inputRight = false;
				this.inputBack = false;
				this.inputLeft = false;
				this.inputUp = false;
				this.inputDown = false;
			}
			
			this.updateRotation();
			
			this.updateMotion();
			
			this.move(MoverType.SELF, this.motionX, this.motionY, this.motionZ);
		}
    }

 

Now my entity seems to move correctly. But the problem now is that the movement looks laggy. So the movement of the player who is riding the entity is smooth similar to movement with a boat. But the entity is a lagging behind and it's movement is jerkily. Also it's a bit faster than the player.

 

Here i registered my entity because i read something about velocity updates but i don't really know where they are defined (i think it has something to do with the tracker but i don't know excatly what that does either):

	public static final EntityEntry ENTITY_ENTRY_C_ENTITY = createEntityEntry(EntityCEntity.class, "entity_c_entity", 0xFFFFFF, 0xAAAAAA);
	
	@SubscribeEvent
	public static void registerTileEntities(RegistryEvent.Register<EntityEntry> event) {
		event.getRegistry().registerAll(
				ENTITY_ENTRY_C_ENTITY
		);
	}
	
	private static EntityEntry createEntityEntry(Class entityClass, String name, int eggCcolor1, int eggColor2) {
		return EntityEntryBuilder.create().entity(entityClass).id(new ResourceLocation(BetterDiving.MOD_ID, name), ID++).name(name).egg(eggCcolor1, eggColor2).tracker(64, 80, true).build();
	}

 

Edited by Meldexun
Posted (edited)

The parameters to the tracker are range, frequency and whether or not to send velocity updates. 

Frequency is the rate at which the entity sends the data. 20 would mean it sends 1 update per 20 ticks. In your case it's 80 meaning it sends the data once per 80 ticks.

Range is the range that the entity must be within in relation to a player to receive updates.

The last parameter is self-explanatory.

 

11 minutes ago, Meldexun said:

public static final EntityEntry ENTITY_ENTRY_C_ENTITY = createEntityEntry(EntityCEntity.class, "entity_c_entity", 0xFFFFFF, 0xAAAAAA);

Don't use static initializers. Instantinate your stuff directly in the appropriate registry event.

 

11 minutes ago, Meldexun said:

GameSettings settings = Minecraft.getMinecraft().gameSettings;

You can't reference client-only code in a common environment like the update method as it will crash the dedicated server. You must use a proxy for something like this. No, the fact that it is hidden behind a World.isRemote check doesn't stop the crash, it is still referenced. Standard JVM won't load the class until it is required, but I can't be so sure about third-party JVM implementations.

Edited by V0idWa1k3r
Posted (edited)
18 minutes ago, V0idWa1k3r said:

The parameters to the tracker are range, frequency and whether or not to send velocity updates. 

Frequency is the rate at which the entity sends the data. 20 would mean it sends 1 update per 20 ticks. In your case it's 80 meaning it sends the data once per 80 ticks.

Range is the range that the entity must be within in relation to a player to receive updates.

The last parameter is self-explanatory.

Thanks for the explanation.

But i now tried to set the frequency higher/lower with updates true/false with no difference.

18 minutes ago, V0idWa1k3r said:

Don't use static initializers. Instantinate your stuff directly in the appropriate registry event.

I can change that.

 

18 minutes ago, V0idWa1k3r said:

You can't reference client-only code in a common environment like the update method as it will crash the dedicated server. You must use a proxy for something like this. No, the fact that it is hidden behind a World.isRemote check doesn't stop the crash, it is still referenced. Standard JVM won't load the class until it is required, but I can't be so sure about third-party JVM implementations.

Yes my code is often messy and buggy with the server/client side stuff. I usually clean that when my stuff works probably. Or when i forget that i normally try my mod in singleplayer and on a dedicated server and then when something crashes i go and clean the code. (Thanks anyway)

 

Edit: Also the entity moves a bit faster than the player who rides it.

Edited by Meldexun
Posted

Ok i now added a model to my entity and the movement is looking good now. I don't really understand why it's working with a real model instead of such a white cube.

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.