【发布时间】:2015-07-30 04:10:35
【问题描述】:
为了将玩家伪装成另一个实体,我制作了一个伪装类,如下所示:
public class Disguise
{
private static HashSet<Disguise> disguises = new HashSet<>();
private net.minecraft.server.v1_8_R2.EntityLiving nmsEntity;
private Player disguise;
public Disguise(Player disguise, EntityLiving entity, boolean affectLogin)
{
if(affectLogin)
disguises.add(this);
this.disguise = disguise;
this.nmsEntity = entity;
}
public Disguise(Player disguise, EntityLiving entity)
{
this(disguise, entity, true);
}
public void send(Player visible)
{
if(visible == disguise)
return;
EntityPlayer player = NMSUtils.getNMSPlayer(visible);
nmsEntity.setPosition(player.locX, player.locY, player.locZ);
nmsEntity.d(disguise.getEntityId());
nmsEntity.setCustomName(disguise.getDisplayName());
nmsEntity.setCustomNameVisible(true);
PacketPlayOutSpawnEntityLiving spawn = new PacketPlayOutSpawnEntityLiving(nmsEntity);
PacketPlayOutEntityDestroy destroy = new PacketPlayOutEntityDestroy(disguise.getEntityId());
player.playerConnection.sendPacket(destroy);
player.playerConnection.sendPacket(spawn);
}
public void send(List<Player> visible)
{
for(Player player : visible)
send(player);
}
public void send(Player... visible)
{
send(Arrays.asList(visible));
}
public void send()
{
send(new ArrayList<>(Bukkit.getOnlinePlayers()));
}
public Player getDisguised()
{
return disguise;
}
public static HashSet<Disguise> getDisguises()
{
return disguises;
}
}
我还有一个静态 HashSet,它存储所有创建的实例。我这样做是因为我希望登录的玩家也能看到伪装,并且我想在玩家退出时从玩家身上移除伪装。是静态 HashSet 的方法吗(就像我正在做的那样)?如果没有,应该怎么做?
【问题讨论】:
-
首先,我会封装
return disguises;,否则其他类可以开始变异HashSet<T>,永远不要返回原始集合本身...... -
你在滥用静态,如果你试图做 OOP 而是通过永远不必创建新对象而使其成为引用编程,而只需要调用类而无需创建实例。
-
你认为 HashSet 是静态的有什么问题?我不确定我看到了。他有一个集中的存储库,不需要实例。难道是因为他把它藏在了伪装之中?我只会有它的访问器/突变器....永远不要直接公开一个集合。
-
@jgr208 我不确定我是否明白你在说什么,但据我了解,我应该删除构造函数和 HashSet 并使发送静态?
-
那么您的程序是否需要或者您是否希望它是 OOP,如果是,则不要使用静态,除非您不需要像实用程序类这样的类的实例。如果您不关心 OOP 并在需要为类使用函数时创建类的新实例,请继续并在任何地方使用静态。一切都取决于您想要做什么的设计。