mojira.dev

clove

Assigned

No issues.

Reported

No issues.

Comments

 

The reason this happens for the majority of entities is that the calls to drop the items are just for the item name, and don't store NBT data.

This could be fixed by instead of just spawning in a blank item this.dropItem(Items.PAINTING);, the game also added the CustomName as NBT.

An example of this occurring can be found below:

The following is just for the Boat item and was decompiled using the Yarn mappings and CFR.

In net.minecraft.entity.vehicle.BoatEntity, the condition for the boat to break is declared.

public boolean damage(DamageSource source, float amount) {
    if (this.isInvulnerableTo(source)) {
        return false;
    } else if (!this.world.isClient && !this.removed) {
        this.setDamageWobbleSide(-this.getDamageWobbleSide());
        this.setDamageWobbleTicks(10);
        this.setDamageWobbleStrength(this.getDamageWobbleStrength() + amount * 10.0F);
        this.scheduleVelocityUpdate();
        boolean bl = source.getAttacker() instanceof PlayerEntity && ((PlayerEntity)source.getAttacker()).abilities.creativeMode;
        if (bl || this.getDamageWobbleStrength() > 40.0F) {
            if (!bl && this.world.getGameRules().getBoolean(GameRules.DO_ENTITY_DROPS)) {


                // This is the line that drops the boat item.
                this.dropItem(this.asItem());
            }

            this.remove();
        }

        return true;
    } else {
        return true;
    }
}

As you can see, the Boat item is dropped using a call to this.dropItem. However, this.asItem does not store the CustomName or any NBT at all, it's just a switch to determine the type of item.

 

The method is seen below.

 

public Item asItem() {
    switch(this.getBoatType()) {
    case OAK:
    default:
        return Items.OAK_BOAT;
    case SPRUCE:
        return Items.SPRUCE_BOAT;
    case BIRCH:
        return Items.BIRCH_BOAT;
    case JUNGLE:
        return Items.JUNGLE_BOAT;
    case ACACIA:
        return Items.ACACIA_BOAT;
    case DARK_OAK:
        return Items.DARK_OAK_BOAT;
    }
}

 

This could be fixed by changing the item to add in the CustomName NBT into its display.Name nbt.

 

Code analysis, if I missed something please tell me 🙂

The following is based on Minecraft 1.16.2 decompiled using the Yarn mappings and CFR.

In net.minecraft.client.render.WorldRenderer, the worldborder is rendered using the method renderWorldBorder.

The sides are rendering using 4 calls to a method.

this.method_22978(lv, f, g, h, lv2.getBoundEast(), 256, t, m + s, m + 0.0f);
this.method_22978(lv, f, g, h, lv2.getBoundEast(), 256, t + u, m + v + s, m + 0.0f);
this.method_22978(lv, f, g, h, lv2.getBoundEast(), 0, t + u, m + v + s, m + 128.0f);
this.method_22978(lv, f, g, h, lv2.getBoundEast(), 0, t, m + s, m + 128.0f);i

As you can see, it's hardcoded to use 256 and 0 for height. This could be fixed by changing those numbers to something like camera.getBlockPos().getY() - [distance] and + [distance].

(There may be a limitation in BufferBuilder preventing it from rendering under 0 and above 256)

This report is invalid because your game and server are modified.

Tried to do a code analysis, if I messed up please tell me 🙂

 

The following was decompiled using https://github.com/hube12/DecompilerMC and CFR.

If we look at net.minecraft.server.commands.LootCommand, the method for /loot kill is declared on line 252.

private static int dropKillLoot(CommandContext<CommandSourceStack> commandContext, Entity entity, DropConsumer dropConsumer) throws CommandSyntaxException {
  if (!(entity instanceof LivingEntity)) {
    throw ERROR_NO_LOOT_TABLE.create((Object)entity.getDisplayName());

     }
  ResourceLocation resourceLocation = ((LivingEntity)entity).getLootTable();
  CommandSourceStack commandSourceStack = (CommandSourceStack)commandContext.getSource();
  LootContext.Builder builder = new LootContext.Builder(commandSourceStack.getLevel());
  Entity entity2 = commandSourceStack.getEntity();
  if (entity2 instanceof Player) {
    builder.withParameter(LootContextParams.LAST_DAMAGE_PLAYER, (Player)entity2);
    }
  *builder.withParameter(LootContextParams.DAMAGE_SOURCE, DamageSource.MAGIC);*
  builder.withOptionalParameter(LootContextParams.DIRECT_KILLER_ENTITY, entity2);
  builder.withOptionalParameter(LootContextParams.KILLER_ENTITY, entity2);
  builder.withParameter(LootContextParams.THIS_ENTITY, entity);
  builder.withParameter(LootContextParams.ORIGIN, commandSourceStack.getPosition());
  LootTable lootTable = commandSourceStack.getServer().getLootTables().get(resourceLocation);
  List<ItemStack> list2 = lootTable.getRandomItems(builder.create(LootContextParamSets.ENTITY));
  return dropConsumer.accept(commandContext, list2, list -> LootCommand.callback(commandSourceStack, list, resourceLocation));
    }

When it adds parameters to the LootContext.Builder (the bolded part), it does not set the random seed (this is done by calling LootContext.Builder.withOptionalRandomSeed). Therefore, the seed is variable.

However, in net.minecraft.world.entity.Mob (this may not be the correct class, but even if this is in a different file the problem and solution are still accurate) on line 463, there's this method:

@Override
protected LootContext.Builder createLootContext(boolean bl, DamageSource damageSource) {
    return super.createLootContext(bl, damageSource).withOptionalRandomSeed(this.lootTableSeed, this.random);
    }

As you can see, it creates a LootContext.Builder with an optional random seed of this.lootTableSeed (which is the NBT tag).

The solution would be to add an additional builder.withOptionalRandomSeed(this.lootTableSeed) in dropKillLoot()

Can confirm for 1.16.3rc1

Can confirm for 1.16.3rc1+

Can confirm for 1.16.3rc1

Can confirm for 1.16.3rc1

Can confirm for 1.16.3rc1

Can confirm for 1.16.3rc1

Can confirm for 1.16.3rc1

Can confirm for 1.16.3rc1

Can confirm in 1.16.3rc1

Can confirm for 1.16.3rc1

Multiplayer inventories are stored in the server files in the playerdata folder if I remember correctly. However, in singleplayer, the items are stored as part of the world and are shared between users (you'll see this effect if you ever opened up a world you got from someone else and started with items). I'm not sure about LAN worlds, however.

Can confirm for 1.16.2

Can confirm for 1.16.2

Can confirm for 1.16.2

Can confirm for 1.16.2

Can confirm for 1.16.2