Advertisement
asteroidsteam

PlayerEntity class

Sep 13th, 2019
1,137
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Java 87.76 KB | None | 0 0
  1. package net.minecraft.entity.player;
  2.  
  3. import com.google.common.collect.ImmutableMap;
  4. import com.google.common.collect.Lists;
  5. import com.mojang.authlib.GameProfile;
  6. import com.mojang.datafixers.util.Either;
  7. import java.nio.charset.StandardCharsets;
  8. import java.util.Collection;
  9. import java.util.List;
  10. import java.util.Map;
  11. import java.util.Optional;
  12. import java.util.OptionalInt;
  13. import java.util.UUID;
  14. import java.util.function.Predicate;
  15. import javax.annotation.Nullable;
  16. import net.minecraft.advancements.CriteriaTriggers;
  17. import net.minecraft.block.BedBlock;
  18. import net.minecraft.block.Block;
  19. import net.minecraft.block.BlockState;
  20. import net.minecraft.block.HorizontalBlock;
  21. import net.minecraft.enchantment.EnchantmentHelper;
  22. import net.minecraft.entity.CreatureAttribute;
  23. import net.minecraft.entity.Entity;
  24. import net.minecraft.entity.EntitySize;
  25. import net.minecraft.entity.EntityType;
  26. import net.minecraft.entity.LivingEntity;
  27. import net.minecraft.entity.MobEntity;
  28. import net.minecraft.entity.Pose;
  29. import net.minecraft.entity.SharedMonsterAttributes;
  30. import net.minecraft.entity.ai.attributes.IAttributeInstance;
  31. import net.minecraft.entity.boss.dragon.EnderDragonPartEntity;
  32. import net.minecraft.entity.item.ArmorStandEntity;
  33. import net.minecraft.entity.item.BoatEntity;
  34. import net.minecraft.entity.item.ItemEntity;
  35. import net.minecraft.entity.item.minecart.AbstractMinecartEntity;
  36. import net.minecraft.entity.monster.MonsterEntity;
  37. import net.minecraft.entity.passive.ParrotEntity;
  38. import net.minecraft.entity.passive.PigEntity;
  39. import net.minecraft.entity.passive.TameableEntity;
  40. import net.minecraft.entity.passive.horse.AbstractHorseEntity;
  41. import net.minecraft.entity.projectile.FishingBobberEntity;
  42. import net.minecraft.inventory.EnderChestInventory;
  43. import net.minecraft.inventory.EquipmentSlotType;
  44. import net.minecraft.inventory.IInventory;
  45. import net.minecraft.inventory.container.Container;
  46. import net.minecraft.inventory.container.INamedContainerProvider;
  47. import net.minecraft.inventory.container.PlayerContainer;
  48. import net.minecraft.item.ArmorItem;
  49. import net.minecraft.item.AxeItem;
  50. import net.minecraft.item.ElytraItem;
  51. import net.minecraft.item.ItemStack;
  52. import net.minecraft.item.Items;
  53. import net.minecraft.item.MerchantOffers;
  54. import net.minecraft.item.ShootableItem;
  55. import net.minecraft.item.SwordItem;
  56. import net.minecraft.item.crafting.IRecipe;
  57. import net.minecraft.nbt.CompoundNBT;
  58. import net.minecraft.nbt.ListNBT;
  59. import net.minecraft.network.datasync.DataParameter;
  60. import net.minecraft.network.datasync.DataSerializers;
  61. import net.minecraft.network.datasync.EntityDataManager;
  62. import net.minecraft.network.play.server.SEntityVelocityPacket;
  63. import net.minecraft.particles.IParticleData;
  64. import net.minecraft.particles.ParticleTypes;
  65. import net.minecraft.potion.EffectInstance;
  66. import net.minecraft.potion.EffectUtils;
  67. import net.minecraft.potion.Effects;
  68. import net.minecraft.scoreboard.ScorePlayerTeam;
  69. import net.minecraft.scoreboard.Scoreboard;
  70. import net.minecraft.scoreboard.Team;
  71. import net.minecraft.stats.Stat;
  72. import net.minecraft.stats.Stats;
  73. import net.minecraft.tags.FluidTags;
  74. import net.minecraft.tileentity.CommandBlockLogic;
  75. import net.minecraft.tileentity.CommandBlockTileEntity;
  76. import net.minecraft.tileentity.JigsawTileEntity;
  77. import net.minecraft.tileentity.SignTileEntity;
  78. import net.minecraft.tileentity.StructureBlockTileEntity;
  79. import net.minecraft.util.ActionResultType;
  80. import net.minecraft.util.CachedBlockInfo;
  81. import net.minecraft.util.CooldownTracker;
  82. import net.minecraft.util.DamageSource;
  83. import net.minecraft.util.Direction;
  84. import net.minecraft.util.FoodStats;
  85. import net.minecraft.util.Hand;
  86. import net.minecraft.util.HandSide;
  87. import net.minecraft.util.ResourceLocation;
  88. import net.minecraft.util.SharedConstants;
  89. import net.minecraft.util.SoundCategory;
  90. import net.minecraft.util.SoundEvent;
  91. import net.minecraft.util.SoundEvents;
  92. import net.minecraft.util.Unit;
  93. import net.minecraft.util.math.AxisAlignedBB;
  94. import net.minecraft.util.math.BlockPos;
  95. import net.minecraft.util.math.MathHelper;
  96. import net.minecraft.util.math.Vec3d;
  97. import net.minecraft.util.text.ITextComponent;
  98. import net.minecraft.util.text.StringTextComponent;
  99. import net.minecraft.util.text.TranslationTextComponent;
  100. import net.minecraft.util.text.event.ClickEvent;
  101. import net.minecraft.world.Difficulty;
  102. import net.minecraft.world.GameRules;
  103. import net.minecraft.world.GameType;
  104. import net.minecraft.world.IWorldReader;
  105. import net.minecraft.world.World;
  106. import net.minecraft.world.server.ServerWorld;
  107. import net.minecraftforge.api.distmarker.Dist;
  108. import net.minecraftforge.api.distmarker.OnlyIn;
  109.  
  110. public abstract class PlayerEntity extends LivingEntity {
  111.    public static final String PERSISTED_NBT_TAG = "PlayerPersisted";
  112.    protected java.util.HashMap<ResourceLocation, BlockPos> spawnPosMap = new java.util.HashMap<>();
  113.    protected java.util.HashMap<ResourceLocation, Boolean> spawnForcedMap = new java.util.HashMap<>();
  114.    public static final net.minecraft.entity.ai.attributes.IAttribute REACH_DISTANCE = new net.minecraft.entity.ai.attributes.RangedAttribute(null, "generic.reachDistance", 5.0D, 0.0D, 1024.0D).setShouldWatch(true);
  115.    public static final EntitySize STANDING_SIZE = EntitySize.flexible(0.6F, 1.8F);
  116.    private static final Map<Pose, EntitySize> SIZE_BY_POSE = ImmutableMap.<Pose, EntitySize>builder().put(Pose.STANDING, STANDING_SIZE).put(Pose.SLEEPING, SLEEPING_SIZE).put(Pose.FALL_FLYING, EntitySize.flexible(0.6F, 0.6F)).put(Pose.SWIMMING, EntitySize.flexible(0.6F, 0.6F)).put(Pose.SPIN_ATTACK, EntitySize.flexible(0.6F, 0.6F)).put(Pose.SNEAKING, EntitySize.flexible(0.6F, 1.5F)).put(Pose.DYING, EntitySize.fixed(0.2F, 0.2F)).build();
  117.    private static final DataParameter<Float> ABSORPTION = EntityDataManager.createKey(PlayerEntity.class, DataSerializers.FLOAT);
  118.    private static final DataParameter<Integer> PLAYER_SCORE = EntityDataManager.createKey(PlayerEntity.class, DataSerializers.VARINT);
  119.    protected static final DataParameter<Byte> PLAYER_MODEL_FLAG = EntityDataManager.createKey(PlayerEntity.class, DataSerializers.BYTE);
  120.    protected static final DataParameter<Byte> MAIN_HAND = EntityDataManager.createKey(PlayerEntity.class, DataSerializers.BYTE);
  121.    protected static final DataParameter<CompoundNBT> LEFT_SHOULDER_ENTITY = EntityDataManager.createKey(PlayerEntity.class, DataSerializers.COMPOUND_NBT);
  122.    protected static final DataParameter<CompoundNBT> RIGHT_SHOULDER_ENTITY = EntityDataManager.createKey(PlayerEntity.class, DataSerializers.COMPOUND_NBT);
  123.    private long field_223730_e;
  124.    public final PlayerInventory inventory = new PlayerInventory(this);
  125.    protected EnderChestInventory enterChestInventory = new EnderChestInventory();
  126.    public final PlayerContainer container;
  127.    public Container openContainer;
  128.    protected FoodStats foodStats = new FoodStats();
  129.    protected int flyToggleTimer;
  130.    public float prevCameraYaw;
  131.    public float cameraYaw;
  132.    public int xpCooldown;
  133.    public double prevChasingPosX;
  134.    public double prevChasingPosY;
  135.    public double prevChasingPosZ;
  136.    public double chasingPosX;
  137.    public double chasingPosY;
  138.    public double chasingPosZ;
  139.    private int sleepTimer;
  140.    protected boolean eyesInWaterPlayer;
  141.    protected BlockPos spawnPos;
  142.    protected boolean spawnForced;
  143.    public final PlayerAbilities abilities = new PlayerAbilities();
  144.    public int experienceLevel;
  145.    public int experienceTotal;
  146.    public float experience;
  147.    protected int xpSeed;
  148.    protected final float speedInAir = 0.02F;
  149.    private int lastXPSound;
  150.    private final GameProfile gameProfile;
  151.    @OnlyIn(Dist.CLIENT)
  152.    private boolean hasReducedDebug;
  153.    private ItemStack itemStackMainHand = ItemStack.EMPTY;
  154.    private final CooldownTracker cooldownTracker = this.createCooldownTracker();
  155.    @Nullable
  156.    public FishingBobberEntity fishingBobber;
  157.    private net.minecraft.world.dimension.DimensionType spawnDimension = net.minecraft.world.dimension.DimensionType.OVERWORLD;
  158.    private final java.util.Collection<ITextComponent> prefixes = new java.util.LinkedList<ITextComponent>();
  159.    private final java.util.Collection<ITextComponent> suffixes = new java.util.LinkedList<ITextComponent>();
  160.  
  161.    public PlayerEntity(World worldIn, GameProfile gameProfileIn) {
  162.       super(EntityType.PLAYER, worldIn);
  163.       this.setUniqueId(getUUID(gameProfileIn));
  164.       this.gameProfile = gameProfileIn;
  165.       this.container = new PlayerContainer(this.inventory, !worldIn.isRemote, this);
  166.       this.openContainer = this.container;
  167.       BlockPos blockpos = worldIn.getSpawnPoint();
  168.       this.setLocationAndAngles((double)blockpos.getX() + 0.5D, (double)(blockpos.getY() + 1), (double)blockpos.getZ() + 0.5D, 0.0F, 0.0F);
  169.       this.unused180 = 180.0F;
  170.    }
  171.  
  172.    public boolean func_223729_a(World p_223729_1_, BlockPos p_223729_2_, GameType p_223729_3_) {
  173.       if (!p_223729_3_.hasLimitedInteractions()) {
  174.          return false;
  175.       } else if (p_223729_3_ == GameType.SPECTATOR) {
  176.          return true;
  177.       } else if (this.isAllowEdit()) {
  178.          return false;
  179.       } else {
  180.          ItemStack itemstack = this.getHeldItemMainhand();
  181.          return itemstack.isEmpty() || !itemstack.canDestroy(p_223729_1_.getTags(), new CachedBlockInfo(p_223729_1_, p_223729_2_, false));
  182.       }
  183.    }
  184.  
  185.    protected void registerAttributes() {
  186.       super.registerAttributes();
  187.       this.getAttributes().registerAttribute(SharedMonsterAttributes.ATTACK_DAMAGE).setBaseValue(1.0D);
  188.       this.getAttribute(SharedMonsterAttributes.MOVEMENT_SPEED).setBaseValue((double)0.1F);
  189.       this.getAttributes().registerAttribute(SharedMonsterAttributes.ATTACK_SPEED);
  190.       this.getAttributes().registerAttribute(SharedMonsterAttributes.LUCK);
  191.       this.getAttributes().registerAttribute(REACH_DISTANCE);
  192.    }
  193.  
  194.    protected void registerData() {
  195.       super.registerData();
  196.       this.dataManager.register(ABSORPTION, 0.0F);
  197.       this.dataManager.register(PLAYER_SCORE, 0);
  198.       this.dataManager.register(PLAYER_MODEL_FLAG, (byte)0);
  199.       this.dataManager.register(MAIN_HAND, (byte)1);
  200.       this.dataManager.register(LEFT_SHOULDER_ENTITY, new CompoundNBT());
  201.       this.dataManager.register(RIGHT_SHOULDER_ENTITY, new CompoundNBT());
  202.    }
  203.  
  204.    /**
  205.     * Called to update the entity's position/logic.
  206.     */
  207.    public void tick() {
  208.       net.minecraftforge.fml.hooks.BasicEventHooks.onPlayerPreTick(this);
  209.       this.noClip = this.isSpectator();
  210.       if (this.isSpectator()) {
  211.          this.onGround = false;
  212.       }
  213.  
  214.       if (this.xpCooldown > 0) {
  215.          --this.xpCooldown;
  216.       }
  217.  
  218.       if (this.isSleeping()) {
  219.          ++this.sleepTimer;
  220.          if (this.sleepTimer > 100) {
  221.             this.sleepTimer = 100;
  222.          }
  223.  
  224.          if (!this.world.isRemote && !net.minecraftforge.event.ForgeEventFactory.fireSleepingTimeCheck(this, getBedPosition())) {
  225.             this.wakeUpPlayer(false, true, true);
  226.          }
  227.       } else if (this.sleepTimer > 0) {
  228.          ++this.sleepTimer;
  229.          if (this.sleepTimer >= 110) {
  230.             this.sleepTimer = 0;
  231.          }
  232.       }
  233.  
  234.       this.updateEyesInWaterPlayer();
  235.       super.tick();
  236.       if (!this.world.isRemote && this.openContainer != null && !this.openContainer.canInteractWith(this)) {
  237.          this.closeScreen();
  238.          this.openContainer = this.container;
  239.       }
  240.  
  241.       if (this.isBurning() && this.abilities.disableDamage) {
  242.          this.extinguish();
  243.       }
  244.  
  245.       this.updateCape();
  246.       if (!this.world.isRemote) {
  247.          this.foodStats.tick(this);
  248.          this.addStat(Stats.PLAY_ONE_MINUTE);
  249.          if (this.isAlive()) {
  250.             this.addStat(Stats.TIME_SINCE_DEATH);
  251.          }
  252.  
  253.          if (this.isSneaking()) {
  254.             this.addStat(Stats.SNEAK_TIME);
  255.          }
  256.  
  257.          if (!this.isSleeping()) {
  258.             this.addStat(Stats.TIME_SINCE_REST);
  259.          }
  260.       }
  261.  
  262.       int i = 29999999;
  263.       double d0 = MathHelper.clamp(this.posX, -2.9999999E7D, 2.9999999E7D);
  264.       double d1 = MathHelper.clamp(this.posZ, -2.9999999E7D, 2.9999999E7D);
  265.       if (d0 != this.posX || d1 != this.posZ) {
  266.          this.setPosition(d0, this.posY, d1);
  267.       }
  268.  
  269.       ++this.ticksSinceLastSwing;
  270.       ItemStack itemstack = this.getHeldItemMainhand();
  271.       if (!ItemStack.areItemStacksEqual(this.itemStackMainHand, itemstack)) {
  272.          if (!ItemStack.areItemsEqualIgnoreDurability(this.itemStackMainHand, itemstack)) {
  273.             this.resetCooldown();
  274.          }
  275.  
  276.          this.itemStackMainHand = itemstack.isEmpty() ? ItemStack.EMPTY : itemstack.copy();
  277.       }
  278.  
  279.       this.updateTurtleHelmet();
  280.       this.cooldownTracker.tick();
  281.       this.updatePose();
  282.       net.minecraftforge.fml.hooks.BasicEventHooks.onPlayerPostTick(this);
  283.    }
  284.  
  285.    protected boolean updateEyesInWaterPlayer() {
  286.       this.eyesInWaterPlayer = this.areEyesInFluid(FluidTags.WATER, true);
  287.       return this.eyesInWaterPlayer;
  288.    }
  289.  
  290.    private void updateTurtleHelmet() {
  291.       ItemStack itemstack = this.getItemStackFromSlot(EquipmentSlotType.HEAD);
  292.       if (itemstack.getItem() == Items.TURTLE_HELMET && !this.areEyesInFluid(FluidTags.WATER)) {
  293.          this.addPotionEffect(new EffectInstance(Effects.WATER_BREATHING, 200, 0, false, false, true));
  294.       }
  295.  
  296.    }
  297.  
  298.    protected CooldownTracker createCooldownTracker() {
  299.       return new CooldownTracker();
  300.    }
  301.  
  302.    private void updateCape() {
  303.       this.prevChasingPosX = this.chasingPosX;
  304.       this.prevChasingPosY = this.chasingPosY;
  305.       this.prevChasingPosZ = this.chasingPosZ;
  306.       double d0 = this.posX - this.chasingPosX;
  307.       double d1 = this.posY - this.chasingPosY;
  308.       double d2 = this.posZ - this.chasingPosZ;
  309.       double d3 = 10.0D;
  310.       if (d0 > 10.0D) {
  311.          this.chasingPosX = this.posX;
  312.          this.prevChasingPosX = this.chasingPosX;
  313.       }
  314.  
  315.       if (d2 > 10.0D) {
  316.          this.chasingPosZ = this.posZ;
  317.          this.prevChasingPosZ = this.chasingPosZ;
  318.       }
  319.  
  320.       if (d1 > 10.0D) {
  321.          this.chasingPosY = this.posY;
  322.          this.prevChasingPosY = this.chasingPosY;
  323.       }
  324.  
  325.       if (d0 < -10.0D) {
  326.          this.chasingPosX = this.posX;
  327.          this.prevChasingPosX = this.chasingPosX;
  328.       }
  329.  
  330.       if (d2 < -10.0D) {
  331.          this.chasingPosZ = this.posZ;
  332.          this.prevChasingPosZ = this.chasingPosZ;
  333.       }
  334.  
  335.       if (d1 < -10.0D) {
  336.          this.chasingPosY = this.posY;
  337.          this.prevChasingPosY = this.chasingPosY;
  338.       }
  339.  
  340.       this.chasingPosX += d0 * 0.25D;
  341.       this.chasingPosZ += d2 * 0.25D;
  342.       this.chasingPosY += d1 * 0.25D;
  343.    }
  344.  
  345.    protected void updatePose() {
  346.       if (this.isPoseClear(Pose.SWIMMING)) {
  347.          Pose pose;
  348.          if (this.isElytraFlying()) {
  349.             pose = Pose.FALL_FLYING;
  350.          } else if (this.isSleeping()) {
  351.             pose = Pose.SLEEPING;
  352.          } else if (this.isSwimming()) {
  353.             pose = Pose.SWIMMING;
  354.          } else if (this.isSpinAttacking()) {
  355.             pose = Pose.SPIN_ATTACK;
  356.          } else if (this.isSneaking() && !this.abilities.isFlying) {
  357.             pose = Pose.SNEAKING;
  358.          } else {
  359.             pose = Pose.STANDING;
  360.          }
  361.  
  362.          Pose pose1;
  363.          if (!this.isSpectator() && !this.isPassenger() && !this.isPoseClear(pose)) {
  364.             if (this.isPoseClear(Pose.SNEAKING)) {
  365.                pose1 = Pose.SNEAKING;
  366.             } else {
  367.                pose1 = Pose.SWIMMING;
  368.             }
  369.          } else {
  370.             pose1 = pose;
  371.          }
  372.  
  373.          this.setPose(pose1);
  374.       }
  375.    }
  376.  
  377.    /**
  378.     * Return the amount of time this entity should stay in a portal before being transported.
  379.     */
  380.    public int getMaxInPortalTime() {
  381.       return this.abilities.disableDamage ? 1 : 80;
  382.    }
  383.  
  384.    protected SoundEvent getSwimSound() {
  385.       return SoundEvents.ENTITY_PLAYER_SWIM;
  386.    }
  387.  
  388.    protected SoundEvent getSplashSound() {
  389.       return SoundEvents.ENTITY_PLAYER_SPLASH;
  390.    }
  391.  
  392.    protected SoundEvent getHighspeedSplashSound() {
  393.       return SoundEvents.ENTITY_PLAYER_SPLASH_HIGH_SPEED;
  394.    }
  395.  
  396.    /**
  397.     * Return the amount of cooldown before this entity can use a portal again.
  398.     */
  399.    public int getPortalCooldown() {
  400.       return 10;
  401.    }
  402.  
  403.    public void playSound(SoundEvent soundIn, float volume, float pitch) {
  404.       this.world.playSound(this, this.posX, this.posY, this.posZ, soundIn, this.getSoundCategory(), volume, pitch);
  405.    }
  406.  
  407.    public void func_213823_a(SoundEvent p_213823_1_, SoundCategory p_213823_2_, float p_213823_3_, float p_213823_4_) {
  408.    }
  409.  
  410.    public SoundCategory getSoundCategory() {
  411.       return SoundCategory.PLAYERS;
  412.    }
  413.  
  414.    protected int getFireImmuneTicks() {
  415.       return 20;
  416.    }
  417.  
  418.    /**
  419.     * Handler for {@link World#setEntityState}
  420.     */
  421.    @OnlyIn(Dist.CLIENT)
  422.    public void handleStatusUpdate(byte id) {
  423.       if (id == 9) {
  424.          this.onItemUseFinish();
  425.       } else if (id == 23) {
  426.          this.hasReducedDebug = false;
  427.       } else if (id == 22) {
  428.          this.hasReducedDebug = true;
  429.       } else if (id == 43) {
  430.          this.func_213824_a(ParticleTypes.CLOUD);
  431.       } else {
  432.          super.handleStatusUpdate(id);
  433.       }
  434.  
  435.    }
  436.  
  437.    @OnlyIn(Dist.CLIENT)
  438.    private void func_213824_a(IParticleData p_213824_1_) {
  439.       for(int i = 0; i < 5; ++i) {
  440.          double d0 = this.rand.nextGaussian() * 0.02D;
  441.          double d1 = this.rand.nextGaussian() * 0.02D;
  442.          double d2 = this.rand.nextGaussian() * 0.02D;
  443.          this.world.addParticle(p_213824_1_, this.posX + (double)(this.rand.nextFloat() * this.getWidth() * 2.0F) - (double)this.getWidth(), this.posY + 1.0D + (double)(this.rand.nextFloat() * this.getHeight()), this.posZ + (double)(this.rand.nextFloat() * this.getWidth() * 2.0F) - (double)this.getWidth(), d0, d1, d2);
  444.       }
  445.  
  446.    }
  447.  
  448.    /**
  449.     * set current crafting inventory back to the 2x2 square
  450.     */
  451.    public void closeScreen() {
  452.       this.openContainer = this.container;
  453.    }
  454.  
  455.    /**
  456.     * Handles updating while riding another entity
  457.     */
  458.    public void updateRidden() {
  459.       if (!this.world.isRemote && this.isSneaking() && this.isPassenger()) {
  460.          this.stopRiding();
  461.          this.setSneaking(false);
  462.       } else {
  463.          double d0 = this.posX;
  464.          double d1 = this.posY;
  465.          double d2 = this.posZ;
  466.          float f = this.rotationYaw;
  467.          float f1 = this.rotationPitch;
  468.          super.updateRidden();
  469.          this.prevCameraYaw = this.cameraYaw;
  470.          this.cameraYaw = 0.0F;
  471.          this.addMountedMovementStat(this.posX - d0, this.posY - d1, this.posZ - d2);
  472.          if (this.getRidingEntity() instanceof LivingEntity && ((LivingEntity)this.getRidingEntity()).shouldRiderFaceForward(this)) {
  473.             this.rotationPitch = f1;
  474.             this.rotationYaw = f;
  475.             this.renderYawOffset = ((LivingEntity)this.getRidingEntity()).renderYawOffset;
  476.          }
  477.  
  478.       }
  479.    }
  480.  
  481.    /**
  482.     * Keeps moving the entity up so it isn't colliding with blocks and other requirements for this entity to be spawned
  483.     * (only actually used on players though its also on Entity)
  484.     */
  485.    @OnlyIn(Dist.CLIENT)
  486.    public void preparePlayerToSpawn() {
  487.       this.setPose(Pose.STANDING);
  488.       super.preparePlayerToSpawn();
  489.       this.setHealth(this.getMaxHealth());
  490.       this.deathTime = 0;
  491.    }
  492.  
  493.    protected void updateEntityActionState() {
  494.       super.updateEntityActionState();
  495.       this.updateArmSwingProgress();
  496.       this.rotationYawHead = this.rotationYaw;
  497.    }
  498.  
  499.    /**
  500.     * Called frequently so the entity can update its state every tick as required. For example, zombies and skeletons
  501.     * use this to react to sunlight and start to burn.
  502.     */
  503.    public void livingTick() {
  504.       if (this.flyToggleTimer > 0) {
  505.          --this.flyToggleTimer;
  506.       }
  507.  
  508.       if (this.world.getDifficulty() == Difficulty.PEACEFUL && this.world.getGameRules().getBoolean(GameRules.NATURAL_REGENERATION)) {
  509.          if (this.getHealth() < this.getMaxHealth() && this.ticksExisted % 20 == 0) {
  510.             this.heal(1.0F);
  511.          }
  512.  
  513.          if (this.foodStats.needFood() && this.ticksExisted % 10 == 0) {
  514.             this.foodStats.setFoodLevel(this.foodStats.getFoodLevel() + 1);
  515.          }
  516.       }
  517.  
  518.       this.inventory.tick();
  519.       this.prevCameraYaw = this.cameraYaw;
  520.       super.livingTick();
  521.       IAttributeInstance iattributeinstance = this.getAttribute(SharedMonsterAttributes.MOVEMENT_SPEED);
  522.       if (!this.world.isRemote) {
  523.          iattributeinstance.setBaseValue((double)this.abilities.getWalkSpeed());
  524.       }
  525.  
  526.       this.jumpMovementFactor = 0.02F;
  527.       if (this.isSprinting()) {
  528.          this.jumpMovementFactor = (float)((double)this.jumpMovementFactor + 0.005999999865889549D);
  529.       }
  530.  
  531.       this.setAIMoveSpeed((float)iattributeinstance.getValue());
  532.       float f;
  533.       if (this.onGround && !(this.getHealth() <= 0.0F) && !this.isSwimming()) {
  534.          f = Math.min(0.1F, MathHelper.sqrt(func_213296_b(this.getMotion())));
  535.       } else {
  536.          f = 0.0F;
  537.       }
  538.  
  539.       this.cameraYaw += (f - this.cameraYaw) * 0.4F;
  540.       if (this.getHealth() > 0.0F && !this.isSpectator()) {
  541.          AxisAlignedBB axisalignedbb;
  542.          if (this.isPassenger() && !this.getRidingEntity().removed) {
  543.             axisalignedbb = this.getBoundingBox().union(this.getRidingEntity().getBoundingBox()).grow(1.0D, 0.0D, 1.0D);
  544.          } else {
  545.             axisalignedbb = this.getBoundingBox().grow(1.0D, 0.5D, 1.0D);
  546.          }
  547.  
  548.          List<Entity> list = this.world.getEntitiesWithinAABBExcludingEntity(this, axisalignedbb);
  549.  
  550.          for(int i = 0; i < list.size(); ++i) {
  551.             Entity entity = list.get(i);
  552.             if (!entity.removed) {
  553.                this.collideWithPlayer(entity);
  554.             }
  555.          }
  556.       }
  557.  
  558.       this.playShoulderEntityAmbientSound(this.getLeftShoulderEntity());
  559.       this.playShoulderEntityAmbientSound(this.getRightShoulderEntity());
  560.       if (!this.world.isRemote && (this.fallDistance > 0.5F || this.isInWater() || this.isPassenger()) || this.abilities.isFlying || this.isSleeping()) {
  561.          this.spawnShoulderEntities();
  562.       }
  563.  
  564.    }
  565.  
  566.    private void playShoulderEntityAmbientSound(@Nullable CompoundNBT p_192028_1_) {
  567.       if (p_192028_1_ != null && !p_192028_1_.contains("Silent") || !p_192028_1_.getBoolean("Silent")) {
  568.          String s = p_192028_1_.getString("id");
  569.          EntityType.byKey(s).filter((p_213830_0_) -> {
  570.             return p_213830_0_ == EntityType.PARROT;
  571.          }).ifPresent((p_213834_1_) -> {
  572.             ParrotEntity.playAmbientSound(this.world, this);
  573.          });
  574.       }
  575.  
  576.    }
  577.  
  578.    private void collideWithPlayer(Entity entityIn) {
  579.       entityIn.onCollideWithPlayer(this);
  580.    }
  581.  
  582.    public int getScore() {
  583.       return this.dataManager.get(PLAYER_SCORE);
  584.    }
  585.  
  586.    /**
  587.     * Set player's score
  588.     */
  589.    public void setScore(int scoreIn) {
  590.       this.dataManager.set(PLAYER_SCORE, scoreIn);
  591.    }
  592.  
  593.    /**
  594.     * Add to player's score
  595.     */
  596.    public void addScore(int scoreIn) {
  597.       int i = this.getScore();
  598.       this.dataManager.set(PLAYER_SCORE, i + scoreIn);
  599.    }
  600.  
  601.    /**
  602.     * Called when the mob's health reaches 0.
  603.     */
  604.    public void onDeath(DamageSource cause) {
  605.       if (net.minecraftforge.common.ForgeHooks.onLivingDeath(this,  cause)) return;
  606.       super.onDeath(cause);
  607.       this.setPosition(this.posX, this.posY, this.posZ);
  608.       if (!this.isSpectator()) {
  609.          this.spawnDrops(cause);
  610.       }
  611.  
  612.       if (cause != null) {
  613.          this.setMotion((double)(-MathHelper.cos((this.attackedAtYaw + this.rotationYaw) * ((float)Math.PI / 180F)) * 0.1F), (double)0.1F, (double)(-MathHelper.sin((this.attackedAtYaw + this.rotationYaw) * ((float)Math.PI / 180F)) * 0.1F));
  614.       } else {
  615.          this.setMotion(0.0D, 0.1D, 0.0D);
  616.       }
  617.  
  618.       this.addStat(Stats.DEATHS);
  619.       this.takeStat(Stats.CUSTOM.get(Stats.TIME_SINCE_DEATH));
  620.       this.takeStat(Stats.CUSTOM.get(Stats.TIME_SINCE_REST));
  621.       this.extinguish();
  622.       this.setFlag(0, false);
  623.    }
  624.  
  625.    protected void dropInventory() {
  626.       super.dropInventory();
  627.       if (!this.world.getGameRules().getBoolean(GameRules.KEEP_INVENTORY)) {
  628.          this.destroyVanishingCursedItems();
  629.          this.inventory.dropAllItems();
  630.       }
  631.  
  632.    }
  633.  
  634.    protected void destroyVanishingCursedItems() {
  635.       for(int i = 0; i < this.inventory.getSizeInventory(); ++i) {
  636.          ItemStack itemstack = this.inventory.getStackInSlot(i);
  637.          if (!itemstack.isEmpty() && EnchantmentHelper.hasVanishingCurse(itemstack)) {
  638.             this.inventory.removeStackFromSlot(i);
  639.          }
  640.       }
  641.  
  642.    }
  643.  
  644.    protected SoundEvent getHurtSound(DamageSource damageSourceIn) {
  645.       if (damageSourceIn == DamageSource.ON_FIRE) {
  646.          return SoundEvents.ENTITY_PLAYER_HURT_ON_FIRE;
  647.       } else if (damageSourceIn == DamageSource.DROWN) {
  648.          return SoundEvents.ENTITY_PLAYER_HURT_DROWN;
  649.       } else {
  650.          return damageSourceIn == DamageSource.SWEET_BERRY_BUSH ? SoundEvents.ENTITY_PLAYER_HURT_SWEET_BERRY_BUSH : SoundEvents.ENTITY_PLAYER_HURT;
  651.       }
  652.    }
  653.  
  654.    protected SoundEvent getDeathSound() {
  655.       return SoundEvents.ENTITY_PLAYER_DEATH;
  656.    }
  657.  
  658.    /**
  659.     * Drop one item out of the currently selected stack if {@code dropAll} is false. If {@code dropItem} is true the
  660.     * entire stack is dropped.
  661.     */
  662.    @Nullable
  663.    public ItemEntity dropItem(boolean dropAll) {
  664.       ItemStack stack = inventory.getCurrentItem();
  665.       if (stack.isEmpty() || !stack.onDroppedByPlayer(this)) return null;
  666.       return net.minecraftforge.common.ForgeHooks.onPlayerTossEvent(this, this.inventory.decrStackSize(this.inventory.currentItem, dropAll && !this.inventory.getCurrentItem().isEmpty() ? this.inventory.getCurrentItem().getCount() : 1), true);
  667.    }
  668.  
  669.    /**
  670.     * Drops an item into the world.
  671.     */
  672.    @Nullable
  673.    public ItemEntity dropItem(ItemStack itemStackIn, boolean unused) {
  674.       return net.minecraftforge.common.ForgeHooks.onPlayerTossEvent(this, itemStackIn, false);
  675.    }
  676.  
  677.    /**
  678.     * Creates and drops the provided item. Depending on the dropAround, it will drop teh item around the player, instead
  679.     * of dropping the item from where the player is pointing at. Likewise, if traceItem is true, the dropped item entity
  680.     * will have the thrower set as the player.
  681.     */
  682.    @Nullable
  683.    public ItemEntity dropItem(ItemStack droppedItem, boolean dropAround, boolean traceItem) {
  684.       if (droppedItem.isEmpty()) {
  685.          return null;
  686.       } else {
  687.          double d0 = this.posY - (double)0.3F + (double)this.getEyeHeight();
  688.          ItemEntity itementity = new ItemEntity(this.world, this.posX, d0, this.posZ, droppedItem);
  689.          itementity.setPickupDelay(40);
  690.          if (traceItem) {
  691.             itementity.setThrowerId(this.getUniqueID());
  692.          }
  693.  
  694.          if (dropAround) {
  695.             float f = this.rand.nextFloat() * 0.5F;
  696.             float f1 = this.rand.nextFloat() * ((float)Math.PI * 2F);
  697.             this.setMotion((double)(-MathHelper.sin(f1) * f), (double)0.2F, (double)(MathHelper.cos(f1) * f));
  698.          } else {
  699.             float f7 = 0.3F;
  700.             float f8 = MathHelper.sin(this.rotationPitch * ((float)Math.PI / 180F));
  701.             float f2 = MathHelper.cos(this.rotationPitch * ((float)Math.PI / 180F));
  702.             float f3 = MathHelper.sin(this.rotationYaw * ((float)Math.PI / 180F));
  703.             float f4 = MathHelper.cos(this.rotationYaw * ((float)Math.PI / 180F));
  704.             float f5 = this.rand.nextFloat() * ((float)Math.PI * 2F);
  705.             float f6 = 0.02F * this.rand.nextFloat();
  706.             itementity.setMotion((double)(-f3 * f2 * 0.3F) + Math.cos((double)f5) * (double)f6, (double)(-f8 * 0.3F + 0.1F + (this.rand.nextFloat() - this.rand.nextFloat()) * 0.1F), (double)(f4 * f2 * 0.3F) + Math.sin((double)f5) * (double)f6);
  707.          }
  708.  
  709.          return itementity;
  710.       }
  711.    }
  712.  
  713.    @Deprecated //Use location sensitive version below
  714.    public float getDigSpeed(BlockState state) {
  715.       return getDigSpeed(state, null);
  716.    }
  717.  
  718.    public float getDigSpeed(BlockState state, @Nullable BlockPos pos) {
  719.       float f = this.inventory.getDestroySpeed(state);
  720.       if (f > 1.0F) {
  721.          int i = EnchantmentHelper.getEfficiencyModifier(this);
  722.          ItemStack itemstack = this.getHeldItemMainhand();
  723.          if (i > 0 && !itemstack.isEmpty()) {
  724.             f += (float)(i * i + 1);
  725.          }
  726.       }
  727.  
  728.       if (EffectUtils.hasMiningSpeedup(this)) {
  729.          f *= 1.0F + (float)(EffectUtils.getMiningSpeedup(this) + 1) * 0.2F;
  730.       }
  731.  
  732.       if (this.isPotionActive(Effects.MINING_FATIGUE)) {
  733.          float f1;
  734.          switch(this.getActivePotionEffect(Effects.MINING_FATIGUE).getAmplifier()) {
  735.          case 0:
  736.             f1 = 0.3F;
  737.             break;
  738.          case 1:
  739.             f1 = 0.09F;
  740.             break;
  741.          case 2:
  742.             f1 = 0.0027F;
  743.             break;
  744.          case 3:
  745.          default:
  746.             f1 = 8.1E-4F;
  747.          }
  748.  
  749.          f *= f1;
  750.       }
  751.  
  752.       if (this.areEyesInFluid(FluidTags.WATER) && !EnchantmentHelper.hasAquaAffinity(this)) {
  753.          f /= 5.0F;
  754.       }
  755.  
  756.       if (!this.onGround) {
  757.          f /= 5.0F;
  758.       }
  759.  
  760.       f = net.minecraftforge.event.ForgeEventFactory.getBreakSpeed(this, state, f, pos);
  761.       return f;
  762.    }
  763.  
  764.    public boolean canHarvestBlock(BlockState state) {
  765.       return net.minecraftforge.event.ForgeEventFactory.doPlayerHarvestCheck(this, state, state.getMaterial().isToolNotRequired() || this.inventory.canHarvestBlock(state));
  766.    }
  767.  
  768.    /**
  769.     * (abstract) Protected helper method to read subclass entity data from NBT.
  770.     */
  771.    public void readAdditional(CompoundNBT compound) {
  772.       super.readAdditional(compound);
  773.       this.setUniqueId(getUUID(this.gameProfile));
  774.       ListNBT listnbt = compound.getList("Inventory", 10);
  775.       this.inventory.read(listnbt);
  776.       this.inventory.currentItem = compound.getInt("SelectedItemSlot");
  777.       this.sleepTimer = compound.getShort("SleepTimer");
  778.       this.experience = compound.getFloat("XpP");
  779.       this.experienceLevel = compound.getInt("XpLevel");
  780.       this.experienceTotal = compound.getInt("XpTotal");
  781.       this.xpSeed = compound.getInt("XpSeed");
  782.       if (this.xpSeed == 0) {
  783.          this.xpSeed = this.rand.nextInt();
  784.       }
  785.  
  786.       this.setScore(compound.getInt("Score"));
  787.       if (compound.contains("SpawnX", 99) && compound.contains("SpawnY", 99) && compound.contains("SpawnZ", 99)) {
  788.          this.spawnPos = new BlockPos(compound.getInt("SpawnX"), compound.getInt("SpawnY"), compound.getInt("SpawnZ"));
  789.          this.spawnForced = compound.getBoolean("SpawnForced");
  790.       }
  791.  
  792.       compound.getList("Spawns", 10).forEach(e -> {
  793.          CompoundNBT data = (CompoundNBT)e;
  794.          ResourceLocation dim = new ResourceLocation(data.getString("Dim"));
  795.          this.spawnPosMap.put(dim, new BlockPos(data.getInt("SpawnX"), data.getInt("SpawnY"), data.getInt("SpawnZ")));
  796.          this.spawnForcedMap.put(dim, data.getBoolean("SpawnForced"));
  797.       });
  798.       net.minecraft.world.dimension.DimensionType spawnDim = null;
  799.       if (compound.contains("SpawnDimension", net.minecraftforge.common.util.Constants.NBT.TAG_STRING))
  800.          spawnDim = net.minecraft.world.dimension.DimensionType.byName(new ResourceLocation(compound.getString("SpawnDimension")));
  801.       this.spawnDimension = spawnDim != null ? spawnDim : net.minecraft.world.dimension.DimensionType.OVERWORLD;
  802.  
  803.       this.foodStats.read(compound);
  804.       this.abilities.read(compound);
  805.       if (compound.contains("EnderItems", 9)) {
  806.          this.enterChestInventory.read(compound.getList("EnderItems", 10));
  807.       }
  808.  
  809.       if (compound.contains("ShoulderEntityLeft", 10)) {
  810.          this.setLeftShoulderEntity(compound.getCompound("ShoulderEntityLeft"));
  811.       }
  812.  
  813.       if (compound.contains("ShoulderEntityRight", 10)) {
  814.          this.setRightShoulderEntity(compound.getCompound("ShoulderEntityRight"));
  815.       }
  816.  
  817.    }
  818.  
  819.    public void writeAdditional(CompoundNBT compound) {
  820.       super.writeAdditional(compound);
  821.       compound.putInt("DataVersion", SharedConstants.getVersion().getWorldVersion());
  822.       compound.put("Inventory", this.inventory.write(new ListNBT()));
  823.       compound.putInt("SelectedItemSlot", this.inventory.currentItem);
  824.       compound.putShort("SleepTimer", (short)this.sleepTimer);
  825.       compound.putFloat("XpP", this.experience);
  826.       compound.putInt("XpLevel", this.experienceLevel);
  827.       compound.putInt("XpTotal", this.experienceTotal);
  828.       compound.putInt("XpSeed", this.xpSeed);
  829.       compound.putInt("Score", this.getScore());
  830.       if (this.spawnPos != null) {
  831.          compound.putInt("SpawnX", this.spawnPos.getX());
  832.          compound.putInt("SpawnY", this.spawnPos.getY());
  833.          compound.putInt("SpawnZ", this.spawnPos.getZ());
  834.          compound.putBoolean("SpawnForced", this.spawnForced);
  835.       }
  836.  
  837.       this.foodStats.write(compound);
  838.       this.abilities.write(compound);
  839.       compound.put("EnderItems", this.enterChestInventory.write());
  840.       if (!this.getLeftShoulderEntity().isEmpty()) {
  841.          compound.put("ShoulderEntityLeft", this.getLeftShoulderEntity());
  842.       }
  843.  
  844.       if (!this.getRightShoulderEntity().isEmpty()) {
  845.          compound.put("ShoulderEntityRight", this.getRightShoulderEntity());
  846.       }
  847.  
  848.       ListNBT spawnlist = new ListNBT();
  849.       spawnPosMap.forEach((dim, pos) -> {
  850.          if (pos != null) {
  851.             CompoundNBT data = new CompoundNBT();
  852.             data.putString("Dim", dim.toString());
  853.             data.putInt("SpawnX", pos.getX());
  854.             data.putInt("SpawnY", pos.getY());
  855.             data.putInt("SpawnZ", pos.getZ());
  856.             data.putBoolean("SpawnForced", spawnForcedMap.getOrDefault(dim, false));
  857.             spawnlist.add(data);
  858.          }
  859.       });
  860.       compound.put("Spawns", spawnlist);
  861.       if (spawnDimension != net.minecraft.world.dimension.DimensionType.OVERWORLD) {
  862.          compound.putString("SpawnDimension", spawnDimension.getRegistryName().toString());
  863.       }
  864.    }
  865.  
  866.    /**
  867.     * Called when the entity is attacked.
  868.     */
  869.    public boolean attackEntityFrom(DamageSource source, float amount) {
  870.       if (!net.minecraftforge.common.ForgeHooks.onPlayerAttack(this, source, amount)) return false;
  871.       if (this.isInvulnerableTo(source)) {
  872.          return false;
  873.       } else if (this.abilities.disableDamage && !source.canHarmInCreative()) {
  874.          return false;
  875.       } else {
  876.          this.idleTime = 0;
  877.          if (this.getHealth() <= 0.0F) {
  878.             return false;
  879.          } else {
  880.             this.spawnShoulderEntities();
  881.             if (source.isDifficultyScaled()) {
  882.                if (this.world.getDifficulty() == Difficulty.PEACEFUL) {
  883.                   amount = 0.0F;
  884.                }
  885.  
  886.                if (this.world.getDifficulty() == Difficulty.EASY) {
  887.                   amount = Math.min(amount / 2.0F + 1.0F, amount);
  888.                }
  889.  
  890.                if (this.world.getDifficulty() == Difficulty.HARD) {
  891.                   amount = amount * 3.0F / 2.0F;
  892.                }
  893.             }
  894.  
  895.             return amount == 0.0F ? false : super.attackEntityFrom(source, amount);
  896.          }
  897.       }
  898.    }
  899.  
  900.    protected void blockUsingShield(LivingEntity p_190629_1_) {
  901.       super.blockUsingShield(p_190629_1_);
  902.       if (p_190629_1_.getHeldItemMainhand().canDisableShield(this.activeItemStack, this, p_190629_1_)) {
  903.          this.disableShield(true);
  904.       }
  905.  
  906.    }
  907.  
  908.    public boolean canAttackPlayer(PlayerEntity other) {
  909.       Team team = this.getTeam();
  910.       Team team1 = other.getTeam();
  911.       if (team == null) {
  912.          return true;
  913.       } else {
  914.          return !team.isSameTeam(team1) ? true : team.getAllowFriendlyFire();
  915.       }
  916.    }
  917.  
  918.    protected void damageArmor(float damage) {
  919.       this.inventory.damageArmor(damage);
  920.    }
  921.  
  922.    protected void damageShield(float damage) {
  923.       if (damage >= 3.0F && this.activeItemStack.isShield(this)) {
  924.          int i = 1 + MathHelper.floor(damage);
  925.          Hand hand = this.getActiveHand();
  926.          this.activeItemStack.damageItem(i, this, (p_213833_1_) -> {
  927.             p_213833_1_.sendBreakAnimation(hand);
  928.             net.minecraftforge.event.ForgeEventFactory.onPlayerDestroyItem(this, this.activeItemStack, hand);
  929.          });
  930.          if (this.activeItemStack.isEmpty()) {
  931.             if (hand == Hand.MAIN_HAND) {
  932.                this.setItemStackToSlot(EquipmentSlotType.MAINHAND, ItemStack.EMPTY);
  933.             } else {
  934.                this.setItemStackToSlot(EquipmentSlotType.OFFHAND, ItemStack.EMPTY);
  935.             }
  936.  
  937.             this.activeItemStack = ItemStack.EMPTY;
  938.             this.playSound(SoundEvents.ITEM_SHIELD_BREAK, 0.8F, 0.8F + this.world.rand.nextFloat() * 0.4F);
  939.          }
  940.       }
  941.  
  942.    }
  943.  
  944.    /**
  945.     * Deals damage to the entity. This will take the armor of the entity into consideration before damaging the health
  946.     * bar.
  947.     */
  948.    protected void damageEntity(DamageSource damageSrc, float damageAmount) {
  949.       if (!this.isInvulnerableTo(damageSrc)) {
  950.          damageAmount = net.minecraftforge.common.ForgeHooks.onLivingHurt(this, damageSrc, damageAmount);
  951.          if (damageAmount <= 0) return;
  952.          damageAmount = this.applyArmorCalculations(damageSrc, damageAmount);
  953.          damageAmount = this.applyPotionDamageCalculations(damageSrc, damageAmount);
  954.          float f = damageAmount;
  955.          damageAmount = Math.max(damageAmount - this.getAbsorptionAmount(), 0.0F);
  956.          this.setAbsorptionAmount(this.getAbsorptionAmount() - (f - damageAmount));
  957.          damageAmount = net.minecraftforge.common.ForgeHooks.onLivingDamage(this, damageSrc, damageAmount);
  958.          float f1 = f - damageAmount;
  959.          if (f1 > 0.0F && f1 < 3.4028235E37F) {
  960.             this.addStat(Stats.DAMAGE_ABSORBED, Math.round(f1 * 10.0F));
  961.          }
  962.  
  963.          if (damageAmount != 0.0F) {
  964.             this.addExhaustion(damageSrc.getHungerDamage());
  965.             float f2 = this.getHealth();
  966.             this.setHealth(this.getHealth() - damageAmount);
  967.             this.getCombatTracker().trackDamage(damageSrc, f2, damageAmount);
  968.             if (damageAmount < 3.4028235E37F) {
  969.                this.addStat(Stats.DAMAGE_TAKEN, Math.round(damageAmount * 10.0F));
  970.             }
  971.  
  972.          }
  973.       }
  974.    }
  975.  
  976.    public void openSignEditor(SignTileEntity signTile) {
  977.    }
  978.  
  979.    public void openMinecartCommandBlock(CommandBlockLogic commandBlock) {
  980.    }
  981.  
  982.    public void openCommandBlock(CommandBlockTileEntity commandBlock) {
  983.    }
  984.  
  985.    public void openStructureBlock(StructureBlockTileEntity structure) {
  986.    }
  987.  
  988.    public void func_213826_a(JigsawTileEntity p_213826_1_) {
  989.    }
  990.  
  991.    public void openHorseInventory(AbstractHorseEntity horse, IInventory inventoryIn) {
  992.    }
  993.  
  994.    public OptionalInt openContainer(@Nullable INamedContainerProvider p_213829_1_) {
  995.       return OptionalInt.empty();
  996.    }
  997.  
  998.    public void func_213818_a(int p_213818_1_, MerchantOffers p_213818_2_, int p_213818_3_, int p_213818_4_, boolean p_213818_5_, boolean p_213818_6_) {
  999.    }
  1000.  
  1001.    public void openBook(ItemStack stack, Hand hand) {
  1002.    }
  1003.  
  1004.    public ActionResultType interactOn(Entity entityToInteractOn, Hand hand) {
  1005.       if (this.isSpectator()) {
  1006.          if (entityToInteractOn instanceof INamedContainerProvider) {
  1007.             this.openContainer((INamedContainerProvider)entityToInteractOn);
  1008.          }
  1009.  
  1010.          return ActionResultType.PASS;
  1011.       } else {
  1012.          ActionResultType cancelResult = net.minecraftforge.common.ForgeHooks.onInteractEntity(this, entityToInteractOn, hand);
  1013.          if (cancelResult != null) return cancelResult;
  1014.          ItemStack itemstack = this.getHeldItem(hand);
  1015.          ItemStack itemstack1 = itemstack.isEmpty() ? ItemStack.EMPTY : itemstack.copy();
  1016.          if (entityToInteractOn.processInitialInteract(this, hand)) {
  1017.             if (this.abilities.isCreativeMode && itemstack == this.getHeldItem(hand) && itemstack.getCount() < itemstack1.getCount()) {
  1018.                itemstack.setCount(itemstack1.getCount());
  1019.             }
  1020.  
  1021.             if (!this.abilities.isCreativeMode && itemstack.isEmpty()) {
  1022.                net.minecraftforge.event.ForgeEventFactory.onPlayerDestroyItem(this, itemstack1, hand);
  1023.             }
  1024.             return ActionResultType.SUCCESS;
  1025.          } else {
  1026.             if (!itemstack.isEmpty() && entityToInteractOn instanceof LivingEntity) {
  1027.                if (this.abilities.isCreativeMode) {
  1028.                   itemstack = itemstack1;
  1029.                }
  1030.  
  1031.                if (itemstack.interactWithEntity(this, (LivingEntity)entityToInteractOn, hand)) {
  1032.                   if (itemstack.isEmpty() && !this.abilities.isCreativeMode) {
  1033.                      net.minecraftforge.event.ForgeEventFactory.onPlayerDestroyItem(this, itemstack1, hand);
  1034.                      this.setHeldItem(hand, ItemStack.EMPTY);
  1035.                   }
  1036.  
  1037.                   return ActionResultType.SUCCESS;
  1038.                }
  1039.             }
  1040.  
  1041.             return ActionResultType.PASS;
  1042.          }
  1043.       }
  1044.    }
  1045.  
  1046.    /**
  1047.     * Returns the Y Offset of this entity.
  1048.     */
  1049.    public double getYOffset() {
  1050.       return -0.35D;
  1051.    }
  1052.  
  1053.    /**
  1054.     * Dismounts this entity from the entity it is riding.
  1055.     */
  1056.    public void stopRiding() {
  1057.       super.stopRiding();
  1058.       this.rideCooldown = 0;
  1059.    }
  1060.  
  1061.    /**
  1062.     * Dead and sleeping entities cannot move
  1063.     */
  1064.    protected boolean isMovementBlocked() {
  1065.       return super.isMovementBlocked() || this.isSleeping();
  1066.    }
  1067.  
  1068.    /**
  1069.     * Attacks for the player the targeted entity with the currently equipped item.  The equipped item has hitEntity
  1070.     * called on it. Args: targetEntity
  1071.     */
  1072.    public void attackTargetEntityWithCurrentItem(Entity targetEntity) {
  1073.       if (!net.minecraftforge.common.ForgeHooks.onPlayerAttackTarget(this, targetEntity)) return;
  1074.       if (targetEntity.canBeAttackedWithItem()) {
  1075.          if (!targetEntity.hitByEntity(this)) {
  1076.             float f = (float)this.getAttribute(SharedMonsterAttributes.ATTACK_DAMAGE).getValue();
  1077.             float f1;
  1078.             if (targetEntity instanceof LivingEntity) {
  1079.                f1 = EnchantmentHelper.getModifierForCreature(this.getHeldItemMainhand(), ((LivingEntity)targetEntity).getCreatureAttribute());
  1080.             } else {
  1081.                f1 = EnchantmentHelper.getModifierForCreature(this.getHeldItemMainhand(), CreatureAttribute.UNDEFINED);
  1082.             }
  1083.  
  1084.             float f2 = this.getCooledAttackStrength(0.5F);
  1085.             f = f * (0.2F + f2 * f2 * 0.8F);
  1086.             f1 = f1 * f2;
  1087.             this.resetCooldown();
  1088.             if (f > 0.0F || f1 > 0.0F) {
  1089.                boolean flag = f2 > 0.9F;
  1090.                boolean flag1 = false;
  1091.                int i = 0;
  1092.                i = i + EnchantmentHelper.getKnockbackModifier(this);
  1093.                if (this.isSprinting() && flag) {
  1094.                   this.world.playSound((PlayerEntity)null, this.posX, this.posY, this.posZ, SoundEvents.ENTITY_PLAYER_ATTACK_KNOCKBACK, this.getSoundCategory(), 1.0F, 1.0F);
  1095.                   ++i;
  1096.                   flag1 = true;
  1097.                }
  1098.  
  1099.                boolean flag2 = flag && this.fallDistance > 0.0F && !this.onGround && !this.isOnLadder() && !this.isInWater() && !this.isPotionActive(Effects.BLINDNESS) && !this.isPassenger() && targetEntity instanceof LivingEntity;
  1100.                flag2 = flag2 && !this.isSprinting();
  1101.                net.minecraftforge.event.entity.player.CriticalHitEvent hitResult = net.minecraftforge.common.ForgeHooks.getCriticalHit(this, targetEntity, flag2, flag2 ? 1.5F : 1.0F);
  1102.                flag2 = hitResult != null;
  1103.                if (flag2) {
  1104.                   f *= hitResult.getDamageModifier();
  1105.                }
  1106.  
  1107.                f = f + f1;
  1108.                boolean flag3 = false;
  1109.                double d0 = (double)(this.distanceWalkedModified - this.prevDistanceWalkedModified);
  1110.                if (flag && !flag2 && !flag1 && this.onGround && d0 < (double)this.getAIMoveSpeed()) {
  1111.                   ItemStack itemstack = this.getHeldItem(Hand.MAIN_HAND);
  1112.                   if (itemstack.getItem() instanceof SwordItem) {
  1113.                      flag3 = true;
  1114.                   }
  1115.                }
  1116.  
  1117.                float f4 = 0.0F;
  1118.                boolean flag4 = false;
  1119.                int j = EnchantmentHelper.getFireAspectModifier(this);
  1120.                if (targetEntity instanceof LivingEntity) {
  1121.                   f4 = ((LivingEntity)targetEntity).getHealth();
  1122.                   if (j > 0 && !targetEntity.isBurning()) {
  1123.                      flag4 = true;
  1124.                      targetEntity.setFire(1);
  1125.                   }
  1126.                }
  1127.  
  1128.                Vec3d vec3d = targetEntity.getMotion();
  1129.                boolean flag5 = targetEntity.attackEntityFrom(DamageSource.causePlayerDamage(this), f);
  1130.                if (flag5) {
  1131.                   if (i > 0) {
  1132.                      if (targetEntity instanceof LivingEntity) {
  1133.                         ((LivingEntity)targetEntity).knockBack(this, (float)i * 0.5F, (double)MathHelper.sin(this.rotationYaw * ((float)Math.PI / 180F)), (double)(-MathHelper.cos(this.rotationYaw * ((float)Math.PI / 180F))));
  1134.                      } else {
  1135.                         targetEntity.addVelocity((double)(-MathHelper.sin(this.rotationYaw * ((float)Math.PI / 180F)) * (float)i * 0.5F), 0.1D, (double)(MathHelper.cos(this.rotationYaw * ((float)Math.PI / 180F)) * (float)i * 0.5F));
  1136.                      }
  1137.  
  1138.                      this.setMotion(this.getMotion().mul(0.6D, 1.0D, 0.6D));
  1139.                      this.setSprinting(false);
  1140.                   }
  1141.  
  1142.                   if (flag3) {
  1143.                      float f3 = 1.0F + EnchantmentHelper.getSweepingDamageRatio(this) * f;
  1144.  
  1145.                      for(LivingEntity livingentity : this.world.getEntitiesWithinAABB(LivingEntity.class, targetEntity.getBoundingBox().grow(1.0D, 0.25D, 1.0D))) {
  1146.                         if (livingentity != this && livingentity != targetEntity && !this.isOnSameTeam(livingentity) && (!(livingentity instanceof ArmorStandEntity) || !((ArmorStandEntity)livingentity).hasMarker()) && this.getDistanceSq(livingentity) < 9.0D) {
  1147.                            livingentity.knockBack(this, 0.4F, (double)MathHelper.sin(this.rotationYaw * ((float)Math.PI / 180F)), (double)(-MathHelper.cos(this.rotationYaw * ((float)Math.PI / 180F))));
  1148.                            livingentity.attackEntityFrom(DamageSource.causePlayerDamage(this), f3);
  1149.                         }
  1150.                      }
  1151.  
  1152.                      this.world.playSound((PlayerEntity)null, this.posX, this.posY, this.posZ, SoundEvents.ENTITY_PLAYER_ATTACK_SWEEP, this.getSoundCategory(), 1.0F, 1.0F);
  1153.                      this.spawnSweepParticles();
  1154.                   }
  1155.  
  1156.                   if (targetEntity instanceof ServerPlayerEntity && targetEntity.velocityChanged) {
  1157.                      ((ServerPlayerEntity)targetEntity).connection.sendPacket(new SEntityVelocityPacket(targetEntity));
  1158.                      targetEntity.velocityChanged = false;
  1159.                      targetEntity.setMotion(vec3d);
  1160.                   }
  1161.  
  1162.                   if (flag2) {
  1163.                      this.world.playSound((PlayerEntity)null, this.posX, this.posY, this.posZ, SoundEvents.ENTITY_PLAYER_ATTACK_CRIT, this.getSoundCategory(), 1.0F, 1.0F);
  1164.                      this.onCriticalHit(targetEntity);
  1165.                   }
  1166.  
  1167.                   if (!flag2 && !flag3) {
  1168.                      if (flag) {
  1169.                         this.world.playSound((PlayerEntity)null, this.posX, this.posY, this.posZ, SoundEvents.ENTITY_PLAYER_ATTACK_STRONG, this.getSoundCategory(), 1.0F, 1.0F);
  1170.                      } else {
  1171.                         this.world.playSound((PlayerEntity)null, this.posX, this.posY, this.posZ, SoundEvents.ENTITY_PLAYER_ATTACK_WEAK, this.getSoundCategory(), 1.0F, 1.0F);
  1172.                      }
  1173.                   }
  1174.  
  1175.                   if (f1 > 0.0F) {
  1176.                      this.onEnchantmentCritical(targetEntity);
  1177.                   }
  1178.  
  1179.                   this.setLastAttackedEntity(targetEntity);
  1180.                   if (targetEntity instanceof LivingEntity) {
  1181.                      EnchantmentHelper.applyThornEnchantments((LivingEntity)targetEntity, this);
  1182.                   }
  1183.  
  1184.                   EnchantmentHelper.applyArthropodEnchantments(this, targetEntity);
  1185.                   ItemStack itemstack1 = this.getHeldItemMainhand();
  1186.                   Entity entity = targetEntity;
  1187.                   if (targetEntity instanceof EnderDragonPartEntity) {
  1188.                      entity = ((EnderDragonPartEntity)targetEntity).dragon;
  1189.                   }
  1190.  
  1191.                   if (!this.world.isRemote && !itemstack1.isEmpty() && entity instanceof LivingEntity) {
  1192.                      ItemStack copy = itemstack1.copy();
  1193.                      itemstack1.hitEntity((LivingEntity)entity, this);
  1194.                      if (itemstack1.isEmpty()) {
  1195.                         net.minecraftforge.event.ForgeEventFactory.onPlayerDestroyItem(this, copy, Hand.MAIN_HAND);
  1196.                         this.setHeldItem(Hand.MAIN_HAND, ItemStack.EMPTY);
  1197.                      }
  1198.                   }
  1199.  
  1200.                   if (targetEntity instanceof LivingEntity) {
  1201.                      float f5 = f4 - ((LivingEntity)targetEntity).getHealth();
  1202.                      this.addStat(Stats.DAMAGE_DEALT, Math.round(f5 * 10.0F));
  1203.                      if (j > 0) {
  1204.                         targetEntity.setFire(j * 4);
  1205.                      }
  1206.  
  1207.                      if (this.world instanceof ServerWorld && f5 > 2.0F) {
  1208.                         int k = (int)((double)f5 * 0.5D);
  1209.                         ((ServerWorld)this.world).spawnParticle(ParticleTypes.DAMAGE_INDICATOR, targetEntity.posX, targetEntity.posY + (double)(targetEntity.getHeight() * 0.5F), targetEntity.posZ, k, 0.1D, 0.0D, 0.1D, 0.2D);
  1210.                      }
  1211.                   }
  1212.  
  1213.                   this.addExhaustion(0.1F);
  1214.                } else {
  1215.                   this.world.playSound((PlayerEntity)null, this.posX, this.posY, this.posZ, SoundEvents.ENTITY_PLAYER_ATTACK_NODAMAGE, this.getSoundCategory(), 1.0F, 1.0F);
  1216.                   if (flag4) {
  1217.                      targetEntity.extinguish();
  1218.                   }
  1219.                }
  1220.             }
  1221.  
  1222.          }
  1223.       }
  1224.    }
  1225.  
  1226.    protected void spinAttack(LivingEntity p_204804_1_) {
  1227.       this.attackTargetEntityWithCurrentItem(p_204804_1_);
  1228.    }
  1229.  
  1230.    public void disableShield(boolean p_190777_1_) {
  1231.       float f = 0.25F + (float)EnchantmentHelper.getEfficiencyModifier(this) * 0.05F;
  1232.       if (p_190777_1_) {
  1233.          f += 0.75F;
  1234.       }
  1235.  
  1236.       if (this.rand.nextFloat() < f) {
  1237.          this.getCooldownTracker().setCooldown(this.getActiveItemStack().getItem(), 100);
  1238.          this.resetActiveHand();
  1239.          this.world.setEntityState(this, (byte)30);
  1240.       }
  1241.  
  1242.    }
  1243.  
  1244.    /**
  1245.     * Called when the entity is dealt a critical hit.
  1246.     */
  1247.    public void onCriticalHit(Entity entityHit) {
  1248.    }
  1249.  
  1250.    public void onEnchantmentCritical(Entity entityHit) {
  1251.    }
  1252.  
  1253.    public void spawnSweepParticles() {
  1254.       double d0 = (double)(-MathHelper.sin(this.rotationYaw * ((float)Math.PI / 180F)));
  1255.       double d1 = (double)MathHelper.cos(this.rotationYaw * ((float)Math.PI / 180F));
  1256.       if (this.world instanceof ServerWorld) {
  1257.          ((ServerWorld)this.world).spawnParticle(ParticleTypes.SWEEP_ATTACK, this.posX + d0, this.posY + (double)this.getHeight() * 0.5D, this.posZ + d1, 0, d0, 0.0D, d1, 0.0D);
  1258.       }
  1259.  
  1260.    }
  1261.  
  1262.    @OnlyIn(Dist.CLIENT)
  1263.    public void respawnPlayer() {
  1264.    }
  1265.  
  1266.    @Override
  1267.    public void remove(boolean keepData) {
  1268.       super.remove(keepData);
  1269.       this.container.onContainerClosed(this);
  1270.       if (this.openContainer != null) {
  1271.          this.openContainer.onContainerClosed(this);
  1272.       }
  1273.  
  1274.    }
  1275.  
  1276.    /**
  1277.     * returns true if this is an EntityPlayerSP, or the logged in player.
  1278.     */
  1279.    public boolean isUser() {
  1280.       return false;
  1281.    }
  1282.  
  1283.    /**
  1284.     * Returns the GameProfile for this player
  1285.     */
  1286.    public GameProfile getGameProfile() {
  1287.       return this.gameProfile;
  1288.    }
  1289.  
  1290.    public Either<PlayerEntity.SleepResult, Unit> trySleep(BlockPos at) {
  1291.       Optional<BlockPos> optAt = Optional.of(at);
  1292.       PlayerEntity.SleepResult ret = net.minecraftforge.event.ForgeEventFactory.onPlayerSleepInBed(this, optAt);
  1293.       if (ret != null) return Either.left(ret);
  1294.       Direction direction = this.world.getBlockState(at).get(HorizontalBlock.HORIZONTAL_FACING);
  1295.       if (!this.world.isRemote) {
  1296.          if (this.isSleeping() || !this.isAlive()) {
  1297.             return Either.left(PlayerEntity.SleepResult.OTHER_PROBLEM);
  1298.          }
  1299.  
  1300.          if (!this.world.dimension.isSurfaceWorld()) {
  1301.             return Either.left(PlayerEntity.SleepResult.NOT_POSSIBLE_HERE);
  1302.          }
  1303.  
  1304.          if (!net.minecraftforge.event.ForgeEventFactory.fireSleepingTimeCheck(this, optAt)) {
  1305.             return Either.left(PlayerEntity.SleepResult.NOT_POSSIBLE_NOW);
  1306.          }
  1307.  
  1308.          if (!this.bedInRange(at, direction)) {
  1309.             return Either.left(PlayerEntity.SleepResult.TOO_FAR_AWAY);
  1310.          }
  1311.  
  1312.          if (this.func_213828_b(at, direction)) {
  1313.             return Either.left(PlayerEntity.SleepResult.OBSTRUCTED);
  1314.          }
  1315.  
  1316.          if (!this.isCreative()) {
  1317.             double d0 = 8.0D;
  1318.             double d1 = 5.0D;
  1319.             List<MonsterEntity> list = this.world.getEntitiesWithinAABB(MonsterEntity.class, new AxisAlignedBB((double)at.getX() - 8.0D, (double)at.getY() - 5.0D, (double)at.getZ() - 8.0D, (double)at.getX() + 8.0D, (double)at.getY() + 5.0D, (double)at.getZ() + 8.0D), (p_213820_1_) -> {
  1320.                return p_213820_1_.isPreventingPlayerRest(this);
  1321.             });
  1322.             if (!list.isEmpty()) {
  1323.                return Either.left(PlayerEntity.SleepResult.NOT_SAFE);
  1324.             }
  1325.          }
  1326.       }
  1327.  
  1328.       this.startSleeping(at);
  1329.       this.sleepTimer = 0;
  1330.       if (this.world instanceof ServerWorld) {
  1331.          ((ServerWorld)this.world).updateAllPlayersSleepingFlag();
  1332.       }
  1333.  
  1334.       return Either.right(Unit.INSTANCE);
  1335.    }
  1336.  
  1337.    public void startSleeping(BlockPos p_213342_1_) {
  1338.       this.takeStat(Stats.CUSTOM.get(Stats.TIME_SINCE_REST));
  1339.       super.startSleeping(p_213342_1_);
  1340.    }
  1341.  
  1342.    private boolean bedInRange(BlockPos p_190774_1_, Direction p_190774_2_) {
  1343.       if (Math.abs(this.posX - (double)p_190774_1_.getX()) <= 3.0D && Math.abs(this.posY - (double)p_190774_1_.getY()) <= 2.0D && Math.abs(this.posZ - (double)p_190774_1_.getZ()) <= 3.0D) {
  1344.          return true;
  1345.       } else if (p_190774_2_ == null) {
  1346.          return false;
  1347.       } else {
  1348.          BlockPos blockpos = p_190774_1_.offset(p_190774_2_.getOpposite());
  1349.          return Math.abs(this.posX - (double)blockpos.getX()) <= 3.0D && Math.abs(this.posY - (double)blockpos.getY()) <= 2.0D && Math.abs(this.posZ - (double)blockpos.getZ()) <= 3.0D;
  1350.       }
  1351.    }
  1352.  
  1353.    private boolean func_213828_b(BlockPos p_213828_1_, Direction p_213828_2_) {
  1354.       BlockPos blockpos = p_213828_1_.up();
  1355.       return !this.isNormalCube(blockpos) || !this.isNormalCube(blockpos.offset(p_213828_2_.getOpposite()));
  1356.    }
  1357.  
  1358.    /**
  1359.     * Wake up the player if they're sleeping.
  1360.     */
  1361.    public void wakeUpPlayer(boolean immediately, boolean updateWorldFlag, boolean setSpawn) {
  1362.       net.minecraftforge.event.ForgeEventFactory.onPlayerWakeup(this, immediately, updateWorldFlag, setSpawn);
  1363.       Optional<BlockPos> optional = this.getBedPosition();
  1364.       super.wakeUp();
  1365.       if (this.world instanceof ServerWorld && updateWorldFlag) {
  1366.          ((ServerWorld)this.world).updateAllPlayersSleepingFlag();
  1367.       }
  1368.  
  1369.       this.sleepTimer = immediately ? 0 : 100;
  1370.       if (setSpawn) {
  1371.          optional.ifPresent((p_213825_1_) -> {
  1372.             this.setSpawnPoint(p_213825_1_, false);
  1373.          });
  1374.       }
  1375.  
  1376.    }
  1377.  
  1378.    public void wakeUp() {
  1379.       this.wakeUpPlayer(true, true, false);
  1380.    }
  1381.  
  1382.    public static Optional<Vec3d> func_213822_a(IWorldReader p_213822_0_, BlockPos p_213822_1_, boolean p_213822_2_) {
  1383.       BlockState blockState = p_213822_0_.getBlockState(p_213822_1_);
  1384.       if (!(blockState.isBed(p_213822_0_, p_213822_1_, null))) {
  1385.          if (!p_213822_2_) {
  1386.             return Optional.empty();
  1387.          } else {
  1388.             boolean flag = blockState.getBlock().canSpawnInBlock();
  1389.             boolean flag1 = p_213822_0_.getBlockState(p_213822_1_.up()).getBlock().canSpawnInBlock();
  1390.             return flag && flag1 ? Optional.of(new Vec3d((double)p_213822_1_.getX() + 0.5D, (double)p_213822_1_.getY() + 0.1D, (double)p_213822_1_.getZ() + 0.5D)) : Optional.empty();
  1391.          }
  1392.       } else {
  1393.          return blockState.getBedSpawnPosition(EntityType.PLAYER, p_213822_0_, p_213822_1_, null);
  1394.       }
  1395.    }
  1396.  
  1397.    /**
  1398.     * Returns whether or not the player is asleep and the screen has fully faded.
  1399.     */
  1400.    public boolean isPlayerFullyAsleep() {
  1401.       return this.isSleeping() && this.sleepTimer >= 100;
  1402.    }
  1403.  
  1404.    public int getSleepTimer() {
  1405.       return this.sleepTimer;
  1406.    }
  1407.  
  1408.    public void sendStatusMessage(ITextComponent chatComponent, boolean actionBar) {
  1409.    }
  1410.  
  1411.    @Deprecated //Forge: Use Dimension sensitive version
  1412.    public BlockPos getBedLocation() {
  1413.       return getBedLocation(this.dimension);
  1414.    }
  1415.  
  1416.    /**
  1417.     * A dimension aware version of getBedLocation.
  1418.     * @param dim The dimension to get the bed spawn for
  1419.     * @return The player specific spawn location for the dimension.  May be null.
  1420.     */
  1421.    public BlockPos getBedLocation(net.minecraft.world.dimension.DimensionType dim) {
  1422.       return dim == net.minecraft.world.dimension.DimensionType.OVERWORLD ? spawnPos : spawnPosMap.get(dim.getRegistryName());
  1423.    }
  1424.  
  1425.    @Deprecated //Forge: Use Dimension sensitive version
  1426.    public boolean isSpawnForced() {
  1427.       return isSpawnForced(this.dimension);
  1428.    }
  1429.  
  1430.    /**
  1431.     * A dimension aware version of isSpawnForced.
  1432.     * Noramally isSpawnForced is used to determine if the respawn system should check for a bed or not.
  1433.     * This just extends that to be dimension aware.
  1434.     * @param dim The dimension to get whether to check for a bed before spawning for
  1435.     * @return The player specific spawn location for the dimension.  May be null.
  1436.     */
  1437.    public boolean isSpawnForced(net.minecraft.world.dimension.DimensionType dim) {
  1438.       return dim == net.minecraft.world.dimension.DimensionType.OVERWORLD ? spawnForced : spawnForcedMap.getOrDefault(dim.getRegistryName(), false);
  1439.    }
  1440.  
  1441.    @Deprecated //Forge: Use Dimension sensitive version
  1442.    public void setSpawnPoint(BlockPos pos, boolean forced) {
  1443.       setSpawnPoint(pos, forced, this.dimension);
  1444.    }
  1445.  
  1446.    /**
  1447.     * A dimension aware version of setSpawnChunk.
  1448.     * This functions identically, but allows you to specify which dimension to affect, rather than affecting the player's current dimension.
  1449.     * @param pos The spawn point to set as the player-specific spawn point for the dimension
  1450.     * @param forced Whether or not the respawn code should check for a bed at this location (true means it won't check for a bed)
  1451.     * @param dim Which dimension to apply the player-specific respawn point to
  1452.     */
  1453.    public void setSpawnPoint(@Nullable BlockPos pos, boolean forced, net.minecraft.world.dimension.DimensionType dim) {
  1454.        if(net.minecraftforge.event.ForgeEventFactory.onPlayerSpawnSet(this, pos, forced)) return;
  1455.        if (dim != net.minecraft.world.dimension.DimensionType.OVERWORLD) {
  1456.           if (pos == null) {
  1457.              spawnPosMap.remove(dim.getRegistryName());
  1458.              spawnForcedMap.remove(dim.getRegistryName());
  1459.           } else {
  1460.              spawnPosMap.put(dim.getRegistryName(), pos);
  1461.              spawnForcedMap.put(dim.getRegistryName(), forced);
  1462.           }
  1463.           return;
  1464.        }
  1465.        if (pos != null) {
  1466.           this.spawnPos = pos;
  1467.           this.spawnForced = forced;
  1468.        } else {
  1469.           this.spawnPos = null;
  1470.           this.spawnForced = false;
  1471.        }
  1472.    }
  1473.  
  1474.    public void addStat(ResourceLocation stat) {
  1475.       this.addStat(Stats.CUSTOM.get(stat));
  1476.    }
  1477.  
  1478.    public void addStat(ResourceLocation p_195067_1_, int p_195067_2_) {
  1479.       this.addStat(Stats.CUSTOM.get(p_195067_1_), p_195067_2_);
  1480.    }
  1481.  
  1482.    /**
  1483.     * Add a stat once
  1484.     */
  1485.    public void addStat(Stat<?> stat) {
  1486.       this.addStat(stat, 1);
  1487.    }
  1488.  
  1489.    /**
  1490.     * Adds a value to a statistic field.
  1491.     */
  1492.    public void addStat(Stat<?> stat, int amount) {
  1493.    }
  1494.  
  1495.    public void takeStat(Stat<?> stat) {
  1496.    }
  1497.  
  1498.    public int unlockRecipes(Collection<IRecipe<?>> p_195065_1_) {
  1499.       return 0;
  1500.    }
  1501.  
  1502.    public void unlockRecipes(ResourceLocation[] p_193102_1_) {
  1503.    }
  1504.  
  1505.    public int resetRecipes(Collection<IRecipe<?>> p_195069_1_) {
  1506.       return 0;
  1507.    }
  1508.  
  1509.    /**
  1510.     * Causes this entity to do an upwards motion (jumping).
  1511.     */
  1512.    public void jump() {
  1513.       super.jump();
  1514.       this.addStat(Stats.JUMP);
  1515.       if (this.isSprinting()) {
  1516.          this.addExhaustion(0.2F);
  1517.       } else {
  1518.          this.addExhaustion(0.05F);
  1519.       }
  1520.  
  1521.    }
  1522.  
  1523.    public void travel(Vec3d p_213352_1_) {
  1524.       double d0 = this.posX;
  1525.       double d1 = this.posY;
  1526.       double d2 = this.posZ;
  1527.       if (this.isSwimming() && !this.isPassenger()) {
  1528.          double d3 = this.getLookVec().y;
  1529.          double d4 = d3 < -0.2D ? 0.085D : 0.06D;
  1530.          if (d3 <= 0.0D || this.isJumping || !this.world.getBlockState(new BlockPos(this.posX, this.posY + 1.0D - 0.1D, this.posZ)).getFluidState().isEmpty()) {
  1531.             Vec3d vec3d1 = this.getMotion();
  1532.             this.setMotion(vec3d1.add(0.0D, (d3 - vec3d1.y) * d4, 0.0D));
  1533.          }
  1534.       }
  1535.  
  1536.       if (this.abilities.isFlying && !this.isPassenger()) {
  1537.          double d5 = this.getMotion().y;
  1538.          float f = this.jumpMovementFactor;
  1539.          this.jumpMovementFactor = this.abilities.getFlySpeed() * (float)(this.isSprinting() ? 2 : 1);
  1540.          super.travel(p_213352_1_);
  1541.          Vec3d vec3d = this.getMotion();
  1542.          this.setMotion(vec3d.x, d5 * 0.6D, vec3d.z);
  1543.          this.jumpMovementFactor = f;
  1544.          this.fallDistance = 0.0F;
  1545.          this.setFlag(7, false);
  1546.       } else {
  1547.          super.travel(p_213352_1_);
  1548.       }
  1549.  
  1550.       this.addMovementStat(this.posX - d0, this.posY - d1, this.posZ - d2);
  1551.    }
  1552.  
  1553.    public void updateSwimming() {
  1554.       if (this.abilities.isFlying) {
  1555.          this.setSwimming(false);
  1556.       } else {
  1557.          super.updateSwimming();
  1558.       }
  1559.  
  1560.    }
  1561.  
  1562.    protected boolean isNormalCube(BlockPos pos) {
  1563.       return !this.world.getBlockState(pos).causesSuffocation(this.world, pos);
  1564.    }
  1565.  
  1566.    /**
  1567.     * the movespeed used for the new AI system
  1568.     */
  1569.    public float getAIMoveSpeed() {
  1570.       return (float)this.getAttribute(SharedMonsterAttributes.MOVEMENT_SPEED).getValue();
  1571.    }
  1572.  
  1573.    /**
  1574.     * Adds a value to a movement statistic field - like run, walk, swin or climb.
  1575.     */
  1576.    public void addMovementStat(double p_71000_1_, double p_71000_3_, double p_71000_5_) {
  1577.       if (!this.isPassenger()) {
  1578.          if (this.isSwimming()) {
  1579.             int i = Math.round(MathHelper.sqrt(p_71000_1_ * p_71000_1_ + p_71000_3_ * p_71000_3_ + p_71000_5_ * p_71000_5_) * 100.0F);
  1580.             if (i > 0) {
  1581.                this.addStat(Stats.SWIM_ONE_CM, i);
  1582.                this.addExhaustion(0.01F * (float)i * 0.01F);
  1583.             }
  1584.          } else if (this.areEyesInFluid(FluidTags.WATER, true)) {
  1585.             int j = Math.round(MathHelper.sqrt(p_71000_1_ * p_71000_1_ + p_71000_3_ * p_71000_3_ + p_71000_5_ * p_71000_5_) * 100.0F);
  1586.             if (j > 0) {
  1587.                this.addStat(Stats.WALK_UNDER_WATER_ONE_CM, j);
  1588.                this.addExhaustion(0.01F * (float)j * 0.01F);
  1589.             }
  1590.          } else if (this.isInWater()) {
  1591.             int k = Math.round(MathHelper.sqrt(p_71000_1_ * p_71000_1_ + p_71000_5_ * p_71000_5_) * 100.0F);
  1592.             if (k > 0) {
  1593.                this.addStat(Stats.WALK_ON_WATER_ONE_CM, k);
  1594.                this.addExhaustion(0.01F * (float)k * 0.01F);
  1595.             }
  1596.          } else if (this.isOnLadder()) {
  1597.             if (p_71000_3_ > 0.0D) {
  1598.                this.addStat(Stats.CLIMB_ONE_CM, (int)Math.round(p_71000_3_ * 100.0D));
  1599.             }
  1600.          } else if (this.onGround) {
  1601.             int l = Math.round(MathHelper.sqrt(p_71000_1_ * p_71000_1_ + p_71000_5_ * p_71000_5_) * 100.0F);
  1602.             if (l > 0) {
  1603.                if (this.isSprinting()) {
  1604.                   this.addStat(Stats.SPRINT_ONE_CM, l);
  1605.                   this.addExhaustion(0.1F * (float)l * 0.01F);
  1606.                } else if (this.isSneaking()) {
  1607.                   this.addStat(Stats.CROUCH_ONE_CM, l);
  1608.                   this.addExhaustion(0.0F * (float)l * 0.01F);
  1609.                } else {
  1610.                   this.addStat(Stats.WALK_ONE_CM, l);
  1611.                   this.addExhaustion(0.0F * (float)l * 0.01F);
  1612.                }
  1613.             }
  1614.          } else if (this.isElytraFlying()) {
  1615.             int i1 = Math.round(MathHelper.sqrt(p_71000_1_ * p_71000_1_ + p_71000_3_ * p_71000_3_ + p_71000_5_ * p_71000_5_) * 100.0F);
  1616.             this.addStat(Stats.AVIATE_ONE_CM, i1);
  1617.          } else {
  1618.             int j1 = Math.round(MathHelper.sqrt(p_71000_1_ * p_71000_1_ + p_71000_5_ * p_71000_5_) * 100.0F);
  1619.             if (j1 > 25) {
  1620.                this.addStat(Stats.FLY_ONE_CM, j1);
  1621.             }
  1622.          }
  1623.  
  1624.       }
  1625.    }
  1626.  
  1627.    /**
  1628.     * Adds a value to a mounted movement statistic field - by minecart, boat, or pig.
  1629.     */
  1630.    private void addMountedMovementStat(double p_71015_1_, double p_71015_3_, double p_71015_5_) {
  1631.       if (this.isPassenger()) {
  1632.          int i = Math.round(MathHelper.sqrt(p_71015_1_ * p_71015_1_ + p_71015_3_ * p_71015_3_ + p_71015_5_ * p_71015_5_) * 100.0F);
  1633.          if (i > 0) {
  1634.             if (this.getRidingEntity() instanceof AbstractMinecartEntity) {
  1635.                this.addStat(Stats.MINECART_ONE_CM, i);
  1636.             } else if (this.getRidingEntity() instanceof BoatEntity) {
  1637.                this.addStat(Stats.BOAT_ONE_CM, i);
  1638.             } else if (this.getRidingEntity() instanceof PigEntity) {
  1639.                this.addStat(Stats.PIG_ONE_CM, i);
  1640.             } else if (this.getRidingEntity() instanceof AbstractHorseEntity) {
  1641.                this.addStat(Stats.HORSE_ONE_CM, i);
  1642.             }
  1643.          }
  1644.       }
  1645.  
  1646.    }
  1647.  
  1648.    public void fall(float distance, float damageMultiplier) {
  1649.       if (!this.abilities.allowFlying) {
  1650.          if (distance >= 2.0F) {
  1651.             this.addStat(Stats.FALL_ONE_CM, (int)Math.round((double)distance * 100.0D));
  1652.          }
  1653.  
  1654.          super.fall(distance, damageMultiplier);
  1655.       } else {
  1656.          net.minecraftforge.event.ForgeEventFactory.onPlayerFall(this, distance, damageMultiplier);
  1657.       }
  1658.    }
  1659.  
  1660.    /**
  1661.     * Plays the {@link #getSplashSound() splash sound}, and the {@link ParticleType#WATER_BUBBLE} and {@link
  1662.     * ParticleType#WATER_SPLASH} particles.
  1663.     */
  1664.    protected void doWaterSplashEffect() {
  1665.       if (!this.isSpectator()) {
  1666.          super.doWaterSplashEffect();
  1667.       }
  1668.  
  1669.    }
  1670.  
  1671.    protected SoundEvent getFallSound(int heightIn) {
  1672.       return heightIn > 4 ? SoundEvents.ENTITY_PLAYER_BIG_FALL : SoundEvents.ENTITY_PLAYER_SMALL_FALL;
  1673.    }
  1674.  
  1675.    /**
  1676.     * This method gets called when the entity kills another one.
  1677.     */
  1678.    public void onKillEntity(LivingEntity entityLivingIn) {
  1679.       this.addStat(Stats.ENTITY_KILLED.get(entityLivingIn.getType()));
  1680.    }
  1681.  
  1682.    public void setMotionMultiplier(BlockState p_213295_1_, Vec3d p_213295_2_) {
  1683.       if (!this.abilities.isFlying) {
  1684.          super.setMotionMultiplier(p_213295_1_, p_213295_2_);
  1685.       }
  1686.  
  1687.    }
  1688.  
  1689.    public void giveExperiencePoints(int p_195068_1_) {
  1690.       this.addScore(p_195068_1_);
  1691.       this.experience += (float)p_195068_1_ / (float)this.xpBarCap();
  1692.       this.experienceTotal = MathHelper.clamp(this.experienceTotal + p_195068_1_, 0, Integer.MAX_VALUE);
  1693.  
  1694.       while(this.experience < 0.0F) {
  1695.          float f = this.experience * (float)this.xpBarCap();
  1696.          if (this.experienceLevel > 0) {
  1697.             this.addExperienceLevel(-1);
  1698.             this.experience = 1.0F + f / (float)this.xpBarCap();
  1699.          } else {
  1700.             this.addExperienceLevel(-1);
  1701.             this.experience = 0.0F;
  1702.          }
  1703.       }
  1704.  
  1705.       while(this.experience >= 1.0F) {
  1706.          this.experience = (this.experience - 1.0F) * (float)this.xpBarCap();
  1707.          this.addExperienceLevel(1);
  1708.          this.experience /= (float)this.xpBarCap();
  1709.       }
  1710.  
  1711.    }
  1712.  
  1713.    public int getXPSeed() {
  1714.       return this.xpSeed;
  1715.    }
  1716.  
  1717.    public void onEnchant(ItemStack enchantedItem, int cost) {
  1718.       this.experienceLevel -= cost;
  1719.       if (this.experienceLevel < 0) {
  1720.          this.experienceLevel = 0;
  1721.          this.experience = 0.0F;
  1722.          this.experienceTotal = 0;
  1723.       }
  1724.  
  1725.       this.xpSeed = this.rand.nextInt();
  1726.    }
  1727.  
  1728.    /**
  1729.     * Add experience levels to this player.
  1730.     */
  1731.    public void addExperienceLevel(int levels) {
  1732.       this.experienceLevel += levels;
  1733.       if (this.experienceLevel < 0) {
  1734.          this.experienceLevel = 0;
  1735.          this.experience = 0.0F;
  1736.          this.experienceTotal = 0;
  1737.       }
  1738.  
  1739.       if (levels > 0 && this.experienceLevel % 5 == 0 && (float)this.lastXPSound < (float)this.ticksExisted - 100.0F) {
  1740.          float f = this.experienceLevel > 30 ? 1.0F : (float)this.experienceLevel / 30.0F;
  1741.          this.world.playSound((PlayerEntity)null, this.posX, this.posY, this.posZ, SoundEvents.ENTITY_PLAYER_LEVELUP, this.getSoundCategory(), f * 0.75F, 1.0F);
  1742.          this.lastXPSound = this.ticksExisted;
  1743.       }
  1744.  
  1745.    }
  1746.  
  1747.    /**
  1748.     * This method returns the cap amount of experience that the experience bar can hold. With each level, the experience
  1749.     * cap on the player's experience bar is raised by 10.
  1750.     */
  1751.    public int xpBarCap() {
  1752.       if (this.experienceLevel >= 30) {
  1753.          return 112 + (this.experienceLevel - 30) * 9;
  1754.       } else {
  1755.          return this.experienceLevel >= 15 ? 37 + (this.experienceLevel - 15) * 5 : 7 + this.experienceLevel * 2;
  1756.       }
  1757.    }
  1758.  
  1759.    /**
  1760.     * increases exhaustion level by supplied amount
  1761.     */
  1762.    public void addExhaustion(float exhaustion) {
  1763.       if (!this.abilities.disableDamage) {
  1764.          if (!this.world.isRemote) {
  1765.             this.foodStats.addExhaustion(exhaustion);
  1766.          }
  1767.  
  1768.       }
  1769.    }
  1770.  
  1771.    /**
  1772.     * Returns the player's FoodStats object.
  1773.     */
  1774.    public FoodStats getFoodStats() {
  1775.       return this.foodStats;
  1776.    }
  1777.  
  1778.    public boolean canEat(boolean ignoreHunger) {
  1779.       return !this.abilities.disableDamage && (ignoreHunger || this.foodStats.needFood());
  1780.    }
  1781.  
  1782.    /**
  1783.     * Checks if the player's health is not full and not zero.
  1784.     */
  1785.    public boolean shouldHeal() {
  1786.       return this.getHealth() > 0.0F && this.getHealth() < this.getMaxHealth();
  1787.    }
  1788.  
  1789.    public boolean isAllowEdit() {
  1790.       return this.abilities.allowEdit;
  1791.    }
  1792.  
  1793.    /**
  1794.     * Returns whether this player can modify the block at a certain location with the given stack.
  1795.     * <p>
  1796.     * The position being queried is {@code pos.offset(facing.getOpposite()))}.
  1797.     *
  1798.     * @return Whether this player may modify the queried location in the current world
  1799.     * @see ItemStack#canPlaceOn(Block)
  1800.     * @see ItemStack#canEditBlocks()
  1801.     * @see PlayerCapabilities#allowEdit
  1802.     */
  1803.    public boolean canPlayerEdit(BlockPos pos, Direction facing, ItemStack stack) {
  1804.       if (this.abilities.allowEdit) {
  1805.          return true;
  1806.       } else {
  1807.          BlockPos blockpos = pos.offset(facing.getOpposite());
  1808.          CachedBlockInfo cachedblockinfo = new CachedBlockInfo(this.world, blockpos, false);
  1809.          return stack.canPlaceOn(this.world.getTags(), cachedblockinfo);
  1810.       }
  1811.    }
  1812.  
  1813.    /**
  1814.     * Get the experience points the entity currently has.
  1815.     */
  1816.    protected int getExperiencePoints(PlayerEntity player) {
  1817.       if (!this.world.getGameRules().getBoolean(GameRules.KEEP_INVENTORY) && !this.isSpectator()) {
  1818.          int i = this.experienceLevel * 7;
  1819.          return i > 100 ? 100 : i;
  1820.       } else {
  1821.          return 0;
  1822.       }
  1823.    }
  1824.  
  1825.    /**
  1826.     * Only use is to identify if class is an instance of player for experience dropping
  1827.     */
  1828.    protected boolean isPlayer() {
  1829.       return true;
  1830.    }
  1831.  
  1832.    @OnlyIn(Dist.CLIENT)
  1833.    public boolean getAlwaysRenderNameTagForRender() {
  1834.       return true;
  1835.    }
  1836.  
  1837.    /**
  1838.     * returns if this entity triggers Block.onEntityWalking on the blocks they walk on. used for spiders and wolves to
  1839.     * prevent them from trampling crops
  1840.     */
  1841.    protected boolean canTriggerWalking() {
  1842.       return !this.abilities.isFlying;
  1843.    }
  1844.  
  1845.    /**
  1846.     * Sends the player's abilities to the server (if there is one).
  1847.     */
  1848.    public void sendPlayerAbilities() {
  1849.    }
  1850.  
  1851.    /**
  1852.     * Sets the player's game mode and sends it to them.
  1853.     */
  1854.    public void setGameType(GameType gameType) {
  1855.    }
  1856.  
  1857.    public ITextComponent getName() {
  1858.       return new StringTextComponent(this.gameProfile.getName());
  1859.    }
  1860.  
  1861.    /**
  1862.     * Returns the InventoryEnderChest of this player.
  1863.     */
  1864.    public EnderChestInventory getInventoryEnderChest() {
  1865.       return this.enterChestInventory;
  1866.    }
  1867.  
  1868.    public ItemStack getItemStackFromSlot(EquipmentSlotType slotIn) {
  1869.       if (slotIn == EquipmentSlotType.MAINHAND) {
  1870.          return this.inventory.getCurrentItem();
  1871.       } else if (slotIn == EquipmentSlotType.OFFHAND) {
  1872.          return this.inventory.offHandInventory.get(0);
  1873.       } else {
  1874.          return slotIn.getSlotType() == EquipmentSlotType.Group.ARMOR ? this.inventory.armorInventory.get(slotIn.getIndex()) : ItemStack.EMPTY;
  1875.       }
  1876.    }
  1877.  
  1878.    public void setItemStackToSlot(EquipmentSlotType slotIn, ItemStack stack) {
  1879.       if (slotIn == EquipmentSlotType.MAINHAND) {
  1880.          this.playEquipSound(stack);
  1881.          this.inventory.mainInventory.set(this.inventory.currentItem, stack);
  1882.       } else if (slotIn == EquipmentSlotType.OFFHAND) {
  1883.          this.playEquipSound(stack);
  1884.          this.inventory.offHandInventory.set(0, stack);
  1885.       } else if (slotIn.getSlotType() == EquipmentSlotType.Group.ARMOR) {
  1886.          this.playEquipSound(stack);
  1887.          this.inventory.armorInventory.set(slotIn.getIndex(), stack);
  1888.       }
  1889.  
  1890.    }
  1891.  
  1892.    public boolean addItemStackToInventory(ItemStack p_191521_1_) {
  1893.       this.playEquipSound(p_191521_1_);
  1894.       return this.inventory.addItemStackToInventory(p_191521_1_);
  1895.    }
  1896.  
  1897.    public Iterable<ItemStack> getHeldEquipment() {
  1898.       return Lists.newArrayList(this.getHeldItemMainhand(), this.getHeldItemOffhand());
  1899.    }
  1900.  
  1901.    public Iterable<ItemStack> getArmorInventoryList() {
  1902.       return this.inventory.armorInventory;
  1903.    }
  1904.  
  1905.    public boolean addShoulderEntity(CompoundNBT p_192027_1_) {
  1906.       if (!this.isPassenger() && this.onGround && !this.isInWater()) {
  1907.          if (this.getLeftShoulderEntity().isEmpty()) {
  1908.             this.setLeftShoulderEntity(p_192027_1_);
  1909.             this.field_223730_e = this.world.getGameTime();
  1910.             return true;
  1911.          } else if (this.getRightShoulderEntity().isEmpty()) {
  1912.             this.setRightShoulderEntity(p_192027_1_);
  1913.             this.field_223730_e = this.world.getGameTime();
  1914.             return true;
  1915.          } else {
  1916.             return false;
  1917.          }
  1918.       } else {
  1919.          return false;
  1920.       }
  1921.    }
  1922.  
  1923.    protected void spawnShoulderEntities() {
  1924.       if (this.field_223730_e + 20L < this.world.getGameTime()) {
  1925.          this.spawnShoulderEntity(this.getLeftShoulderEntity());
  1926.          this.setLeftShoulderEntity(new CompoundNBT());
  1927.          this.spawnShoulderEntity(this.getRightShoulderEntity());
  1928.          this.setRightShoulderEntity(new CompoundNBT());
  1929.       }
  1930.  
  1931.    }
  1932.  
  1933.    private void spawnShoulderEntity(CompoundNBT p_192026_1_) {
  1934.       if (!this.world.isRemote && !p_192026_1_.isEmpty()) {
  1935.          EntityType.loadEntityUnchecked(p_192026_1_, this.world).ifPresent((p_213827_1_) -> {
  1936.             if (p_213827_1_ instanceof TameableEntity) {
  1937.                ((TameableEntity)p_213827_1_).setOwnerId(this.entityUniqueID);
  1938.             }
  1939.  
  1940.             p_213827_1_.setPosition(this.posX, this.posY + (double)0.7F, this.posZ);
  1941.             ((ServerWorld)this.world).summonEntity(p_213827_1_);
  1942.          });
  1943.       }
  1944.  
  1945.    }
  1946.  
  1947.    /**
  1948.     * Only used by renderer in EntityLivingBase subclasses.
  1949.     * Determines if an entity is visible or not to a specific player, if the entity is normally invisible.
  1950.     * For EntityLivingBase subclasses, returning false when invisible will render the entity semi-transparent.
  1951.     */
  1952.    @OnlyIn(Dist.CLIENT)
  1953.    public boolean isInvisibleToPlayer(PlayerEntity player) {
  1954.       if (!this.isInvisible()) {
  1955.          return false;
  1956.       } else if (player.isSpectator()) {
  1957.          return false;
  1958.       } else {
  1959.          Team team = this.getTeam();
  1960.          return team == null || player == null || player.getTeam() != team || !team.getSeeFriendlyInvisiblesEnabled();
  1961.       }
  1962.    }
  1963.  
  1964.    /**
  1965.     * Returns true if the player is in spectator mode.
  1966.     */
  1967.    public abstract boolean isSpectator();
  1968.  
  1969.    public boolean isSwimming() {
  1970.       return !this.abilities.isFlying && !this.isSpectator() && super.isSwimming();
  1971.    }
  1972.  
  1973.    public abstract boolean isCreative();
  1974.  
  1975.    public boolean isPushedByWater() {
  1976.       return !this.abilities.isFlying;
  1977.    }
  1978.  
  1979.    public Scoreboard getWorldScoreboard() {
  1980.       return this.world.getScoreboard();
  1981.    }
  1982.  
  1983.    public ITextComponent getDisplayName() {
  1984.       ITextComponent itextcomponent = new StringTextComponent("");
  1985.       prefixes.forEach(e -> itextcomponent.appendSibling(e));
  1986.       itextcomponent.appendSibling(ScorePlayerTeam.formatMemberName(this.getTeam(), this.getName()));
  1987.       suffixes.forEach(e -> itextcomponent.appendSibling(e));
  1988.       return this.addTellEvent(itextcomponent);
  1989.    }
  1990.  
  1991.    public ITextComponent getDisplayNameAndUUID() {
  1992.       return (new StringTextComponent("")).appendSibling(this.getName()).appendText(" (").appendText(this.gameProfile.getId().toString()).appendText(")");
  1993.    }
  1994.  
  1995.    private ITextComponent addTellEvent(ITextComponent p_208016_1_) {
  1996.       String s = this.getGameProfile().getName();
  1997.       return p_208016_1_.applyTextStyle((p_211521_2_) -> {
  1998.          p_211521_2_.setClickEvent(new ClickEvent(ClickEvent.Action.SUGGEST_COMMAND, "/tell " + s + " ")).setHoverEvent(this.getHoverEvent()).setInsertion(s);
  1999.       });
  2000.    }
  2001.  
  2002.    /**
  2003.     * Returns a String to use as this entity's name in the scoreboard/entity selector systems
  2004.     */
  2005.    public String getScoreboardName() {
  2006.       return this.getGameProfile().getName();
  2007.    }
  2008.  
  2009.    public float getStandingEyeHeight(Pose poseIn, EntitySize sizeIn) {
  2010.       switch(poseIn) {
  2011.       case SWIMMING:
  2012.       case FALL_FLYING:
  2013.       case SPIN_ATTACK:
  2014.          return 0.4F;
  2015.       case SNEAKING:
  2016.          return 1.27F;
  2017.       default:
  2018.          return 1.62F;
  2019.       }
  2020.    }
  2021.  
  2022.    public void setAbsorptionAmount(float amount) {
  2023.       if (amount < 0.0F) {
  2024.          amount = 0.0F;
  2025.       }
  2026.  
  2027.       this.getDataManager().set(ABSORPTION, amount);
  2028.    }
  2029.  
  2030.    /**
  2031.     * Returns the amount of health added by the Absorption effect.
  2032.     */
  2033.    public float getAbsorptionAmount() {
  2034.       return this.getDataManager().get(ABSORPTION);
  2035.    }
  2036.  
  2037.    /**
  2038.     * Gets a players UUID given their GameProfie
  2039.     */
  2040.    public static UUID getUUID(GameProfile profile) {
  2041.       UUID uuid = profile.getId();
  2042.       if (uuid == null) {
  2043.          uuid = getOfflineUUID(profile.getName());
  2044.       }
  2045.  
  2046.       return uuid;
  2047.    }
  2048.  
  2049.    public static UUID getOfflineUUID(String username) {
  2050.       return UUID.nameUUIDFromBytes(("OfflinePlayer:" + username).getBytes(StandardCharsets.UTF_8));
  2051.    }
  2052.  
  2053.    @OnlyIn(Dist.CLIENT)
  2054.    public boolean isWearing(PlayerModelPart part) {
  2055.       return (this.getDataManager().get(PLAYER_MODEL_FLAG) & part.getPartMask()) == part.getPartMask();
  2056.    }
  2057.  
  2058.    public boolean replaceItemInInventory(int inventorySlot, ItemStack itemStackIn) {
  2059.       if (inventorySlot >= 0 && inventorySlot < this.inventory.mainInventory.size()) {
  2060.          this.inventory.setInventorySlotContents(inventorySlot, itemStackIn);
  2061.          return true;
  2062.       } else {
  2063.          EquipmentSlotType equipmentslottype;
  2064.          if (inventorySlot == 100 + EquipmentSlotType.HEAD.getIndex()) {
  2065.             equipmentslottype = EquipmentSlotType.HEAD;
  2066.          } else if (inventorySlot == 100 + EquipmentSlotType.CHEST.getIndex()) {
  2067.             equipmentslottype = EquipmentSlotType.CHEST;
  2068.          } else if (inventorySlot == 100 + EquipmentSlotType.LEGS.getIndex()) {
  2069.             equipmentslottype = EquipmentSlotType.LEGS;
  2070.          } else if (inventorySlot == 100 + EquipmentSlotType.FEET.getIndex()) {
  2071.             equipmentslottype = EquipmentSlotType.FEET;
  2072.          } else {
  2073.             equipmentslottype = null;
  2074.          }
  2075.  
  2076.          if (inventorySlot == 98) {
  2077.             this.setItemStackToSlot(EquipmentSlotType.MAINHAND, itemStackIn);
  2078.             return true;
  2079.          } else if (inventorySlot == 99) {
  2080.             this.setItemStackToSlot(EquipmentSlotType.OFFHAND, itemStackIn);
  2081.             return true;
  2082.          } else if (equipmentslottype == null) {
  2083.             int i = inventorySlot - 200;
  2084.             if (i >= 0 && i < this.enterChestInventory.getSizeInventory()) {
  2085.                this.enterChestInventory.setInventorySlotContents(i, itemStackIn);
  2086.                return true;
  2087.             } else {
  2088.                return false;
  2089.             }
  2090.          } else {
  2091.             if (!itemStackIn.isEmpty()) {
  2092.                if (!(itemStackIn.getItem() instanceof ArmorItem) && !(itemStackIn.getItem() instanceof ElytraItem)) {
  2093.                   if (equipmentslottype != EquipmentSlotType.HEAD) {
  2094.                      return false;
  2095.                   }
  2096.                } else if (MobEntity.getSlotForItemStack(itemStackIn) != equipmentslottype) {
  2097.                   return false;
  2098.                }
  2099.             }
  2100.  
  2101.             this.inventory.setInventorySlotContents(equipmentslottype.getIndex() + this.inventory.mainInventory.size(), itemStackIn);
  2102.             return true;
  2103.          }
  2104.       }
  2105.    }
  2106.  
  2107.    /**
  2108.     * Whether the "reducedDebugInfo" option is active for this player.
  2109.     */
  2110.    @OnlyIn(Dist.CLIENT)
  2111.    public boolean hasReducedDebug() {
  2112.       return this.hasReducedDebug;
  2113.    }
  2114.  
  2115.    @OnlyIn(Dist.CLIENT)
  2116.    public void setReducedDebug(boolean reducedDebug) {
  2117.       this.hasReducedDebug = reducedDebug;
  2118.    }
  2119.  
  2120.    public HandSide getPrimaryHand() {
  2121.       return this.dataManager.get(MAIN_HAND) == 0 ? HandSide.LEFT : HandSide.RIGHT;
  2122.    }
  2123.  
  2124.    public void setPrimaryHand(HandSide hand) {
  2125.       this.dataManager.set(MAIN_HAND, (byte)(hand == HandSide.LEFT ? 0 : 1));
  2126.    }
  2127.  
  2128.    public CompoundNBT getLeftShoulderEntity() {
  2129.       return this.dataManager.get(LEFT_SHOULDER_ENTITY);
  2130.    }
  2131.  
  2132.    protected void setLeftShoulderEntity(CompoundNBT tag) {
  2133.       this.dataManager.set(LEFT_SHOULDER_ENTITY, tag);
  2134.    }
  2135.  
  2136.    public CompoundNBT getRightShoulderEntity() {
  2137.       return this.dataManager.get(RIGHT_SHOULDER_ENTITY);
  2138.    }
  2139.  
  2140.    protected void setRightShoulderEntity(CompoundNBT tag) {
  2141.       this.dataManager.set(RIGHT_SHOULDER_ENTITY, tag);
  2142.    }
  2143.  
  2144.    public float getCooldownPeriod() {
  2145.       return (float)(1.0D / this.getAttribute(SharedMonsterAttributes.ATTACK_SPEED).getValue() * 20.0D);
  2146.    }
  2147.  
  2148.    /**
  2149.     * Returns the percentage of attack power available based on the cooldown (zero to one).
  2150.     */
  2151.    public float getCooledAttackStrength(float adjustTicks) {
  2152.       return MathHelper.clamp(((float)this.ticksSinceLastSwing + adjustTicks) / this.getCooldownPeriod(), 0.0F, 1.0F);
  2153.    }
  2154.  
  2155.    public void resetCooldown() {
  2156.       this.ticksSinceLastSwing = 0;
  2157.    }
  2158.  
  2159.    public CooldownTracker getCooldownTracker() {
  2160.       return this.cooldownTracker;
  2161.    }
  2162.  
  2163.    public float getLuck() {
  2164.       return (float)this.getAttribute(SharedMonsterAttributes.LUCK).getValue();
  2165.    }
  2166.  
  2167.    public boolean canUseCommandBlock() {
  2168.       return this.abilities.isCreativeMode && this.getPermissionLevel() >= 2;
  2169.    }
  2170.  
  2171.    public boolean func_213365_e(ItemStack p_213365_1_) {
  2172.       EquipmentSlotType equipmentslottype = MobEntity.getSlotForItemStack(p_213365_1_);
  2173.       return this.getItemStackFromSlot(equipmentslottype).isEmpty();
  2174.    }
  2175.  
  2176.    public EntitySize getSize(Pose poseIn) {
  2177.       return SIZE_BY_POSE.getOrDefault(poseIn, STANDING_SIZE);
  2178.    }
  2179.  
  2180.    public ItemStack findAmmo(ItemStack shootable) {
  2181.       if (!(shootable.getItem() instanceof ShootableItem)) {
  2182.          return ItemStack.EMPTY;
  2183.       } else {
  2184.          Predicate<ItemStack> predicate = ((ShootableItem)shootable.getItem()).getAmmoPredicate();
  2185.          ItemStack itemstack = ShootableItem.getHeldAmmo(this, predicate);
  2186.          if (!itemstack.isEmpty()) {
  2187.             return itemstack;
  2188.          } else {
  2189.             predicate = ((ShootableItem)shootable.getItem()).getInventoryAmmoPredicate();
  2190.  
  2191.             for(int i = 0; i < this.inventory.getSizeInventory(); ++i) {
  2192.                ItemStack itemstack1 = this.inventory.getStackInSlot(i);
  2193.                if (predicate.test(itemstack1)) {
  2194.                   return itemstack1;
  2195.                }
  2196.             }
  2197.  
  2198.             return this.abilities.isCreativeMode ? new ItemStack(Items.ARROW) : ItemStack.EMPTY;
  2199.          }
  2200.       }
  2201.    }
  2202.  
  2203.    public ItemStack onFoodEaten(World p_213357_1_, ItemStack p_213357_2_) {
  2204.       this.getFoodStats().consume(p_213357_2_.getItem(), p_213357_2_);
  2205.       this.addStat(Stats.ITEM_USED.get(p_213357_2_.getItem()));
  2206.       p_213357_1_.playSound((PlayerEntity)null, this.posX, this.posY, this.posZ, SoundEvents.ENTITY_PLAYER_BURP, SoundCategory.PLAYERS, 0.5F, p_213357_1_.rand.nextFloat() * 0.1F + 0.9F);
  2207.       if (this instanceof ServerPlayerEntity) {
  2208.          CriteriaTriggers.CONSUME_ITEM.trigger((ServerPlayerEntity)this, p_213357_2_);
  2209.       }
  2210.  
  2211.       return super.onFoodEaten(p_213357_1_, p_213357_2_);
  2212.    }
  2213.  
  2214.    public static enum SleepResult {
  2215.       NOT_POSSIBLE_HERE,
  2216.       NOT_POSSIBLE_NOW(new TranslationTextComponent("block.minecraft.bed.no_sleep")),
  2217.       TOO_FAR_AWAY(new TranslationTextComponent("block.minecraft.bed.too_far_away")),
  2218.       OBSTRUCTED(new TranslationTextComponent("block.minecraft.bed.obstructed")),
  2219.       OTHER_PROBLEM,
  2220.       NOT_SAFE(new TranslationTextComponent("block.minecraft.bed.not_safe"));
  2221.  
  2222.       @Nullable
  2223.       private final ITextComponent message;
  2224.  
  2225.       private SleepResult() {
  2226.          this.message = null;
  2227.       }
  2228.  
  2229.       private SleepResult(ITextComponent msg) {
  2230.          this.message = msg;
  2231.       }
  2232.  
  2233.       @Nullable
  2234.       public ITextComponent getMessage() {
  2235.          return this.message;
  2236.       }
  2237.    }
  2238.    // =========== FORGE START ==============//
  2239.    public net.minecraft.world.dimension.DimensionType getSpawnDimension() {
  2240.       return this.spawnDimension;
  2241.    }
  2242.  
  2243.    public void setSpawnDimenion(net.minecraft.world.dimension.DimensionType dim) {
  2244.        this.spawnDimension = dim;
  2245.    }
  2246.  
  2247.    public Collection<ITextComponent> getPrefixes() {
  2248.        return this.prefixes;
  2249.    }
  2250.  
  2251.    public Collection<ITextComponent> getSuffixes() {
  2252.        return this.suffixes;
  2253.    }
  2254.  
  2255.    private final net.minecraftforge.common.util.LazyOptional<net.minecraftforge.items.IItemHandler>
  2256.          playerMainHandler = net.minecraftforge.common.util.LazyOptional.of(
  2257.                () -> new net.minecraftforge.items.wrapper.PlayerMainInvWrapper(inventory));
  2258.  
  2259.    private final net.minecraftforge.common.util.LazyOptional<net.minecraftforge.items.IItemHandler>
  2260.          playerEquipmentHandler = net.minecraftforge.common.util.LazyOptional.of(
  2261.                () -> new net.minecraftforge.items.wrapper.CombinedInvWrapper(
  2262.                      new net.minecraftforge.items.wrapper.PlayerArmorInvWrapper(inventory),
  2263.                      new net.minecraftforge.items.wrapper.PlayerOffhandInvWrapper(inventory)));
  2264.  
  2265.    private final net.minecraftforge.common.util.LazyOptional<net.minecraftforge.items.IItemHandler>
  2266.          playerJoinedHandler = net.minecraftforge.common.util.LazyOptional.of(
  2267.                () -> new net.minecraftforge.items.wrapper.PlayerInvWrapper(inventory));
  2268.  
  2269.    @Override
  2270.    public <T> net.minecraftforge.common.util.LazyOptional<T> getCapability(net.minecraftforge.common.capabilities.Capability<T> capability, @Nullable Direction facing) {
  2271.       if (this.isAlive() && capability == net.minecraftforge.items.CapabilityItemHandler.ITEM_HANDLER_CAPABILITY) {
  2272.          if (facing == null) return playerJoinedHandler.cast();
  2273.          else if (facing.getAxis().isVertical()) return playerMainHandler.cast();
  2274.          else if (facing.getAxis().isHorizontal()) return playerEquipmentHandler.cast();
  2275.       }
  2276.       return super.getCapability(capability, facing);
  2277.    }
  2278. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement