Partial scaling support

This commit is contained in:
libraryaddict 2024-07-02 00:29:15 +12:00
parent cd44863106
commit 98105683e5
12 changed files with 212 additions and 36 deletions

View File

@ -229,7 +229,7 @@ public class DisguiseConfig {
private static BukkitTask updaterTask; private static BukkitTask updaterTask;
@Getter @Getter
@Setter @Setter
private static boolean tallSelfDisguises; private static boolean tallSelfDisguises, tallSelfDisguisesScaling;
@Getter @Getter
@Setter @Setter
private static PlayerNameType playerNameType = PlayerNameType.TEAMS; private static PlayerNameType playerNameType = PlayerNameType.TEAMS;
@ -291,6 +291,12 @@ public class DisguiseConfig {
@Getter @Getter
@Setter @Setter
private static boolean removeDisguiseBlockPlace, removeDisguiseBlockBreak; private static boolean removeDisguiseBlockPlace, removeDisguiseBlockBreak;
@Getter
@Setter
private static boolean scaleSelfDisguises;
@Getter
@Setter
private static double scaleSelfDisguisesMax;
public static boolean isArmorstandsName() { public static boolean isArmorstandsName() {
return getPlayerNameType() == PlayerNameType.ARMORSTANDS; return getPlayerNameType() == PlayerNameType.ARMORSTANDS;
@ -585,9 +591,12 @@ public class DisguiseConfig {
setHideDisguisedPlayers(config.getBoolean("HideDisguisedPlayersFromTab")); setHideDisguisedPlayers(config.getBoolean("HideDisguisedPlayersFromTab"));
setPlayerHideArmor(config.getBoolean("PlayerHideArmor")); setPlayerHideArmor(config.getBoolean("PlayerHideArmor"));
setTallSelfDisguises(config.getBoolean("TallSelfDisguises")); setTallSelfDisguises(config.getBoolean("TallSelfDisguises"));
setTallSelfDisguisesScaling(config.getBoolean("TallSelfDisguisesScaling"));
setRandomDisguises(config.getBoolean("RandomDisguiseOptions")); setRandomDisguises(config.getBoolean("RandomDisguiseOptions"));
setViewDisguises(config.getBoolean("ViewSelfDisguises")); setViewDisguises(config.getBoolean("ViewSelfDisguises"));
setViewSelfDisguisesDefault(config.getBoolean("ViewSelfDisguisesDefault")); setViewSelfDisguisesDefault(config.getBoolean("ViewSelfDisguisesDefault"));
setScaleSelfDisguises(config.getBoolean("SelfDisguisesScaling"));
setScaleSelfDisguisesMax(config.getDouble("SelfDisguisesScaleMax"));
setSelfDisguisesSoundsReplaced(config.getBoolean("HearSelfDisguise")); setSelfDisguisesSoundsReplaced(config.getBoolean("HearSelfDisguise"));
setShowDisguisedPlayersInTab(config.getBoolean("ShowPlayerDisguisesInTab")); setShowDisguisedPlayersInTab(config.getBoolean("ShowPlayerDisguisesInTab"));
setVelocitySent(config.getBoolean("SendVelocity")); setVelocitySent(config.getBoolean("SendVelocity"));

View File

@ -1,8 +1,11 @@
package me.libraryaddict.disguise.commands.utils; package me.libraryaddict.disguise.commands.utils;
import me.libraryaddict.disguise.DisguiseAPI; import me.libraryaddict.disguise.DisguiseAPI;
import me.libraryaddict.disguise.DisguiseConfig;
import me.libraryaddict.disguise.disguisetypes.DisguiseType;
import me.libraryaddict.disguise.disguisetypes.TargetedDisguise; import me.libraryaddict.disguise.disguisetypes.TargetedDisguise;
import me.libraryaddict.disguise.utilities.DisguiseUtilities; import me.libraryaddict.disguise.utilities.DisguiseUtilities;
import me.libraryaddict.disguise.utilities.reflection.NmsVersion;
import me.libraryaddict.disguise.utilities.translations.LibsMsg; import me.libraryaddict.disguise.utilities.translations.LibsMsg;
import org.bukkit.command.Command; import org.bukkit.command.Command;
import org.bukkit.command.CommandExecutor; import org.bukkit.command.CommandExecutor;
@ -40,7 +43,9 @@ public class DisguiseViewSelfCommand implements CommandExecutor {
// If they're disguised, tall disguises are hidden, it's a tall disguise // If they're disguised, tall disguises are hidden, it's a tall disguise
// Then tell the player, it's not a bug! The disguise is too tall // Then tell the player, it's not a bug! The disguise is too tall
if (disguise != null && !disguise.isTallDisguisesVisible() && disguise.canSee(player) && if (disguise != null && !disguise.isTallDisguisesVisible() &&
(!NmsVersion.v1_21_R1.isSupported() || !DisguiseConfig.isTallSelfDisguisesScaling() ||
(disguise.isMiscDisguise() || disguise.getType() == DisguiseType.ENDER_DRAGON)) && disguise.canSee(player) &&
DisguiseUtilities.isTallDisguise(disguise)) { DisguiseUtilities.isTallDisguise(disguise)) {
LibsMsg.VIEW_SELF_TALL_NOTE.send(player); LibsMsg.VIEW_SELF_TALL_NOTE.send(player);
} }

View File

@ -1,8 +1,10 @@
package me.libraryaddict.disguise.disguisetypes; package me.libraryaddict.disguise.disguisetypes;
import com.github.retrooper.packetevents.PacketEvents; import com.github.retrooper.packetevents.PacketEvents;
import com.github.retrooper.packetevents.protocol.attribute.Attributes;
import com.github.retrooper.packetevents.wrapper.PacketWrapper; import com.github.retrooper.packetevents.wrapper.PacketWrapper;
import com.github.retrooper.packetevents.wrapper.play.server.WrapperPlayServerPlayerInfo; import com.github.retrooper.packetevents.wrapper.play.server.WrapperPlayServerPlayerInfo;
import com.github.retrooper.packetevents.wrapper.play.server.WrapperPlayServerUpdateAttributes;
import lombok.AccessLevel; import lombok.AccessLevel;
import lombok.Getter; import lombok.Getter;
import lombok.Setter; import lombok.Setter;
@ -29,6 +31,8 @@ import net.md_5.bungee.api.chat.BaseComponent;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
import org.bukkit.NamespacedKey; import org.bukkit.NamespacedKey;
import org.bukkit.attribute.Attribute; import org.bukkit.attribute.Attribute;
import org.bukkit.attribute.AttributeInstance;
import org.bukkit.attribute.AttributeModifier;
import org.bukkit.boss.BarColor; import org.bukkit.boss.BarColor;
import org.bukkit.boss.BarStyle; import org.bukkit.boss.BarStyle;
import org.bukkit.boss.BossBar; import org.bukkit.boss.BossBar;
@ -40,11 +44,13 @@ import org.bukkit.entity.FallingBlock;
import org.bukkit.entity.Item; import org.bukkit.entity.Item;
import org.bukkit.entity.LivingEntity; import org.bukkit.entity.LivingEntity;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
import org.bukkit.inventory.EquipmentSlotGroup;
import org.bukkit.metadata.FixedMetadataValue; import org.bukkit.metadata.FixedMetadataValue;
import org.bukkit.scheduler.BukkitRunnable; import org.bukkit.scheduler.BukkitRunnable;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Arrays; import java.util.Arrays;
import java.util.Collections;
import java.util.HashMap; import java.util.HashMap;
import java.util.HashSet; import java.util.HashSet;
import java.util.LinkedHashMap; import java.util.LinkedHashMap;
@ -76,6 +82,13 @@ public abstract class Disguise {
private BarStyle bossBarStyle = DisguiseConfig.getBossBarStyle(); private BarStyle bossBarStyle = DisguiseConfig.getBossBarStyle();
@Getter(value = AccessLevel.PRIVATE) @Getter(value = AccessLevel.PRIVATE)
private final NamespacedKey bossBar = new NamespacedKey("libsdisguises", UUID.randomUUID().toString()); private final NamespacedKey bossBar = new NamespacedKey("libsdisguises", UUID.randomUUID().toString());
/**
* -- GETTER --
* Get the flag watcher
*
* @return flagWatcher
*/
@Getter
private FlagWatcher watcher; private FlagWatcher watcher;
/** /**
* If set, how long before disguise expires * If set, how long before disguise expires
@ -105,6 +118,13 @@ public abstract class Disguise {
@Setter @Setter
private String soundGroup; private String soundGroup;
private UUID uuid = ReflectionManager.getRandomUUID(); private UUID uuid = ReflectionManager.getRandomUUID();
/**
* The biggest we'll allow the self disguise to be scaled up to, including disguise applied scale
*/
@Getter
private double selfDisguiseTallScaleMax = 1;
@Getter
private boolean scalePlayerToDisguise = DisguiseConfig.isScaleSelfDisguises();
public Disguise(DisguiseType disguiseType) { public Disguise(DisguiseType disguiseType) {
this.disguiseType = disguiseType; this.disguiseType = disguiseType;
@ -180,7 +200,7 @@ public abstract class Disguise {
public abstract double getHeight(); public abstract double getHeight();
public double getNameHeightScale() { public double getNameHeightScale() {
if (!NmsVersion.v1_21_R1.isSupported()) { if (!NmsVersion.v1_21_R1.isSupported() || isMiscDisguise()) {
return 1; return 1;
} }
@ -189,10 +209,8 @@ public abstract class Disguise {
if (watcherScale != null) { if (watcherScale != null) {
finalScale = watcherScale; finalScale = watcherScale;
} else if (getEntity() instanceof LivingEntity) {
finalScale = ((LivingEntity) getEntity()).getAttribute(Attribute.GENERIC_SCALE).getValue();
} else { } else {
finalScale = 1; finalScale = DisguiseUtilities.getActualEntityScale(getEntity());
} }
// Clamp // Clamp
@ -210,6 +228,8 @@ public abstract class Disguise {
return; return;
} }
adjustTallSelfDisguiseScale();
for (Player player : DisguiseUtilities.getPerverts(this)) { for (Player player : DisguiseUtilities.getPerverts(this)) {
if (!DisguiseUtilities.isFancyHiddenTabs() && isPlayerDisguise() && if (!DisguiseUtilities.isFancyHiddenTabs() && isPlayerDisguise() &&
LibsDisguises.getInstance().getSkinHandler().isSleeping(player, (PlayerDisguise) this)) { LibsDisguises.getInstance().getSkinHandler().isSleeping(player, (PlayerDisguise) this)) {
@ -497,7 +517,11 @@ public abstract class Disguise {
} }
if (getEntity() instanceof Player && isSelfDisguiseVisible() && !isTallDisguisesVisible() && isTallDisguise()) { if (getEntity() instanceof Player && isSelfDisguiseVisible() && !isTallDisguisesVisible() && isTallDisguise()) {
setSelfDisguiseVisible(false); if (DisguiseConfig.isTallSelfDisguisesScaling() && NmsVersion.v1_21_R1.isSupported() && canScaleDisguise()) {
adjustTallSelfDisguiseScale();
} else {
setSelfDisguiseVisible(false);
}
} }
return this; return this;
@ -507,6 +531,95 @@ public abstract class Disguise {
return DisguiseUtilities.isTallDisguise(this); return DisguiseUtilities.isTallDisguise(this);
} }
protected boolean canScaleDisguise() {
return !isMiscDisguise() && getType() != DisguiseType.ENDER_DRAGON;
}
public void setScalePlayerToDisguise(boolean scalePlayerToDisguise) {
if (!LibsPremium.isPremium() && !DisguiseConfig.isScaleSelfDisguises() && scalePlayerToDisguise) {
scalePlayerToDisguise = false;
DisguiseUtilities.getLogger()
.info("You cannot use setScalePlayerToDisguise if it's disabled in the config without the Premium Plugin");
}
this.scalePlayerToDisguise = scalePlayerToDisguise;
adjustTallSelfDisguiseScale();
}
protected void adjustTallSelfDisguiseScale() {
if (!NmsVersion.v1_21_R1.isSupported() || !canScaleDisguise()) {
return;
}
// Get the scale, default to "not scaled" if not a player
double playerHeightScale = DisguiseUtilities.getActualEntityScale(getEntity());
double disguiseHeight = getHeight() * getNameHeightScale();
// Here we have the scale of the player itself, where they'd be scaled up or down to match the disguise's scale
// So a disguise that's 0.5 blocks high, will have the player be given something like 0.33 scale
double playerScale = disguiseHeight / (1.8 * playerHeightScale);
playerScale = Math.min(playerScale, DisguiseConfig.getScaleSelfDisguisesMax());
// The max size the self disguise is allowed to be, as it'd hide the player's view
double prevScale = this.selfDisguiseTallScaleMax;
// Adjust so it's not blocking eyes. So smaller than normal
// And ofc, it's 1 if the disguise was not too tall to begin with
this.selfDisguiseTallScaleMax = DisguiseUtilities.isTallDisguise(this) ? (1.5 * playerScale) / disguiseHeight : 1;
if (!isDisguiseInUse() || !(getEntity() instanceof Player) || !canScaleDisguise() ||
!((TargetedDisguise) this).canSee((Player) getEntity())) {
return;
}
if (prevScale != selfDisguiseTallScaleMax && isSelfDisguiseVisible()) {
double scaleToSend;
if (((LivingWatcher) getWatcher()).getScale() != null) {
scaleToSend = ((LivingWatcher) getWatcher()).getScale();
} else {
scaleToSend = DisguiseUtilities.getActualEntityScale(getEntity());
}
scaleToSend = Math.min(scaleToSend, getSelfDisguiseTallScaleMax());
// The scale of the self disguise, not the player
WrapperPlayServerUpdateAttributes.Property property =
new WrapperPlayServerUpdateAttributes.Property(Attributes.GENERIC_SCALE, scaleToSend, new ArrayList<>());
WrapperPlayServerUpdateAttributes packet =
new WrapperPlayServerUpdateAttributes(DisguiseAPI.getSelfDisguiseId(), Collections.singletonList(property));
PacketEvents.getAPI().getPlayerManager().sendPacket(getEntity(), packet);
}
// Now we figure out the scale we need to have the player at the same eye level of the disguise
AttributeInstance attribute = ((Player) getEntity()).getAttribute(Attribute.GENERIC_SCALE);
AttributeModifier modifier =
attribute.getModifiers().stream().filter(a -> a.getKey().equals(DisguiseUtilities.getSelfDisguiseScaleNamespace())).findAny()
.orElse(null);
// Disabled or not allowed or doesn't need to scale up
if (!isScalePlayerToDisguise() || (!LibsPremium.isPremium() && !DisguiseConfig.isScaleSelfDisguises()) || playerScale == 1 ||
isPlayerDisguise()) {
if (modifier != null) {
attribute.removeModifier(modifier);
}
} else if (isScalePlayerToDisguise() && DisguiseConfig.isScaleSelfDisguises()) {
if (modifier != null) {
// Nothing changed, don't change anything
if (modifier.getAmount() == playerScale && modifier.getOperation() == AttributeModifier.Operation.MULTIPLY_SCALAR_1) {
return;
}
attribute.removeModifier(modifier);
}
// Subtract 1, as 1 is added internally
attribute.addModifier(new AttributeModifier(DisguiseUtilities.getSelfDisguiseScaleNamespace(), playerScale - 1,
AttributeModifier.Operation.MULTIPLY_SCALAR_1, EquipmentSlotGroup.ANY));
}
}
/** /**
* Get the disguise type * Get the disguise type
* *
@ -516,15 +629,6 @@ public abstract class Disguise {
return disguiseType; return disguiseType;
} }
/**
* Get the flag watcher
*
* @return flagWatcher
*/
public FlagWatcher getWatcher() {
return watcher;
}
/** /**
* Deprecated as this isn't used as it should be * Deprecated as this isn't used as it should be
*/ */
@ -746,6 +850,10 @@ public abstract class Disguise {
return true; return true;
} }
if (NmsVersion.v1_21_R1.isSupported()) {
DisguiseUtilities.removeSelfDisguiseScale(getEntity());
}
if (this instanceof PlayerDisguise) { if (this instanceof PlayerDisguise) {
PlayerDisguise disguise = (PlayerDisguise) this; PlayerDisguise disguise = (PlayerDisguise) this;
@ -893,7 +1001,11 @@ public abstract class Disguise {
@Deprecated @Deprecated
public Disguise setViewSelfDisguise(boolean viewSelfDisguise) { public Disguise setViewSelfDisguise(boolean viewSelfDisguise) {
if (viewSelfDisguise && !isTallDisguisesVisible() && isTallDisguise()) { if (viewSelfDisguise && !isTallDisguisesVisible() && isTallDisguise()) {
viewSelfDisguise = false; if (DisguiseConfig.isTallSelfDisguisesScaling() && NmsVersion.v1_21_R1.isSupported() && canScaleDisguise()) {
adjustTallSelfDisguiseScale();
} else {
viewSelfDisguise = false;
}
} }
if (isSelfDisguiseVisible() == viewSelfDisguise || !DisguiseConfig.isViewDisguises()) { if (isSelfDisguiseVisible() == viewSelfDisguise || !DisguiseConfig.isViewDisguises()) {
@ -1051,6 +1163,7 @@ public abstract class Disguise {
makeBossBar(); makeBossBar();
DisguiseUtilities.saveDisguises(getEntity()); DisguiseUtilities.saveDisguises(getEntity());
adjustTallSelfDisguiseScale();
return true; return true;
} }

View File

@ -504,6 +504,8 @@ public class FlagWatcher {
return; return;
} }
getDisguise().adjustTallSelfDisguiseScale();
for (Player player : DisguiseUtilities.getPerverts(getDisguise())) { for (Player player : DisguiseUtilities.getPerverts(getDisguise())) {
if (!DisguiseUtilities.isFancyHiddenTabs() && getDisguise().isPlayerDisguise() && if (!DisguiseUtilities.isFancyHiddenTabs() && getDisguise().isPlayerDisguise() &&
LibsDisguises.getInstance().getSkinHandler().isSleeping(player, (PlayerDisguise) getDisguise())) { LibsDisguises.getInstance().getSkinHandler().isSleeping(player, (PlayerDisguise) getDisguise())) {

View File

@ -6,6 +6,7 @@ import com.github.retrooper.packetevents.util.Vector3i;
import com.github.retrooper.packetevents.wrapper.play.server.WrapperPlayServerUpdateAttributes; import com.github.retrooper.packetevents.wrapper.play.server.WrapperPlayServerUpdateAttributes;
import lombok.Getter; import lombok.Getter;
import me.libraryaddict.disguise.DisguiseAPI; import me.libraryaddict.disguise.DisguiseAPI;
import me.libraryaddict.disguise.DisguiseConfig;
import me.libraryaddict.disguise.disguisetypes.Disguise; import me.libraryaddict.disguise.disguisetypes.Disguise;
import me.libraryaddict.disguise.disguisetypes.DisguiseType; import me.libraryaddict.disguise.disguisetypes.DisguiseType;
import me.libraryaddict.disguise.disguisetypes.FlagWatcher; import me.libraryaddict.disguise.disguisetypes.FlagWatcher;
@ -16,9 +17,7 @@ import me.libraryaddict.disguise.utilities.reflection.annotations.MethodGroupTyp
import me.libraryaddict.disguise.utilities.reflection.annotations.MethodOnlyUsedBy; import me.libraryaddict.disguise.utilities.reflection.annotations.MethodOnlyUsedBy;
import me.libraryaddict.disguise.utilities.reflection.annotations.NmsAddedIn; import me.libraryaddict.disguise.utilities.reflection.annotations.NmsAddedIn;
import org.bukkit.Color; import org.bukkit.Color;
import org.bukkit.attribute.Attribute;
import org.bukkit.entity.Entity; import org.bukkit.entity.Entity;
import org.bukkit.entity.LivingEntity;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
import org.bukkit.potion.PotionEffectType; import org.bukkit.potion.PotionEffectType;
@ -82,21 +81,23 @@ public class LivingWatcher extends FlagWatcher {
return; return;
} }
updateNameHeight();
double scaleToSend; double scaleToSend;
if (getScale() != null) { if (getScale() != null) {
scaleToSend = getScale(); scaleToSend = getScale();
} else if (getDisguise().getEntity() instanceof LivingEntity) {
scaleToSend = (float) ((LivingEntity) getDisguise().getEntity()).getAttribute(Attribute.GENERIC_SCALE).getValue();
} else { } else {
scaleToSend = 1; scaleToSend = DisguiseUtilities.getActualEntityScale(getDisguise().getEntity());
} }
Entity entity = getDisguise().getEntity(); Entity entity = getDisguise().getEntity();
for (Player player : DisguiseUtilities.getPerverts(getDisguise())) { for (Player player : DisguiseUtilities.getPerverts(getDisguise())) {
double toSend = player == entity && DisguiseConfig.isTallSelfDisguisesScaling() ?
Math.min(getDisguise().getSelfDisguiseTallScaleMax(), scaleToSend) : scaleToSend;
WrapperPlayServerUpdateAttributes.Property property = WrapperPlayServerUpdateAttributes.Property property =
new WrapperPlayServerUpdateAttributes.Property(Attributes.GENERIC_SCALE, scaleToSend, new ArrayList<>()); new WrapperPlayServerUpdateAttributes.Property(Attributes.GENERIC_SCALE, toSend, new ArrayList<>());
WrapperPlayServerUpdateAttributes packet = new WrapperPlayServerUpdateAttributes( WrapperPlayServerUpdateAttributes packet = new WrapperPlayServerUpdateAttributes(
player == getDisguise().getEntity() ? DisguiseAPI.getSelfDisguiseId() : getDisguise().getEntity().getEntityId(), player == getDisguise().getEntity() ? DisguiseAPI.getSelfDisguiseId() : getDisguise().getEntity().getEntityId(),
@ -108,8 +109,6 @@ public class LivingWatcher extends FlagWatcher {
PacketEvents.getAPI().getPlayerManager().sendPacket(player, packet); PacketEvents.getAPI().getPlayerManager().sendPacket(player, packet);
} }
} }
updateNameHeight();
} }
@NmsAddedIn(NmsVersion.v1_14) @NmsAddedIn(NmsVersion.v1_14)

View File

@ -392,6 +392,7 @@ public class DisguiseListener implements Listener {
Player p = event.getPlayer(); Player p = event.getPlayer();
p.removeMetadata("ld_loggedin", LibsDisguises.getInstance()); p.removeMetadata("ld_loggedin", LibsDisguises.getInstance());
DisguiseUtilities.removeSelfDisguiseScale(p);
plugin.getUpdateChecker().notifyUpdate(p); plugin.getUpdateChecker().notifyUpdate(p);
String requiredPacketEvents = PacketEventsUpdater.getMinimumPacketEventsVersion(); String requiredPacketEvents = PacketEventsUpdater.getMinimumPacketEventsVersion();

View File

@ -56,10 +56,16 @@ public class PacketHandlerAttributes implements IPacketHandler<WrapperPlayServer
// Override whatever they're sending if we're using a non-default scale // Override whatever they're sending if we're using a non-default scale
Double scale = ((LivingWatcher) disguise.getWatcher()).getScale(); Double scale = ((LivingWatcher) disguise.getWatcher()).getScale();
if (scale == null) { // If it's for the self disguise and the disguise had to be scaled down
attributes.add(property); if (entity == observer && DisguiseConfig.isTallSelfDisguisesScaling()) {
attributes.add(new WrapperPlayServerUpdateAttributes.Property(Attributes.GENERIC_SCALE,
Math.min(disguise.getSelfDisguiseTallScaleMax(), scale == null ? property.getValue() : scale), new ArrayList<>()));
} else { } else {
attributes.add(new WrapperPlayServerUpdateAttributes.Property(Attributes.GENERIC_SCALE, scale, new ArrayList<>())); if (scale == null) {
attributes.add(property);
} else {
attributes.add(new WrapperPlayServerUpdateAttributes.Property(Attributes.GENERIC_SCALE, scale, new ArrayList<>()));
}
} }
} else if (property.getAttribute() == Attributes.GENERIC_GRAVITY) { } else if (property.getAttribute() == Attributes.GENERIC_GRAVITY) {
attributes.add(property); attributes.add(property);

View File

@ -237,14 +237,14 @@ public enum LibsMsg {
SKIN_API_FAIL_TOO_FAST("<red>Too many requests accessing mineskin.org, please slow down!"), SKIN_API_FAIL_TOO_FAST("<red>Too many requests accessing mineskin.org, please slow down!"),
SKIN_API_BAD_URL("<red>Invalid url provided! Please ensure it is a .png file download!"), SKIN_API_BAD_URL("<red>Invalid url provided! Please ensure it is a .png file download!"),
SKIN_API_FAILED_URL("<red>Invalid url provided! mineskin.org failed to grab it!"), SKIN_API_FAILED_URL("<red>Invalid url provided! mineskin.org failed to grab it!"),
SKIN_API_FAIL_CODE("<red>Error with MineSkin code %s! %s"), SKIN_API_FAIL_CODE("<red>Error! Mineskin gave code %s, %s"),
SKIN_API_403("mineskin.org denied access to that url"), SKIN_API_403("mineskin.org denied access to that url"),
SKIN_API_404("mineskin.org unable to find an image at that url"), SKIN_API_404("mineskin.org unable to find an image at that url"),
SKIN_API_IMAGE_TIMEOUT("<red>Error! mineskin.org took too long to connect! Is your image valid?"), SKIN_API_IMAGE_TIMEOUT("<red>Error! mineskin.org took too long to connect! Is your image valid?"),
SKIN_API_TIMEOUT_ERROR("<red>Error! Took too long to connect to mineskin.org!"), SKIN_API_TIMEOUT_ERROR("<red>Error! Took too long to connect to mineskin.org!"),
SKIN_API_TIMEOUT_API_KEY_ERROR("<red>Error! Took too long to connect to mineskin.org! Is the API Key correct?"), SKIN_API_TIMEOUT_API_KEY_ERROR("<red>Error! Took too long to connect to mineskin.org! Is the API Key correct?"),
SKIN_API_TIMEOUT("<red>Took too long to connect to mineskin.org!"), SKIN_API_TIMEOUT("<red>Took too long to connect to mineskin.org!"),
SKIN_API_IMAGE_HAS_ERROR("Your image has the error: %s"), SKIN_API_IMAGE_HAS_ERROR("Mineskin tells us this error and that's all we know: %s"),
SKIN_API_USING_URL("<gray>Url provided, now attempting to connect to mineskin.org"), SKIN_API_USING_URL("<gray>Url provided, now attempting to connect to mineskin.org"),
SKIN_API_BAD_FILE_NAME("<red>Invalid file name provided! File not found!"), SKIN_API_BAD_FILE_NAME("<red>Invalid file name provided! File not found!"),
SKIN_API_BAD_FILE("<red>Invalid file provided! Please ensure it is a valid .png skin!"), SKIN_API_BAD_FILE("<red>Invalid file provided! Please ensure it is a valid .png skin!"),

View File

@ -10,9 +10,11 @@ import me.libraryaddict.disguise.disguisetypes.FlagWatcher;
import me.libraryaddict.disguise.disguisetypes.PlayerDisguise; import me.libraryaddict.disguise.disguisetypes.PlayerDisguise;
import me.libraryaddict.disguise.disguisetypes.watchers.PlayerWatcher; import me.libraryaddict.disguise.disguisetypes.watchers.PlayerWatcher;
import me.libraryaddict.disguise.utilities.DisguiseUtilities; import me.libraryaddict.disguise.utilities.DisguiseUtilities;
import me.libraryaddict.disguise.utilities.LibsPremium;
import me.libraryaddict.disguise.utilities.params.ParamInfo; import me.libraryaddict.disguise.utilities.params.ParamInfo;
import me.libraryaddict.disguise.utilities.params.ParamInfoManager; import me.libraryaddict.disguise.utilities.params.ParamInfoManager;
import me.libraryaddict.disguise.utilities.parser.WatcherMethod; import me.libraryaddict.disguise.utilities.parser.WatcherMethod;
import me.libraryaddict.disguise.utilities.reflection.NmsVersion;
import me.libraryaddict.disguise.utilities.reflection.ReflectionManager; import me.libraryaddict.disguise.utilities.reflection.ReflectionManager;
import me.libraryaddict.disguise.utilities.reflection.WatcherInfo; import me.libraryaddict.disguise.utilities.reflection.WatcherInfo;
import org.bukkit.boss.BarColor; import org.bukkit.boss.BarColor;
@ -24,6 +26,7 @@ import java.lang.invoke.MethodHandles;
import java.lang.invoke.MethodType; import java.lang.invoke.MethodType;
import java.nio.charset.StandardCharsets; import java.nio.charset.StandardCharsets;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap; import java.util.HashMap;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
@ -177,10 +180,17 @@ public class DisguiseMethods {
PlayerDisguise disguise = new PlayerDisguise(""); PlayerDisguise disguise = new PlayerDisguise("");
List<String> extraMethods = new ArrayList<>(
Arrays.asList("setSelfDisguiseVisible", "setHideHeldItemFromSelf", "setHideArmorFromSelf", "setHearSelfDisguise",
"setHidePlayer", "setExpires", "setNotifyBar", "setBossBarColor", "setBossBarStyle", "setTallDisguisesVisible",
"setDynamicName", "setSoundGroup", "setDisguiseName", "setDeadmau5Ears"));
if (NmsVersion.v1_21_R1.isSupported()) {
extraMethods.add("setScalePlayerToDisguise");
}
// Add these last as it's what we want to present to be called the least // Add these last as it's what we want to present to be called the least
for (String methodName : new String[]{"setSelfDisguiseVisible", "setHideHeldItemFromSelf", "setHideArmorFromSelf", for (String methodName : extraMethods) {
"setHearSelfDisguise", "setHidePlayer", "setExpires", "setNotifyBar", "setBossBarColor", "setBossBarStyle",
"setTallDisguisesVisible", "setDynamicName", "setSoundGroup", "setDisguiseName", "setDeadmau5Ears"}) {
try { try {
Class cl = boolean.class; Class cl = boolean.class;
Class disguiseClass = Disguise.class; Class disguiseClass = Disguise.class;
@ -226,11 +236,16 @@ public class DisguiseMethods {
(a) -> new ArrayList<>()).add(method); (a) -> new ArrayList<>()).add(method);
String getName = (cl == boolean.class ? "is" : "get") + methodName.substring(3); String getName = (cl == boolean.class ? "is" : "get") + methodName.substring(3);
boolean[] hiddenFor = new boolean[DisguiseType.values().length];
// No one really cares about it but don't let players see it if they don't have premium
if (methodName.equals("setScalePlayerToDisguise") && !LibsPremium.isPremium()) {
Arrays.fill(hiddenFor, true);
}
WatcherMethod getMethod = new WatcherMethod(disguiseClass, WatcherMethod getMethod = new WatcherMethod(disguiseClass,
MethodHandles.publicLookup().findVirtual(disguiseClass, getName, MethodType.methodType(cl)), getName, MethodHandles.publicLookup().findVirtual(disguiseClass, getName, MethodType.methodType(cl)), getName,
getName, cl, null, randomDefault, false, new boolean[DisguiseType.values().length], getName, cl, null, randomDefault, false, new boolean[DisguiseType.values().length], hiddenFor);
new boolean[DisguiseType.values().length]);
methods.add(getMethod); methods.add(getMethod);
break; break;

View File

@ -13,6 +13,17 @@ ViewSelfDisguises: true
# Default is true # Default is true
ViewSelfDisguisesDefault: true ViewSelfDisguisesDefault: true
# If this is enabled and the server is 1.21+, players will be given the scale attribute to scale them up/down to the disguise's size
# This will only work on living disguises, and is false by default due to the possibility of abuse as it'd shrink hitboxes and the like
# This may behave unexpectably if you're playing with other scaling modifiers outside of this plugin!
# An example of what this setting does, is if you disguise as a cat you will be scaled down so your viewpoint is at the same height of an actual cat
# The player's move, jump, etc is unchanged
SelfDisguisesScaling: false
# The max size a self disguise will change the player to match, 1 means they can only shrink, 2 means they can go up to 2x the size
# There is no min set as there's not much of a point, disable this entirely if you need the min.
SelfDisguisesScaleMax: 1
# Shall the disguised hear their disguise sounds or their damage sounds. # Shall the disguised hear their disguise sounds or their damage sounds.
# I disable this as it can be a little confusing when not used with self disguises # I disable this as it can be a little confusing when not used with self disguises
HearSelfDisguise: true HearSelfDisguise: true
@ -20,8 +31,15 @@ HearSelfDisguise: true
# Some disguises are rather big and tall and block your vision # Some disguises are rather big and tall and block your vision
# By default those disguises are disabled, such as zombies, players, etc. # By default those disguises are disabled, such as zombies, players, etc.
# The baby versions however, are normally short enough that it's a non-issue # The baby versions however, are normally short enough that it's a non-issue
# false = hidden, true = shown
TallSelfDisguises: false TallSelfDisguises: false
# This setting which is for servers that are 1.21+, allows the server to scale down the self disguise instead of hiding it completely
# If a player looks down, they'll see a mini figure of the previously large disguise
# This setting only works if the disguise wouldn't be shown as it's too tall, aka the above setting is false
# This will only work on living disguises!
TallSelfDisguisesScaling: true
# Hide players in tab when disguised? This means a disguised player cannot be seen when you press tab! This can be toggled on/off per disguise # Hide players in tab when disguised? This means a disguised player cannot be seen when you press tab! This can be toggled on/off per disguise
HideDisguisedPlayersFromTab: false HideDisguisedPlayersFromTab: false

View File

@ -146,6 +146,14 @@ public class DisguiseUtilitiesTest {
Assertions.assertFalse(DisguiseUtilities.isOlderThan("1.0", "1")); Assertions.assertFalse(DisguiseUtilities.isOlderThan("1.0", "1"));
Assertions.assertFalse(DisguiseUtilities.isOlderThan("1.0", "1.0")); Assertions.assertFalse(DisguiseUtilities.isOlderThan("1.0", "1.0"));
Assertions.assertFalse(DisguiseUtilities.isOlderThan("1", "1.0")); Assertions.assertFalse(DisguiseUtilities.isOlderThan("1", "1.0"));
Assertions.assertFalse(DisguiseUtilities.isOlderThan("3.0.0", "3.1.0"));
Assertions.assertFalse(DisguiseUtilities.isOlderThan("3.0.0", "3.0.1"));
Assertions.assertFalse(DisguiseUtilities.isOlderThan("3.0.0", "3.0.1-SNAPSHOT"));
Assertions.assertFalse(DisguiseUtilities.isOlderThan("3.1.0", "3.1.1-SNAPSHOT"));
Assertions.assertFalse(DisguiseUtilities.isOlderThan("3.1.1-SNAPSHOT", "3.4.0"));
Assertions.assertFalse(DisguiseUtilities.isOlderThan("3.1.1-SNAPSHOT", "3.4.0-SNAPSHOT"));
Assertions.assertFalse(DisguiseUtilities.isOlderThan("2.3.1", "2.4.0-SNAPSHOT"));
} }
@Test @Test

View File

@ -24,7 +24,7 @@
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<lombok.version>1.18.32</lombok.version> <lombok.version>1.18.32</lombok.version>
<packetevents.version>2.3.1-SNAPSHOT</packetevents.version> <packetevents.version>2.4.0-SNAPSHOT</packetevents.version>
<spigot.version>1.21-R0.1-SNAPSHOT</spigot.version> <spigot.version>1.21-R0.1-SNAPSHOT</spigot.version>
<junit.version>4.13.2</junit.version> <junit.version>4.13.2</junit.version>
<junit-jupiter.version>5.9.3</junit-jupiter.version> <junit-jupiter.version>5.9.3</junit-jupiter.version>