Mojira Archive
MC-80893

Sender bias (c=1) applies when sender is not the closest entity to specified x/y/z origin

The bug

When you use a command in the chat like:

/say @e[x=0,y=0,z=0,c=1]

Your name will always be stated even if there was a different entity closer to those coordinates. In this case, sender bias (which assumes "the entity closest to itself is always itself") does not take into account if the origin has been changed.

How to reproduce

  1. /tp 20 60 0
  2. /summon armor_stand 0 60 0 {CustomName:"closestEntity",NoGravity:1b,NoAI:1b}
  3. /summon armor_stand 10 60 0 {CustomName:"commandExecuter",NoGravity:1b,NoAI:1b}
  4. /execute @e[type=armor_stand,name=commandExecuter] ~ ~ ~ /say @e[x=0,y=60,z=0,c=1,r=20]
    → It will print "commandExecuter" instead of "closestEntity"

To make sure that "closestEntity" is indeed the closest one, you can run the following command:

/say @e[type=armor_stand,x=0,y=60,z=0,c=1,r=20]

The reason

The following is based on a decompiled version of Minecraft 1.10 using MCP 9.30.

The reason for this is that the method net.minecraft.command.EntitySelector.getEntitiesFromPredicates(List<T>, Map<String, String>, ICommandSender, Class<? extends T>, String, Vec3d) explicitely uses the sender of the command if c=1.

private static <T extends Entity> List<T> getEntitiesFromPredicates(List<T> matchingEntities, Map<String, String> params, ICommandSender sender, Class <? extends T > targetClass, String type, final Vec3d pos)
{
    int i = parseIntWithDefault(params, "c", !type.equals("a") && !type.equals("e") ? 1 : 0);

    if (!type.equals("p") && !type.equals("a") && !type.equals("e"))
    {
        if (type.equals("r"))
        {
            Collections.shuffle((List<?>)matchingEntities);
        }
    }
    else
    {
        Collections.sort((List<T>)matchingEntities, new Comparator<Entity>()
        {
            public int compare(Entity p_compare_1_, Entity p_compare_2_)
            {
                System.out.println(ComparisonChain.start().compare(p_compare_1_.getDistanceSq(pos.xCoord, pos.yCoord, pos.zCoord), p_compare_2_.getDistanceSq(pos.xCoord, pos.yCoord, pos.zCoord)).result());
                return ComparisonChain.start().compare(p_compare_1_.getDistanceSq(pos.xCoord, pos.yCoord, pos.zCoord), p_compare_2_.getDistanceSq(pos.xCoord, pos.yCoord, pos.zCoord)).result();
            }
        });
    }

    // This prefers the sender of the command if c=1
    //Entity entity = sender.getCommandSenderEntity();
    //
    //if (entity != null && targetClass.isAssignableFrom(entity.getClass()) && i == 1 && ((List)matchingEntities).contains(entity) && !"r".equals(type))
    //{
    //    matchingEntities = Lists.newArrayList((T)entity);
    //}

    if (i != 0)
    {
        if (i < 0)
        {
            Collections.reverse((List<?>)matchingEntities);
        }

        matchingEntities = ((List)matchingEntities).subList(0, Math.min(Math.abs(i), ((List)matchingEntities).size()));
    }

    return (List)matchingEntities;
}

Note: This is not a duplicate of MC-80400, because there it only happens with scoreboard commands and affects command blocks. This bug described here is not caused by command blocks and also doesn't only prefer players but instead the entity which ran the command.

Fixed

Marcono1234

2015-05-31, 10:01 PM

2020-08-09, 08:13 PM

2017-11-09, 02:19 PM

5

6

Confirmed

argument, selector

Minecraft 1.8.6 - Minecraft 17w16bMinecraft 1.8.6, Minecraft 1.10.2, Minecraft 16w33a, Minecraft 16w40a, Minecraft 1.11, Minecraft 1.11.2, Minecraft 17w16b

Minecraft 17w45a